How the ADHD Engine's Phase 0 Reframe Pass Strips Incidental Anchors from Problem Statements

The reframe pass uses a specialized system prompt to instruct an LLM to identify and remove implementation-specific details—such as existing tech stacks or team structures—while preserving genuine constraints, then replaces the original problem statement with the cleaned version for subsequent divergence phases.

The reframe pass serves as the foundation of the ADHD engine's creative process, operating as Phase 0 before any divergent thinking begins. Located in src/engine.ts, this preprocessing step ensures that incidental anchors—unintentional constraints baked into problem wording—do not bias every subsequent branch of exploration. By sanitizing inputs through an LLM-guided analysis, the engine creates a neutral starting point where only load-bearing constraints (compliance, budget, physical limits) survive.

What the Reframe Pass Does

The implementation follows a five-stage pipeline that transforms raw problem statements into anchor-free versions suitable for broad exploration.

System Prompt Definition

At the core of the process lies the REFRAME_SYSTEM constant, which defines the LLM's role as a constraint analyzer. This prompt explicitly directs the model to distinguish between superficial implementation details and essential limits.

const REFRAME_SYSTEM = `You strip load‑bearing anchors from a problem statement ...`;

The full definition resides in src/engine.ts at lines 96-113, where the system prompt instructs the LLM to eliminate references to current tech stacks, existing tools, or team structures while guarding true constraints.

LLM Call via reframeProblem

The reframeProblem helper function (lines 123-140) constructs the user payload and executes the LLM call. It combines the original problem with optional context, then transmits both to the model using the reframe system prompt.

const raw = await callLLM({ model, systemPrompt: REFRAME_SYSTEM, userPrompt });

This abstraction ensures consistent prompting across all reframe operations.

Structured Output Parsing

The LLM must return valid JSON conforming to ReframeSchema, defined at lines 55-59. The engine strictly parses this output to extract three critical fields:

  • reframed – The potentially modified problem statement.
  • changed – A boolean flag indicating whether any anchors were removed.
  • note – An optional explanation of what specific anchors were stripped.
const parsed = parseJSON(raw, ReframeSchema);

Decision Logic in the Run Loop

Within the main run function (lines 31-46), the engine evaluates whether anchor stripping is enabled and whether the reframe produced valid results. When stripAnchors is true and the LLM returns changed: true with non-empty content, the engine swaps the original problem for the reframed version.

if (stripAnchors) {
    const r = await reframeProblem(problem, context, model);
    if (r.changed && r.reframed.trim().length > 0) {
        divergeProblem = r.reframed;
        reframe = r.reframed;
    }
    onEvent?.({ kind: "reframe:done", changed: Boolean(reframe) });
}

The reframed text becomes the input for the divergence phase, while the original remains stored in the final result for reference.

Event Emission for Transparency

Upon completion, the engine emits a reframe:done event to signal Phase 0 completion. The CLI handler at src/cli.ts (line 122) listens for this event to display "↺ anchors stripped from problem" notifications, providing users immediate visibility into preprocessing actions.

Why Anchor Stripping Matters

Removing incidental anchors provides three strategic advantages for creative problem-solving.

  • Isolation of branches – Every divergent branch receives the identical reframed problem, preventing a hidden anchor in the original wording from contaminating all exploration paths simultaneously.
  • Preservation of real constraints – Only non-negotiable limits survive the filter, allowing downstream ideas to explore novel architectures or tools while respecting essential boundaries.
  • Debugging transparency – The changed flag and optional note field make the transformation explicit, enabling users to audit exactly which constraints were removed and why.

Implementation Examples

Enabling the Reframe Pass

To activate Phase 0 processing, set stripAnchors: true in the configuration object passed to run():

import { run } from "./engine.js";

await run({
  problem: "Build a feature flag dashboard using our existing React+Redux stack.",
  context: undefined,
  stripAnchors: true,          // Enable Phase 0 reframe
  framesPerRun: 5,
  ideasPerFrame: 6,
  topK: 3,
});

Given this input, the LLM might return:

{
  "reframed": "Create a dashboard that lets users toggle feature flags and see their effects in real time.",
  "changed": true,
  "note": "Removed explicit mention of React+Redux stack."
}

The engine subsequently diverges on the reframed statement, permitting solutions involving Vue, Svelte, or no-code alternatives that the original wording would have excluded.

Inspecting Reframe Results

Access the transformation metadata through the result object to verify what occurred during Phase 0:

const result = await run({ /* …options… */ });
console.log("Original problem:", result.problem);
console.log("Reframed problem:", result.reframe);

If no anchors required removal, result.reframe remains undefined and the changed flag returns false, indicating the original problem statement proceeded unmodified into divergence.

Summary

  • The reframe pass in src/engine.ts acts as Phase 0 of the ADHD engine, sanitizing problem statements before divergent thinking begins.
  • REFRAME_SYSTEM instructs the LLM to strip implementation-specific details while preserving load-bearing constraints.
  • reframeProblem handles the LLM invocation, while ReframeSchema validates the structured output containing reframed, changed, and note fields.
  • The stripAnchors parameter toggles the feature, and the reframe:done event provides CLI transparency.
  • Successful reframes replace the original problem for downstream phases, ensuring branches explore solutions free from incidental technological bias.

Frequently Asked Questions

What distinguishes an incidental anchor from a load-bearing constraint?

An incidental anchor represents an implementation detail assumed by the problem author—such as "using our React stack" or "integrating with the current CRM"—that unnecessarily restricts solution space. A load-bearing constraint is a fundamental limit that must persist across all solutions, such as "must comply with HIPAA" or "cannot exceed $10,000 budget." The REFRAME_SYSTEM prompt trains the LLM to recognize this distinction based on whether removing the detail would fundamentally alter the problem's solvability or merely change the implementation path.

How does the engine handle cases where no anchors exist?

When the LLM determines the problem statement contains no incidental anchors, it returns changed: false and typically mirrors the original text in the reframed field. The decision logic in run() checks r.changed && r.reframed.trim().length > 0; since changed is false, the engine retains the original problem for divergence while leaving result.reframe undefined. This ensures the process adds no overhead when problems are already anchor-free.

Can the reframe pass be disabled during engine execution?

Yes. The reframe pass is opt-in via the stripAnchors boolean parameter in the run() function options. If omitted or set to false, the engine skips the reframeProblem call entirely and proceeds directly to divergence using the original problem statement. This configuration is useful when working with abstract problem definitions or when the user explicitly wants to constrain solutions to specific technologies mentioned in the prompt.

What file handles the CLI feedback for anchor stripping?

The src/cli.ts module consumes the reframe:done event emitted by the engine. When the reframe pass completes—whether or not anchors were found—the CLI prints a status indicator (e.g., "↺ anchors stripped from problem") to stderr, keeping users informed of preprocessing activity without polluting the structured JSON output stream.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →