denoland/deno · error · AnyError

Task not found

Error message

Task not found: {}

What it means

While topologically sorting matched tasks (sort_tasks_topo in cli/tools/task.rs), Deno resolves every task's `dependencies` array; a dependency naming a task that exists in no workspace package yields TaskError::NotFound. The name in the message is the missing *dependency*, not the task you asked for. When invoked via `deno run <name>` (task_flags.is_run, set in cli/lib.rs:414) it becomes a hard error; under `deno task` it is logged with the list of available tasks and exit code 1.

Solutions

  1. Run `deno task` with no arguments to list the task names that actually exist.
  2. Fix the deno.json `dependencies` array of the task that references the missing name — the {name} in the message tells you exactly which entry is dangling.
  3. If the dependency is optional, either remove it from the list or define a no-op task ("clean": "echo skip") for it.

Example fix

// deno.json — before
{
  "tasks": {
    "build": { "dependencies": ["clean", "bundle"] },
    "bundle": "esbuild src/index.ts --bundle"
  }
}

// after — define the missing dependency
{
  "tasks": {
    "build": { "dependencies": ["clean", "bundle"] },
    "clean": "rm -rf dist",
    "bundle": "esbuild src/index.ts --bundle"
  }
}
Defensive patterns

Strategy: validation

Validate before calling

// Verify every dependency referenced in deno.json exists before running tasks
import denoJson from "./deno.json" with { type: "json" };
const tasks: Record<string, unknown> = denoJson.tasks ?? {};
const names = new Set(Object.keys(tasks));
for (const [name, def] of Object.entries(tasks)) {
  const deps = (def as { dependencies?: string[] })?.dependencies ?? [];
  for (const dep of deps) {
    if (!names.has(dep)) throw new Error(`task "${name}" depends on missing task "${dep}"`);
  }
}

Type guard

const taskExists = (name: string, tasks: Record<string, unknown>) =>
  Object.hasOwn(tasks, name);

Prevention

When it happens

Trigger: deno task build (or deno run build) where build has "dependencies": ["clean"] and no task named clean exists in any member's deno.json tasks or package.json scripts; a workspace member with the task was removed or renamed.

Common situations: Renaming a task without updating dependents; typos in dependency arrays; copy-pasting tasks from another repo that reference repo-local tasks; workspace restructuring that moved a task to a non-member directory.

Related errors


AI-assisted analysis of denoland/deno@9ad36f7a2c (2026-08-20). Data as JSON: /api/errors/5ab5a4a4b115a93b. Report an issue: GitHub.

Appendix: source

Thrown at cli/tools/task.rs:434

impl<'a> TaskRunner<'a> {
  /// Topologically sort all matched tasks across the given packages into a
  /// single flat list, then run them through `run_tasks_in_parallel` so tasks
  /// from sibling packages execute concurrently.
  pub async fn run_all_tasks(
    &self,
    packages: &'a [PackageTaskInfo],
    task_name: &str,
    kill_signal: &KillSignal,
    argv: &'a [String],
  ) -> Result<i32, deno_core::anyhow::Error> {
    let mut sorted: Vec<ResolvedTask<'a>> = Vec::new();
    for pkg in packages {
      if let Err(err) = sort_tasks_topo(pkg, &mut sorted) {
        return match err {
          TaskError::NotFound(name) => {
            if self.task_flags.is_run {
              return Err(anyhow!("Task not found: {}", name));
            }
            log::error!("Task not found: {}", name);
            if log::log_enabled!(log::Level::Error) {
              self.print_available_tasks(&pkg.tasks_config)?;
            }
            Ok(1)
          }
          TaskError::TaskDepCycle { path } => {
            log::error!("Task cycle detected: {}", path.join(" -> "));
            Ok(1)
          }
        };
      }
    }

    if sorted.is_empty() {
      if self.task_flags.is_run {
        return Err(anyhow!("Task not found: {}", task_name));

View on GitHub (pinned to 9ad36f7a2c)