Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/nrwl/nx/llms.txt

Use this file to discover all available pages before exploring further.

In a monorepo, tasks rarely run in isolation. Building myapp requires building shared-ui and feat-products first. Nx manages these relationships through a task pipeline — a set of rules that determine execution order and parallelism.

Why pipelines matter

Without a task pipeline, you have two bad options:
  1. Run tasks serially in a manually maintained order — slow and brittle as the repo grows.
  2. Run all tasks in parallel — broken, because some tasks depend on the outputs of others.
Nx’s task pipeline gives you the best of both: tasks that can run concurrently do run concurrently, while tasks that have dependencies wait for those dependencies to complete.
         shared-ui:build

      feat-products:build

        myreactapp:build
In this example, shared-ui:build and feat-products:build are sequenced correctly, and anything that doesn’t share a dependency edge runs in parallel.

Configuring task dependencies

Task dependencies are declared with the dependsOn property. You can set this globally in nx.json under targetDefaults, or locally in a project’s project.json or package.json.

Global defaults in nx.json

nx.json
{
  "targetDefaults": {
    "build": {
      "dependsOn": ["^build", "prebuild"]
    },
    "test": {
      "dependsOn": ["build"]
    }
  }
}
With this configuration, running nx test myproj causes Nx to:
  1. Run myproj:build first (because test depends on build of the same project)
  2. Run build for all of myproj’s dependencies first (because build depends on ^build — the ^ means “dependencies in the project graph”)
  3. Run myproj:prebuild before myproj:build (same-project dependency without ^)

Per-project configuration

Project-level configuration overrides global defaults for that project only:
apps/myapp/project.json
{
  "name": "myapp",
  "targets": {
    "build": {
      "executor": "@nx/webpack:webpack",
      "dependsOn": ["^build"],
      "outputs": ["{projectRoot}/dist"]
    },
    "test": {
      "executor": "@nx/jest:jest",
      "dependsOn": ["build"],
      "outputs": ["{workspaceRoot}/coverage/apps/myapp"]
    }
  }
}

The dependsOn syntax

The ^ prefix means “run this target for all projects that this project depends on in the project graph.” This is the most common pattern for build tasks, ensuring that library builds complete before app builds start.
"dependsOn": ["^build"]
Without a ^, the dependency refers to a target on the same project. This lets you chain targets within a single project.
"dependsOn": ["prebuild"]
You can also declare dependencies on specific named projects:
"dependsOn": [
  { "projects": "some-lib", "target": "build" }
]

Parallelism

Nx runs as many tasks in parallel as the dependency constraints allow. The default parallelism limit is 3 concurrent tasks. You can override this with --parallel:
nx run-many -t build --parallel=5
Tasks that share a dependency edge always run sequentially in the correct order. Only tasks with no dependency relationship between them run in parallel.

Example: parallel vs. sequential

Given three projects where app1 and app2 both depend on lib:
nx.json
{
  "targetDefaults": {
    "build": {
      "dependsOn": ["^build"]
    }
  }
}
Running nx run-many -t build produces this execution order:
Step 1 (parallel): lib:build
Step 2 (parallel): app1:build, app2:build
Both app builds start as soon as lib:build completes. Nx does not wait for one app to finish before starting the other.

Mixing targets in one run

Task graphs can contain different targets running simultaneously. For instance, while Nx is building app2, it can be testing app1 at the same time — as long as neither task depends on the other.
# Build and test run concurrently where the dependency graph allows
nx run-many -t build,test

Scope of configuration

LocationScopeOverride priority
nx.json targetDefaultsAll projectsLowest
project.json / package.json per-projectSingle projectHighest
Project-level configuration always wins over targetDefaults.
See the Configuration reference for all targetDefaults options including advanced patterns like cross-target dependencies and self-referential dependsOn.