Skip to content

feat(validation): warn when explicit-mode agent prompts reference undeclared inputs #105

@PolyphonyRequiem

Description

@PolyphonyRequiem

Provenance: AI-drafted (GitHub Copilot CLI / Claude Opus 4.6), human-reviewed and approved, AI-submitted.

Problem

When using context.mode: explicit, agent prompts can reference {{ workflow.input.X }} variables that aren't declared in the agent's input: list. The workflow validates and loads successfully, but fails at runtime with a TemplateError:

TemplateError: Undefined variable in template: 'dict object' has no attribute 'prompt'

This is a silent misconfiguration — the validator doesn't check whether prompt templates reference variables that will be available in the agent's scoped context.

Example

workflow:
  name: example
  context:
    mode: explicit
  input:
    work_item_id: { type: number, required: true }
    prompt: { type: string, required: false }

agents:
  - name: intake
    input:
      - workflow.input.work_item_id   # declared
      # workflow.input.prompt NOT declared
    prompt: |
      Work item: {{ workflow.input.work_item_id }}
      {% if workflow.input.prompt %}          <-- BOOM: 'prompt' not in scope
      Prompt: {{ workflow.input.prompt }}
      {% endif %}

conductor validate reports success. At runtime, the prompt template fails because workflow.input.prompt isn't in the agent's explicit context.

Impact

This is especially painful when:

  • Sharing prompts across workflows via !file — different workflows declare different inputs, but the shared prompt references all of them
  • Extracting sub-workflows — the new workflow needs to re-declare every input the shared prompt touches, and missing one is a silent error until runtime
  • Refactoring inputs — adding/renaming a workflow input requires checking every agent's input: list manually

We hit this repeatedly while decomposing a large workflow into sub-workflows. Each missing input declaration caused a runtime crash that could have been caught at validation time.

Proposed solution

During conductor validate, when context.mode: explicit:

  1. Parse Jinja2 template expressions in each agent's prompt and system_prompt
  2. Extract referenced variables (e.g., workflow.input.X, agent_name.output.Y)
  3. Check that each referenced variable is reachable from the agent's input: declarations
  4. Emit a warning (not error) for unreachable references — some may be guarded by {% if X is defined %} conditionals

A warning is preferable to an error because:

  • Some templates use {% if X is defined %} guards intentionally
  • Full Jinja2 static analysis is hard; false positives are possible
  • A warning catches the common case (forgot to add to input:) without breaking valid workflows

Scope

This applies to explicit mode only. In accumulate and last_only modes, all prior outputs are available, so missing input: declarations don't cause template failures.

Provenance: Found during production workflow decomposition. AI-reported, human-reviewed.

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions