v1.0.0 — 13 ecosystems supported

Run only what matters.

A standalone CLI that detects affected packages in your monorepo — then runs tests, lints, or any command on only those packages.

Get Started
~/projects/myappon main$

13 ecosystems, zero configuration. Auto-detected from your manifest files.

CargonpmpnpmYarnBunGoPythonMavenGradle.NETSwiftDartElixir

Built different.

Zero config. Zero dependencies. Just one binary that understands your entire monorepo.

affected — zsh
$ affected test --base main
Detected ecosystem: Cargo workspace
Found 23 packages, 4 affected
Running: cargo test -p core -p api -p cli -p utils
✓ All 4 tests passed · 3.1s

Zero Configuration

Auto-detects your ecosystem from manifest files. Cargo.toml? Rust workspace. package.json? Node monorepo. No setup required.

affected
~5 MB
Turborepo
~100+ MB
Nx
~200+ MB
Bazel
~500+ MB
~5MB
Single binaryNo runtime

Lightning Fast

Single ~5MB Rust binary. No Node.js, no JVM, no runtime dependencies. Starts in milliseconds.

changed
core
api
affected
cli
affected
web
affected

Full Blast Radius

Transitive dependency graph analysis. If core changes and api depends on it, both are affected.

.github/workflows/ci.yml
# .github/workflows/ci.yml
- uses: Rani367/setup-affected@v1
- run: affected test --base $${{ github.event.pull_request.base.sha }}
- run: affected lint --output junit
GitHub ActionsGitLab CICircleCIAzure PipelinesJenkins

CI-Native

GitHub Actions, GitLab CI, CircleCI, Azure Pipelines. Dynamic matrices, PR comment bot, JUnit output.

How it
works

From git diff to targeted test execution — six steps, milliseconds. affected builds a dependency graph of your monorepo, diffs against your base branch, and runs commands on only the affected packages.


01
Detect. Scans for manifest files to identify your ecosystem.
02
Resolve. Parses manifests into a full dependency graph.
03
Diff. Computes changed files via libgit2.
04
Map. Maps each changed file to its owning package.
05
Traverse. Reverse BFS to find all dependents.
06
Execute. Runs your command on only the affected packages.
$ affected list --base main --explain
3 affected package(s):
core (directly changed: src/lib.rs)
api (depends on: core)
cli (depends on: api → core)

The --explain flag

See exactly why each package is affected. Full dependency chain visualization from changed file to impacted package.

$ affected test --watch --base main
watching 3 packages...
──────────────────────
~ src/core/mod.rs modified
re-running: cargo test -p core
core passed (0.6s)

Watch mode

Re-runs on file change. Built-in debouncing for smooth dev loops. Your tests stay in sync as you code.

How affected
stacks up

The power of a build system. The simplicity of a CLI.


Feature
affected ✦
Nx
Turborepo
Bazel
Zero config
Standalone binary
Node.js
Node.js
JVM
Setup time
1 min
Hours
Hours
Days
Binary size
~5 MB
~200 MB+
~100 MB+
~500 MB+
Ecosystems
13
JS/TS
JS/TS
Any
--explain
Watch mode
Multi-CI
5 platforms
GitHub
GitHub
Custom

Get running in
60 seconds

Choose your preferred method. All roads lead to affected.


Homebrew

$brew install Rani367/tap/affected

Cargo

$cargo install affected-cli

uv / pipx

$uv tool install affected

GitHub Actions

$uses: Rani367/setup-affected@v1

Star on GitHub to support the project

Star on GitHub