Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 0 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
# Changelog

- **Added** `dependsOn` can now run the specified task in each direct workspace package listed in `dependencies`, `devDependencies`, or `peerDependencies`; for example, `{ "task": "build", "from": ["dependencies", "devDependencies"] }` runs `build` in each direct dependency and dev dependency ([#467](https://github.com/voidzero-dev/vite-task/pull/467), [#469](https://github.com/voidzero-dev/vite-task/pull/469)).
- **Added** First-party support for caching `vite build` with zero cache config, giving Vite projects correct cache hits out of the box ([vitejs/vite#22453](https://github.com/vitejs/vite/pull/22453)).
- **Added** [`@voidzero-dev/vite-task-client`](https://npmx.dev/package/@voidzero-dev/vite-task-client), allowing tools to report cache information to Vite Task at runtime so users do not need to configure it manually ([#441](https://github.com/voidzero-dev/vite-task/pull/441), [#454](https://github.com/voidzero-dev/vite-task/pull/454), [#449](https://github.com/voidzero-dev/vite-task/pull/449), [#450](https://github.com/voidzero-dev/vite-task/pull/450), [#458](https://github.com/voidzero-dev/vite-task/pull/458), [#431](https://github.com/voidzero-dev/vite-task/pull/431), [#459](https://github.com/voidzero-dev/vite-task/pull/459), [#472](https://github.com/voidzero-dev/vite-task/pull/472)).
- **Changed** Cached tasks now restore automatically tracked output files by default; use `output: []` to disable restoration ([#460](https://github.com/voidzero-dev/vite-task/pull/460), [#461](https://github.com/voidzero-dev/vite-task/pull/461)).
Expand Down
1 change: 0 additions & 1 deletion Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 2 additions & 2 deletions crates/vite_task/docs/boolean-flags.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ This document describes how boolean flags work in `vp` commands.
- `--recursive` / `-r` — Run task in all packages in the workspace
- `--transitive` / `-t` — Run task in the current package and its transitive dependencies
- `--workspace-root` / `-w` — Run task in the workspace root package
- `--ignore-depends-on` — Skip `dependsOn` dependencies
- `--ignore-depends-on` — Skip explicit `dependsOn` dependencies
- `--verbose` / `-v` — Show full detailed summary after execution
- `--cache` / `--no-cache` — Force caching on or off for all tasks and scripts

Expand Down Expand Up @@ -39,7 +39,7 @@ vp run build -t
# Run in workspace root
vp run build -w

# Skip dependsOn dependencies
# Skip explicit dependsOn edges
vp run build --ignore-depends-on

# Verbose output
Expand Down
45 changes: 8 additions & 37 deletions crates/vite_task/docs/task-query.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,14 +7,13 @@ How `vp run` decides which tasks to run and in what order.
When `vp` starts, it builds two data structures from the workspace:

1. **Package graph** — which packages depend on which. Built from `package.json` dependency fields.
2. **Task graph** — which tasks exist and their string-form `dependsOn` relationships. Built from `vite.config.*` and `package.json` scripts.
2. **Task graph** — which tasks exist and their explicit `dependsOn` relationships. Built from `vite.config.*` and `package.json` scripts.

Both are built once and reused for every query, including nested `vp run` calls inside task scripts.

### What goes into the task graph

The task graph contains a node for every task in every package. String-form
`dependsOn` declarations become edges in this graph:
The task graph contains a node for every task in every package, and edges only for explicit `dependsOn` declarations:

```jsonc
// packages/app/vite.config.*
Expand All @@ -38,8 +37,6 @@ Task graph:
```

Package dependency ordering (app depends on lib) is NOT stored as edges in the task graph. Why not is explained below.
Object-form `dependsOn` entries are also not stored as global task graph edges;
they are kept on the declaring task and expanded for each query.

## What happens when you run a query

Expand Down Expand Up @@ -77,7 +74,7 @@ Given the package subgraph and a task name, we build the execution plan:
1. Find which selected packages have the requested task.
2. For packages that don't have it, reconnect their predecessors to their successors (skip-intermediate, explained below).
3. Map the remaining package nodes to task nodes — this gives us topological ordering.
4. Expand `dependsOn` from these tasks (may pull in tasks from outside the selected packages).
4. Follow explicit `dependsOn` edges outward from these tasks (may pull in tasks from outside the selected packages).

The result is the execution plan: which tasks to run and in what order.

Expand Down Expand Up @@ -172,11 +169,9 @@ The package subgraph is already a lightweight `DiGraphMap<PackageNodeIndex, ()>`

So we clone the `DiGraphMap` once and mutate the clone. We iterate the original (stable node order) while modifying the clone.

## `dependsOn` expansion
## Explicit dependency expansion

After mapping the package subgraph to tasks, we expand `dependsOn` entries.
String-form entries follow task graph edges and can pull in tasks from packages
outside the selected set.
After mapping the package subgraph to tasks, we follow explicit `dependsOn` edges from the task graph. This can pull in tasks from packages outside the selected set.

```jsonc
// packages/app/vite.config.*
Expand All @@ -193,31 +188,7 @@ If you run `vp run --filter app build`, the package subgraph contains only `app`

This is intentional — `dependsOn` is an explicit declaration that a task can't run without its dependency. Ignoring it would break the build. (Users can skip this with `--ignore-depends-on`.)

Object-form entries select direct package dependencies from the declaring task:

```jsonc
// packages/app/vite.config.*
{
"tasks": {
"test": {
"command": "vitest run",
"dependsOn": [{ "task": "build", "from": ["dependencies", "devDependencies"] }],
},
},
}
```

For `app#test`, this runs `build` in direct workspace dependency packages selected
by the listed package.json fields. Packages without `build` are skipped. Supported
fields are `dependencies`, `devDependencies`, and `peerDependencies`.

Recursive expansion comes from dependency tasks declaring their own `dependsOn`
entries. For example, if `ui#build` also has `{ "task": "build", "from": "dependencies" }`,
then `tokens#build` is selected while expanding `ui#build`.

The expansion follows `dependsOn` entries, not every topological edge.
Topological ordering comes from the package subgraph — it's already baked into
the task execution graph by Stage 2.
The expansion only follows explicit edges, not topological ones. Topological ordering comes from the package subgraph — it's already baked into the task execution graph by Stage 2.

## Nested `vp run`

Expand All @@ -242,7 +213,7 @@ The nested query produces its own execution subgraph, which gets embedded inside
```
Startup (once):
workspace files ──> package graph ──> task graph
(dependencies) (tasks + string dependsOn edges)
(dependencies) (tasks + dependsOn edges)

Per query:
CLI flags ──> PackageQuery
Expand All @@ -254,7 +225,7 @@ Per query:
task graph ────> task execution graph
(map packages to tasks,
skip-intermediate reconnection,
dependsOn expansion)
explicit dep expansion)
execution plan
Expand Down
1 change: 0 additions & 1 deletion crates/vite_task_graph/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@ serde = { workspace = true, features = ["derive"] }
serde_json = { workspace = true }
thiserror = { workspace = true }
tracing = { workspace = true }
vec1 = { workspace = true, features = ["serde"] }
vite_path = { workspace = true }
vite_str = { workspace = true }
vite_workspace = { workspace = true }
Expand Down
24 changes: 2 additions & 22 deletions crates/vite_task_graph/run-config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,6 @@ auto: boolean, };

export type Command = string | Array<string>;

export type DependencyType = "dependencies" | "devDependencies" | "peerDependencies";

export type DependsOnEntry = string | UserPackageDependency;

export type DependsOnFrom = DependencyType | Array<DependencyType>;

export type GlobWithBase = {
/**
* The glob pattern (positive or negative starting with `!`)
Expand All @@ -36,13 +30,9 @@ command: Command,
*/
cwd?: string,
/**
* Dependencies of this task.
*
* String entries keep same-package / `package-name#task-name` behavior.
* Object entries run a task name in direct workspace dependency
* packages selected by package.json dependency fields.
* Dependencies of this task. Use `package-name#task-name` to refer to tasks in other packages.
*/
dependsOn?: Array<DependsOnEntry>, } & ({
dependsOn?: Array<string>, } & ({
/**
* Whether to cache the task
*/
Expand Down Expand Up @@ -105,16 +95,6 @@ scripts?: boolean,
*/
tasks?: boolean, };

export type UserPackageDependency = {
/**
* Task name to run in dependency packages.
*/
task: string,
/**
* Package.json dependency field or fields to use when selecting direct dependency packages.
*/
from: DependsOnFrom, };

export type RunConfig = {
/**
* Root-level cache configuration.
Expand Down
8 changes: 3 additions & 5 deletions crates/vite_task_graph/src/config/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,8 @@ use rustc_hash::FxHashSet;
use serde::Serialize;
pub use user::{
AutoTracking, Command, EnabledCacheConfig, GlobWithBase, InputBase, ResolvedGlobalCacheConfig,
UserCacheConfig, UserDependencyType, UserDependsOnEntry, UserDependsOnFrom,
UserGlobalCacheConfig, UserInputEntry, UserInputsConfig, UserOutputEntry,
UserPackageDependency, UserRunConfig, UserTaskConfig, UserTaskDefinition,
UserCacheConfig, UserGlobalCacheConfig, UserInputEntry, UserInputsConfig, UserOutputEntry,
UserRunConfig, UserTaskConfig, UserTaskDefinition,
};
use vite_path::AbsolutePath;
use vite_str::Str;
Expand All @@ -26,8 +25,7 @@ use crate::config::user::UserTaskOptions;
/// For example, `cwd` is resolved to absolute ones (no external factor can change it),
/// but `command` is not parsed into program and args yet because environment variables in it may need to be expanded.
///
/// `depends_on` is not included here because string-form entries are represented by task graph
/// edges, and package dependency entries are stored separately on the indexed task graph.
/// `depends_on` is not included here because it's represented by the edges of the task graph.
#[derive(Debug, Serialize)]
pub struct ResolvedTaskConfig {
/// The command or commands to run for this task.
Expand Down
Loading
Loading