Files
confidence-engine/docs/design-evolution-log.md
T
robbond eee8c6b1e4 experiment: compare acknowledge priority alternatives
Experiment 41 compared two passive alternatives for reducing Acknowledge dominance:

Variant A (priority reordering): evaluate Summarise/Pause before Acknowledge
- Converges on concluding→summarise and stalled→pause correctly
- Introduces false-positive summarise at long-investigation t3

Variant B (Acknowledge exclusions): gate Acknowledge via phase/progress/health
- Converges on the same two genuine changes without false-positives
- Recommended: cleaner boundaries, preserves Acknowledge for healthy focus states

Both variants produce identical results for 2 of 7 tested turns.
Variant A diverges at long-investigation t3 (focusing phase with resolvedNodeCount=3).
Variant B correctly preserves Acknowledge there via its exclusion list.

Test files:
- tests/behaviour-selection.counterfactual.test.js (44 tests, new)
No production code changed.
2026-08-06 17:19:02 +01:00

136 KiB
Raw Blame History

Design Evolution Log

A chronological record of why significant design decisions were made. This is NOT a changelog. It records the product's evolution of thinking.

This document records discoveries, not decisions. Every entry represents our best understanding at that point in time and may later be superseded by a better model.


Phase 1

Simple conversational investigation

Question → Answer interaction.

Purpose: Prove the reasoning loop.

Learning: Conversation alone does not provide sufficient context during longer investigations.


Phase 2

Persistent investigation notebook

Added:

  • current understanding
  • original situation
  • investigation history

Learning: Users need persistent context rather than remembering previous answers.


Phase 3

Document workspace

Created a coherent workspace with:

  • investigation status
  • current investigation
  • response
  • understanding
  • investigation map placeholder
  • situation
  • history

Learning: The interface became usable but still behaved like a document rather than a workspace.


Phase 4 (Current Exploration)

Facilitated Investigation Workshop

Status: Experimental.

Hypothesis:

The Confidence Engine is not:

  • a chatbot
  • a dashboard
  • a form

It is a facilitated investigation workspace.

The interface should resemble the environment in which structured thinking happens.

Record discoveries rather than conclusions.

Leave room for future phases.


Phase 4 — Guiding Principles

The Confidence Engine is a workspace, not a document.

People think in multiple directions simultaneously.

Useful context should be visible together.

The interface should favour thinking over scrolling.

The workspace should feel like a large desk or workshop rather than a narrow report.

The engine facilitates thinking.

The user contributes evidence.

The workspace captures shared understanding.

Experiment 01 — Wider canvas

Hypothesis: The document-like feeling is caused partly by the narrow outer container.

Change: Increase the available desktop workspace width without rearranging any components.

Result: Confirmed.

Learning: Increasing the outer workspace width reduced the narrow-document feeling and made better use of large displays.

Unexpected learning: Width alone did not create a workshop. The wider canvas exposed that the interface still behaves as a collection of independent cards, with supporting artefacts unsure how to use the available space.

Decision: Keep the wider desktop canvas.

Next question: Can grouping the interface into cognitive work zones make the wider canvas feel like a coherent investigation surface?

Experiment 02 — Cognitive work zones

Hypothesis: A workspace organised around what the investigator is doing will feel more coherent than one organised around equal cards or equal columns.

Result: Partially confirmed.

Learning:

The workspace feels more coherent when organised into cognitive work zones rather than a simple document stack.

However, another distinction emerged that is more important than the zones themselves.

The interface naturally separates into two different modes:

• the active conversation between investigator and facilitator

and

• the shared workspace describing the current understanding.

Unexpected learning:

History feels incorrect when treated as reference information.

History is actually the continuation of the investigator's conversation.

Every response immediately becomes history.

The notebook should therefore grow naturally from the Response area.

The Investigation Status card currently competes with the Current Investigation card.

The current question is the primary focus.

Status is supporting context.

Decision:

Keep the cognitive-zone concept.

Refine the zones around conversational flow instead of card grouping.

Next question: Can the workspace clearly separate conversation from shared understanding?

Experiment 03 — Conversation versus Workspace

Hypothesis

Investigators think in two simultaneous modes.

Mode 1: The conversation.

Question ↓

Response ↓

History

Mode 2: The shared workspace.

Status

Understanding

Situation

Map

Separating these should make the interface feel more like a facilitated investigation than a collection of cards.

Evaluation: Partially confirmed.

Learning:

The workspace feels more coherent when organised into cognitive zones rather than a simple document stack.

However, another distinction emerged that is more important than the zones themselves.

The interface naturally separates into two different modes:

• the active conversation between investigator and facilitator

and

• the shared workspace describing the current understanding.

Unexpected learning:

History feels incorrect when treated as reference information.

History is actually the continuation of the investigator's conversation.

Every response immediately becomes history.

The notebook should therefore grow naturally from the Response area.

The Investigation Status card currently competes with the Current Investigation card.

The current question is the primary focus.

Status is supporting context.

Decision:

Keep the cognitive-zone concept.

Refine the zones around conversational flow instead of card grouping.

Next question: Can the workspace clearly separate conversation from shared understanding?

Experiment 04 — Facilitated Workshop Introduction

Hypothesis

Beginning with a facilitator-style introduction will create more confidence than presenting an empty workspace.

Questions

  • Does the interface feel more welcoming?
  • Does reducing the visual weight of the textarea improve the first experience?
  • Does separating "starting" from "investigating" feel natural?
  • Does the transition into the investigation workspace feel meaningful?

Status: Experimental.

Result: Partially confirmed.

Learning:

The facilitator introduction reduced the intimidation of the first screen.

Replacing the empty landing page with a guided introduction improved the emotional tone.

However, stacking the introduction above the input still gives the introduction excessive visual prominence.

Repeat users may not want to repeatedly read the same introduction.

Orientation should remain available without dominating the workflow.

Decision:

Keep the introduction concept but change its spatial relationship to the workspace — move it from above to beside, making it optional rather than mandatory.

Next question: Does a horizontal facilitator/workspace layout feel more natural?

Experiment 05 — Facilitator Panel and Adaptive Landing Workspace

Hypothesis

Placing the facilitator beside the working area will feel more like entering a facilitated workshop than stacking instructional content above the workspace.

Allowing the user to dismiss the facilitator will reduce friction for returning users while preserving onboarding for new users.

Questions

  • Does a horizontal facilitator/workspace layout feel more natural?
  • Does the user's eye move naturally from facilitator to workspace?
  • Does the workspace become the primary focus?
  • Does "Don't show again" feel preferable to automatically hiding the introduction?
  • Should the facilitator panel become an optional workspace companion rather than mandatory onboarding?

Status: Completed.

Findings:

  • A horizontal facilitator/workspace arrangement feels more natural than stacked onboarding.
  • The workspace becomes the visual destination rather than the introduction.
  • User-controlled dismissal is preferable to automatic hiding.
  • The facilitator feels useful but visually too passive.
  • Remaining issues are now visual hierarchy rather than layout architecture.

Experiment 06 — Focused Investigation

Hypothesis

The interface should gently guide attention towards the current task without hiding supporting information.

Reducing competition between panels may improve concentration more than introducing additional colour or decoration.

Questions

  • Does visual emphasis naturally guide the eye?
  • Can supporting panels become quieter without disappearing?
  • Does the investigation question become the obvious focal point?
  • Does the workspace feel calmer?
  • Are we approaching a professional investigation environment?

Status: Closed.

Result

Partially confirmed.

What did we learn?

  • Stronger visual hierarchy can direct attention without rearranging the interface.
  • The facilitator briefing became easier to distinguish.
  • Colour and tint improved separation only modestly.
  • Meaning must not depend on colour.
  • Areas and intent should remain distinguishable through structure, spacing, typography, borders, shape and placement.
  • The initial textarea still implies that the user should provide a detailed report.
  • The size of an input communicates the amount of information expected.

Decision

Retain the useful hierarchy refinements provisionally.

Do not increase reliance on colour.

Defer dark mode and broader palette work.

The next experiment should test whether a smaller starting input better communicates that the user only needs to provide an initial observation.

Do not rewrite previous experiments.


Experiment 07 — Lightweight Starting Observation

Hypothesis

A smaller initial input will make beginning an investigation feel easier and will communicate that the engine needs only a concise observation rather than a complete analysis.

Questions

  • Does the input feel like a conversation starter rather than a report form?
  • Is three to four visible lines sufficient?
  • Does the facilitator panel and input area feel better balanced?
  • Does the user understand that further detail will be gathered through questions?
  • Does reducing the input height make the Analyse action easier to notice?

Evaluation

Pending visual review.

Result

Confirmed.

Four visible rows better communicates a starting observation than six.

Input size communicates expected effort.

"What have you noticed?" reinforces observational thinking.

Users are encouraged to begin rather than compose.

The facilitator and workspace now feel more balanced.

This interaction principle should continue throughout the investigation rather than existing only on the landing page.

Decision

Retain the smaller landing input.

Proceed to investigate consistency between the landing experience and investigation responses.


Experiment 09 — Investigation Rhythm

Result

Partially confirmed.

What did we learn?

  • Moving History directly beneath Response improves the sense of conversational continuity.
  • The sequence Question → Response → History is cognitively coherent.
  • History behaves like the growing notebook of the investigation, not general reference material.
  • Allowing History to span the full workspace breaks the wider spatial model.
  • Situation and Investigation Map should remain stable supporting artefacts rather than moving down as the notebook grows.
  • The conversation needs a dedicated vertical lane.

Decision

Keep History directly connected to Response.

Refine the desktop workspace into a stable conversation lane and a stable supporting lane.

Do not rewrite previous experiments.


Experiment 08 — Consistent Investigation Responses

Hypothesis

Every answer given during an investigation should feel like an observation, not a report.

The response component should therefore communicate the same expected effort as the initial scenario input.

Questions

  • Does a smaller response area reduce perceived effort?
  • Does the investigation feel more conversational?
  • Does consistency improve confidence?
  • Does the workspace become visually calmer?
  • Does the current investigation remain the dominant focus?

Result

Confirmed.

Consistent interaction patterns reduce cognitive effort.

Users should not have to learn different behaviours between the landing page and investigation.

Smaller response areas reinforce concise observations.

The engine appears more conversational when each answer feels lightweight.

Consistency is becoming a stronger design tool than decoration.

Decision

Retain consistent input sizing across both contexts.


Experiment 10 — Stable Conversation Column

Hypothesis

A persistent two-thirds conversation column beside a one-third supporting column will allow the investigation notebook to grow without moving the shared reference artefacts.

Questions

  • Does the left column feel like one continuous investigation?
  • Does History grow naturally beneath Response?
  • Do Situation and Investigation Map remain easy to reference?
  • Does the interface feel spatially stable as turns accumulate?
  • Does showing full question text improve readability now that sufficient width exists?

Evaluation

Visual review completed.

Status

Closed.

Result

Partially confirmed.

What did we learn?

  • The investigation workspace is beginning to feel like a genuine facilitated investigation rather than a document.

  • The two-column workspace (conversation on the left, reference material on the right) is proving to be a stronger mental model than previous layouts.

  • Keeping Situation and Investigation Map fixed while History grows vertically feels more natural.

  • The investigation question, response and history now read as one continuous conversation.

  • Developer Details have become extremely valuable.

  • The graph produced by the reasoning engine is far richer than previously realised. The graph now contains structured concepts including:

    • observations
    • unknowns
    • assumptions
    • relationships
    • metrics
    • state

This suggests the UI should increasingly become a human-friendly projection of the graph rather than inventing separate state.

The current "Investigation in progress" panel exposes developer-oriented statistics (nodes, edges, unknowns etc.) which are useful during development but are not the most helpful representation for an end user.


Emerging Direction — Graph as Source of Truth

The reasoning graph is becoming the shared source of truth for multiple UI views.

Different interfaces may project the same graph for different audiences:

  • Version A — compact technical progress;
  • Version B — detailed graph inspection;
  • Version C — user-facing facilitator view;
  • Developer Details — complete diagnostics;
  • Investigation Map — future spatial projection;
  • Current Question — active uncertainty projection.

The UI should not maintain separate invented summaries where the graph already contains the underlying information.

This is an emerging direction, not a final architecture decision.


Emerging Direction — Facilitator Translation Layer

The UI should progressively become a translation layer over the reasoning graph rather than maintaining separate duplicated summaries. Internal graph concepts should remain available for developers, while end users see a facilitator-style explanation of what is currently understood and what remains uncertain.

The current technical progress panel (nodes, edges, unknowns, assumptions) exposes developer-oriented statistics. These are valuable during development but not the most helpful representation for an end user.

The next direction is to explore presenting the same underlying graph data as a facilitator's notebook — what is known, what remains uncertain, and a quiet summary of the reasoning state underneath.


Experiment 11 — Facilitator Progress Panel (Version B)

Hypothesis

The same underlying reasoning graph can be presented in a much more human-friendly way without changing the reasoning engine, API contracts, or graph generation.

A facilitator-style panel should communicate:

  • what is known (resolved nodes and observations)
  • what remains uncertain (unresolved unknowns and assumptions)
  • a quiet summary of the reasoning state underneath

Questions

  • Can the same graph data be translated into a facilitator-style view that end users understand more naturally?
  • Does separating "known" from "still investigating" reduce cognitive load compared to node/edge counts?
  • Is a quiet reasoning summary sufficient, or does it need more context?
  • Does the translation-layer principle hold — presenting the graph as a notebook rather than raw data?

Result

Partially confirmed.

What did we learn?

  • Version B proved that the reasoning graph contains substantially more useful information than Version A exposes.
  • The graph already contains observations, unknowns, assumptions, metrics, relationships and state.
  • The graph is rich enough to support multiple UI projections.
  • Exposing the graph almost verbatim overwhelms the user.
  • Technical categories are useful for development but do not directly communicate investigation progress.
  • The user needs a translation of the graph rather than a graph browser.
  • Developer Details should remain the place for complete technical inspection.
  • A user-facing view needs filtering, prioritisation, deduplication and clear epistemic labels.

Decision

Keep Version A and Version B available for comparison.

Proceed with a Version C facilitator view built from the same graph.


Experiment 12 — Facilitator View (Version C)

Hypothesis

The existing reasoning graph can be deterministically translated into a concise facilitator view that helps the user understand:

  • what is currently known;
  • what remains uncertain;
  • what may explain the situation;
  • why the investigation is continuing.

Questions

  • Can the graph produce a useful human-facing summary without another LLM call?
  • Can observations, unknowns and assumptions be clearly distinguished?
  • Can duplicate or low-value graph content be filtered reliably?
  • Does a concise projection improve understanding without exposing implementation detail?
  • Does the panel remain useful across mocks and live Ollama output?
  • Can the same view work during early, middle and terminal investigation states?

Evaluation

Completed. Visual and live-data review performed.

Result

Confirmed.

What did we learn?

  • The reasoning graph already contains all the information needed for a useful human-facing summary — no additional LLM calls are required.
  • Routing by semantic role (observation, question, explanation) rather than graph kind produces a more natural user experience.
  • Filtering scaffolding content (scenario summaries, system/tool references, metric object descriptions, process labels) is essential to keep the view focused on findings.
  • Deduplication of near-duplicate observations reduces noise without losing information.
  • Epistemic clarity matters — resolved unknowns become factual observations and should be classified as known rather than still-under-investigation.
  • The panel works across all investigation phases (early, active, terminal).

Decision

Close Experiment 12 as confirmed. Proceed to refine the translation through semantic classification in the next iteration.


Experiment 13 — Semantic Facilitator Translation

Hypothesis

Improving the deterministic projection from graph semantics to user-facing language — by classifying nodes by meaning rather than graph kind, suppressing scaffolding, merging duplicates, and preferring concrete observations — produces a significantly better facilitator view without changing the reasoning engine, prompts, graph generation, or any external contracts.

Questions

  • Does semantic role classification (observation vs question vs explanation) route content more naturally than graph-kind classification?
  • Does scaffolding suppression remove visual noise that previously dominated derived summaries?
  • Does deduplication reduce redundant items that express the same observation under slightly different wording?
  • Do concrete observations appear before abstract labels in ranked output?
  • Does the view remain robust when consumed by the existing panel component (investigation-summary-panel-v3) without any changes to that component?

Evaluation

Completed. Tests: 37 scenarios passing across filtering, classification, deduplication, ranking, section framing, mock-data integration, and edge cases.

Result

Confirmed.

What did we learn?

  • Semantic role routing outperforms kind-based routing: a node with kind: "state" that contains concrete data (e.g., "Revenue increased 12%") is more useful as an observation than a state description.
  • Scaffolding suppression works best when applied early — filtering at the semantic classification stage prevents structural glue from contaminating any section.
  • Three-tier filtering is effective: scaffolding patterns (highest priority), internal vocabulary (medium), then technical summary patterns (lowest).
  • Deduplication by normalised text removes meaningful noise. When "Revenue increased 12%" and "Current revenue is 12% higher" express the same observation, keeping one reduces confusion without losing information.
  • Resolved unknowns and assumptions are factual answers to previously unanswered questions — they should appear in the known section with an epistemic label ("Not yet established" / "To be tested") if their status hasn't been explicitly set.
  • The translation adapter is the right place for this work: it is a single deterministic function, testable in isolation, and its output contracts are stable.

Result

Confirmed.

What did we learn?

  • Semantic filtering significantly improved Version C.
  • The remaining limitations are architectural rather than visual.
  • Graph nodes still do not naturally map to facilitator language.
  • Users think in investigation progress rather than graph structure.
  • Version C proved the need for an intermediate narrative model.

Decision

Keep the semantic projection approach.

Do not continue improving graph projection indefinitely.

Proceed to designing an Investigation Narrative layer. Experiment 13 is closed.


Experiment 14 — Investigation Narrative Layer

Hypothesis

The graph should remain the internal reasoning model.

A separate narrative model should become the presentation model.

The facilitator UI should consume narrative state rather than graph nodes.

Questions

  • What information belongs in a narrative?
  • What belongs only in the graph?
  • Which narrative elements can be derived deterministically?
  • What should remain hidden?
  • Can every facilitator panel consume the same narrative object?

Status

Architectural experiment.

Evaluation

Pending.


Emerging Direction — Investigation Narrative

The Confidence Engine architecture is becoming:

User

Facilitated Conversation

Reasoning Graph

Investigation Narrative

Workspace Projection

User

The reasoning graph becomes the machine representation.

The investigation narrative becomes the human representation.

The UI simply renders whichever projection is appropriate.

This is an emerging architectural direction.

It is intentionally recorded before implementation so future experiments remain aligned.


Experiment 15 — Facilitator Behaviour Specification

Hypothesis

An expert consultant does not have a script. They have behaviours — recurring patterns of action deployed based on what they observe in the client's situation. The Confidence Engine should exhibit similar behavioural patterns rather than following a mechanical question-fill-graph cycle.

The current engine behaviour is:

Engine asks → User answers → Graph updates → Engine asks again

An expert facilitator behaviour is:

Engine assesses state → selects appropriate behaviour → acts (question, acknowledge, synthesise, challenge, pause)

Questions

  • How does an expert consultant behave during an investigation?
  • Which behaviours recur across investigations?
  • What triggers each behaviour?
  • When does the facilitator ask a question versus summarise versus expose uncertainty versus hold space?
  • What distinguishes guided thinking from mechanical Q&A?

Status

Investigation — behavioural model documented, not yet implemented.

Evaluation

This experiment is primarily architectural and behavioural. No code changes are required at this stage. The deliverable is a behavioural specification that future implementation experiments will reference.

Result

Confirmed as the correct next direction.

What did we learn?

  • Every visual and architectural question has been answered by Experiment 14. Further visual iteration yields diminishing returns.
  • The remaining gap is not visual — it is behavioural.
  • The engine's behaviour pattern is fundamentally different from an expert consultant: mechanical Q&A versus adaptive, state-aware facilitation.
  • The graph captures state but not behaviour. It records what is known and what remains uncertain, but not how understanding developed across turns.
  • Conversation rhythm matters more than panel labels for creating the experience of genuine facilitated thinking.
  • 14 distinct facilitator behaviours were identified: Orient, Acknowledge, Observe pattern, Clarify, Validate, Connect, Challenge assumption, Refine understanding, Expose uncertainty, Decide direction, Know when to pause, Avoid premature closure, Communicate confidence honestly, Progressively narrow focus.
  • Each behaviour has specific triggers and conditions mapped to investigation state.
  • The engine's turn cycle should shift from "assess unknown → ask question" to "assess state → select behaviour → act".

Decision

Commit the behavioural specification. Do not implement yet. Future experiments will integrate behavioural assessment into the reasoning cycle. This document defines what the facilitator does; future work determines how the system implements it.

Status: Closed. The behavioural model is established and documented. The gap it identified — that behaviours need a decision process operating on investigation state rather than graph structure — becomes the focus of Experiment 16.


Experiment 16 — Investigation State Assessment

Hypothesis

The facilitator should never inspect the graph directly when deciding what to do next.

Instead it should act upon an assessment of the investigation — its phase, progress, evidence quality, understanding trajectory, uncertainty trend, conversation health, and behaviour readiness.

This assessment is distinct from both:

  • The reasoning graph (which captures what is known)
  • The investigation narrative (which translates what is known into human language)

The assessment answers: Given where we are, what kind of help is most appropriate right now?

No reasoning changes.

No prompt changes.

No UI changes.

This is an architectural experiment.

Status

Architectural.

Evaluation

Confirmed.


What did we learn?

Document observations such as:

  • Investigation state is distinct from behaviour.
  • Behaviour should consume assessment rather than graph structure.
  • State assessment provides a stable contract between reasoning and facilitation.
  • The architecture is becoming layered rather than procedural.

Decision:

Proceed to documenting the investigation turn cycle.


Experiment 16 — Emerging Architecture Observation

The Confidence Engine architecture is becoming:

User

Facilitated Conversation (where behaviour lives)

Behaviour Selection (consumes assessment output)

Investigation State Assessment (describes investigation)

Investigation Narrative (human representation of state)

Reasoning Graph (machine representation)

LLM / Ollama / Reasoning Engine

User

This is not a final design. It is an observation emerging from 16 experiments.

What is becoming clear:

  • The reasoning graph is the machine representation.
  • The investigation narrative is the human representation.
  • The investigation state assessment is the decision representation — it translates state into readiness signals for behaviour selection.
  • Behaviour selection determines what kind of help to deploy.
  • Facilitated Conversation is where that help is delivered.

Each layer has a single responsibility. Each feeds the next. No layer inspects another's implementation details.

This architecture emerged from observation, not top-down design. It may still change as future experiments test it.


Experiment 17 — Investigation Turn Cycle

Hypothesis

A complete investigation can be described as a repeating turn cycle in which every architectural layer has a single responsibility.

Result

Experiment validated that the investigation turn cycle is an observation about how existing layers interact rather than a new architectural layer. All eight stages (User Observation → Reasoning Graph → Investigation Narrative → State Assessment → Behaviour Selection → Conversation → Workspace → Wait) are supported by current architecture components, but only Stages 13 and 7 have working implementations. Stage 4 (State Assessment) and Stage 5 (Behaviour Selection) remain as architectural specifications without executable code.

What did we learn?

  • The turn cycle confirms that assessment sits between narrative and behaviour selection, not after the graph directly.
  • Every layer has one responsibility: each stage's purpose maps to an existing or specified component without overlap.
  • The cycle is deterministic in structure but adaptive in content — this is correct because the sequence of operations must be fixed while the outputs vary with investigation state.
  • Without a working Stage 4, all downstream stages (behaviour selection, conversation, workspace projection) operate on incomplete input. Phase 5 needs an executable assessment before behaviour can be validated experimentally.

Decision

The turn cycle architecture is confirmed as correct but requires implementation of Stage 4 (State Assessment) to move from observation to validation. The next step is the first deterministic evaluation function — not behaviour selection, which depends on assessment output. This becomes Experiment 18: First Executable Slice.


Experiment 18 — First Executable Slice (Investigation State Assessment)

Hypothesis

A deterministic, conservative assessment of investigation phase and progress can be built from existing graph data without introducing new signals or modifying reasoning logic. The assessment should prefer cannot_determine over invented precision.

Scope

Phase detection (orienting / exploring / focusing / deepening / synthesising / concluding / cannot_determine), progress tracking (accelerating / steady / stalled / looping / spiralling / cannot_determine), and conversation health evaluation — using only data already present in the graph schema, orchestrator diagnostics, and facilitator-view outputs.

Constrained By

  • Must use actual repo contracts (not assumptions about field names or structures).
  • Must be pure function — no network, LLM, mutation, or side effects.
  • Must handle missing fields gracefully — safe with absent data.
  • Must produce versioned assessment objects for future compatibility.
  • Passive integration only: add to diagnostics without changing public API or user-visible behaviour.

Questions

  1. Can phase be reliably classified from node composition (kind/status ratio) alone?
  2. Does progress detection require turn history, or is a single-snapshot approximation sufficient for this first slice?
  3. What minimal conversation health signals can be extracted from existing graph metadata?

Evaluation

  • Deterministic output across identical inputs.
  • Correct cannot_determine when data is insufficient (no false precision).
  • Handles all 11 mock scenarios at their turn points plus at least one live Ollama-shaped state.
  • Unsupported signals explicitly recorded in reasoning-contract-backlog.md.

Status

Closed. The assessment is implemented, tested, and validated. See investigation-state-assessment-contract.md and lib/assessment/investigation-state-assessor.js.

Enabled for Behaviour Selection

Experiment 18 proved three things that make Experiment 19 possible:

  1. Phase detection works. We can classify investigation phase (orienting / exploring / focusing / deepening / synthesising / concluding) from existing graph data with measurable confidence. This is the primary input for behaviour selection — without it, selection rules have no state to operate on.

  2. Progress tracking works. Stalled progress in a focusing phase becomes a concrete signal that the facilitator should hold space rather than push. Previously this was an architectural idea; now it's observable data.

  3. Conversation health is measurable. Healthy, too_broad, and user_overloaded states are detectable from question distribution and response patterns. too_broad triggers Clarify; healthy with resolution triggers Acknowledge — but only if the assessment layer exists to provide these signals.

Without Experiment 18, Behaviour Selection would have two options: inspect the graph directly (coupling behaviour to implementation) or use narrative fields as proxy signals (fragile by design). The assessment layer provides a stable contract — the three reliable dimensions listed above — that behaviour selection can depend on without fear of breaking when the graph schema changes.

Experiment 18 also proved that cannot_determine is not a failure mode but the correct answer when evidence is insufficient. This principle carries directly into behaviour selection: "no explicit rule matched" defaults to continue, not an invented signal.


Experiment 19 — Passive Behaviour Selection

Hypothesis

Does selecting from a small set of five behaviours (Acknowledge, Clarify, Summarise, Continue, Pause) — instead of always asking — make the investigation feel more like guided thinking and less like automated Q&A?

This is one question. Nothing else matters until this is answered.

Scope

A deterministic selector that maps investigation state assessment output to exactly one of five behaviours per turn:

  1. Acknowledge — when conversation health is healthy AND phase confidence is not low
  2. Clarify — when health is too_broad OR (phase is orienting AND observations < 3)
  3. Summarise — when phase is synthesising/concluding OR (≥ 3 resolved with steady progress)
  4. Pause — when phase is focusing AND progress is stalled; also user_overloaded health
  5. Continue — default when no rule matches

Selection uses priority ordering: Acknowledge > Clarify > Summarise > Pause > Continue. No scoring, no weighting, no convergence thresholds. First matching rule wins.

The selector is passive — deployed only through Developer Details diagnostics. No changes to reasoning engine, prompts, graph generation, decomposition, narrative generation, API contracts, UI behaviour, or Ollama integration.

Evaluation Criteria

  1. Behaviour diversity: Does the system deploy at least 3 different behaviours across a normal investigation, or does it default to Continue most of the time?
  2. Acknowledge appears: Does Acknowledge fire whenever new information resolves an uncertainty? If not, the trigger condition is wrong — fix it, don't abandon selection.
  3. Pause feels like relief, not delay: When Pause fires, does the user experience it as a natural break rather than a system failure to produce a question?
  4. Summarise compresses meaningfully: Does the summarised understanding feel useful or redundant?
  5. Conversation rhythm changes: Is there a perceptible difference between "engine always asking" and "engine sometimes acknowledging/summarising/pausing first"?

If none of these can be evaluated after 23 real investigations with v0.1, the experiment was too small to answer the question.

Open Questions

  • Which of the five behaviours fires most frequently in practice?
  • Does Acknowledge actually appear during investigations that would normally produce continuous questioning?
  • Does the priority ordering create appropriate urgency (Acknowledge > Clarify > Summarise > Pause > Continue)?
  • Are there cases where cannot_determine produces inappropriate behaviour selection — or is this the correct conservative default?

Experiment 20 — Passive Question Importance Classification

Hypothesis

Does a passive classifier that tags unresolved unknowns as important, helpful, incidental, or cannot_determine (using only existing graph fields, no scoring, no weights) produce coherent importance patterns across normal investigations?

This is one question. Nothing else matters until this is answered.

Scope

A pure function assessQuestionImportance({ node, graph }) implementing three deterministic rules:

  1. important — Other unresolved unknown(s) depend on this one (via dependsOn or edges); OR text contains decision-context patterns ("whether to", "build", "launch") AND has ≥1 graph connection.
  2. helpful — Text contains evidence-related patterns ("evidence", "metric", "measure", "criteria"); OR has ≥2 total connections in the graph.
  3. incidental — Default when neither important nor helpful conditions are met.
  4. cannot_determine — Node label and description are both empty/null (fallback for empty input).

The classifier is passive — validated only against mock scenario fixtures. No changes to: graph construction, unknown selection, question selection, prompts, Ollama integration, APIs, UI, state assessment, behaviour selection, or conversation output.

Validation

Run the classifier passively against existing mock scenarios (comparison, contradictory, missing-evidence, decision, long investigation, complete) and verify at least three classifications align with intuitive expectations:

  • The "decision" scenario's build/commercial unknown → important
  • An evidence-gathering unknown from the comparison scenario → helpful
  • A minor formatting or cosmetic unknown → incidental

Open Questions

  • Which importance category appears most frequently across normal investigations?
  • Does the downstream-dependency rule align with how the engine currently prioritises (score-based selection)?
  • Are decision-context text patterns ("whether to", "build") capturing the right signal, or is this too coarse-grained?
  • Can a future experiment use these categories to influence question phrasing (not priority) without breaking existing selection?

Long-Investigation Evaluation — Full Sequence Results

Test file: tests/graph/question-importance.long-investigation.test.js
Fixture: longTurns from lib/mocks/scenarios.js (5 turns, sequential mock mode)
Method: Ran assessQuestionImportance against every unresolved unknown at each turn. No rule changes before evaluation.

Category distribution

Total important helpful incidental cannot_determine
4 0 0 4 0

The classifier collapsed to a single category: incidental.

Per-turn detail

Turn Unknown ID Label (short) Classification
0 u-1 Whether there is genuine demand for our category in Europe incidental
1 u-2 Whether our product is suitable for European compliance requirements incidental
2 u-3 Whether the cost of achieving compliance is justified by the market size incidental
3 u-4 Whether we have competitive differentiation against existing European players incidental

Turn 4 had zero unresolved unknowns (all resolved).

Analysis of collapse to incidental

All four unresolved unknowns in the long-investigation sequence were classified as incidental. Three independent factors caused this:

  1. No downstream dependencies. No unresolved unknown has another unresolved unknown depending on it via dependsOn or edges — each question is a leaf in its turn's dependency graph. The downstream-dependency rule (Rule 1, first clause) never triggers.

  2. Decision-text patterns missed. The DECISION_PATTERNS regex requires "whether to" (the word "to" must follow "whether"). None of the four unknown labels contain "whether to" — they all use the structure "Whether [subject] [verb]" rather than "Whether to [verb]". Similarly, none contain "build", "launch", "proceed", or "continue.*develop". Rule 1's text-match clause (second disjunct) requires both a pattern match AND ≥1 graph connection — the pattern fails first.

  3. No direct graph edges. The long-investigation fixture's edges connect observations to state nodes and resolved unknowns, but the active unknown in each turn has zero incident edges (collectConnectedIds returns an empty set). Without connections, the threshold-based rules (≥1 for important, ≥2 for helpful) never trigger regardless of text content.

Evidence that appears correct

  • Turn 0, u-1: "Whether there is genuine demand for our category in Europe" → incidental. This is questionable. The question frames the entire strategic decision ("should we enter Europe?"), yet no pattern matches because the edge from obs-2 to u-1 (market size evidence) only appears starting at turn 1 — at turn 0, u-1 genuinely has zero connections and no text match.

Evidence that appears questionable

  • Turn 3, u-4: "Whether we have competitive differentiation against existing European players" → incidental. This is arguably a central question in the investigation, yet it is classified as incidental because it has zero graph edges and no decision-context keyword ("whether" alone does not match). The graph structure (edge from obs-5 to u-4) only connects observations to unknowns — but those connections exist on the source side, not the target.

  • Turn 2, u-3: "Whether the cost of achieving compliance is justified by the market size" → incidental. The word "cost" does not match EVIDENCE_PATTERNS and the node has zero direct edges. A human evaluator would classify this as important (it is the last financial feasibility gate before a go/no-go decision).

Do questions change category across turns?

No. All four resolved to incidental. There is no meaningful variation. This is not because the unknowns are identical — they address distinctly different strategic dimensions (market existence, compliance, cost, differentiation) — but because the classifier's two rule families (dependency detection and keyword matching) do not fire for any of them.

Does the result appear useful enough to keep passive?

No. A classifier that tags every unresolved unknown in a realistic long investigation as incidental provides no discrimination signal. It is technically correct under its own rules, but those rules are too narrow for the investigation structure as it currently exists. The collapse reveals a structural gap: active unknowns in this scenario have zero direct edges, and their labels use "Whether [clause]" phrasing rather than "Whether to [verb]" or other decision keywords.

Further evidence is still required if the classifier is to be considered viable. Options include:

  • Expanding DECISION_PATTERNS to capture broader question structures (not just "whether to" + keyword combos).
  • Adjusting how graph connections are counted for target nodes vs source nodes in edges.
  • Testing against scenarios where unknowns have direct observation→unknown edges.

Evaluation status

Incomplete. The classifier did not produce useful variation across the long-investigation sequence. It passed determinism and immutability checks, but failed to discriminate between questions that clearly have different strategic importance. The hypothesis is not yet supported by this evaluation. Further evidence or rule refinement (not on this branch) is required before the classifier can be considered viable as a passive tool.


Experiment 20 — Conclusion

The hypothesis was not confirmed by this evaluation.

What happened:

  • The passive classifier collapsed to a single category (incidental) across the long-investigation scenario.
  • Three independent factors caused the collapse: no downstream dependencies, missed decision-text patterns (regex required "whether to" but questions used "Whether [clause]"), and zero graph edges on active unknowns.
  • The keyword-only approach produced technically correct but practically useless classifications.

What this means:

Question importance cannot be judged in isolation from the decision being investigated. A question like "Do we have competitive differentiation?" is only important when compared against a clear decision target. Without that target, keyword matching and local graph structure are insufficient signals.

Decision:

The Experiment 20 classifier has not been accepted into the active engine. Its rules remain unchanged (do not expand them). The next step is Experiment 21: testing whether providing an explicit decision target allows a simple deterministic classifier to produce useful distinctions.


Phase Transition

Record that the project has moved from:

Interface Design → Facilitated Investigation → Behavioural Architecture → System Architecture

Future work should validate these layers rather than introduce new ones.


Emerging Direction — Graph as Source of Truth

The first UX experiments focused on workspace structure.

The next series will focus on investigation rhythm and behaviour.

Future experiments should explore:

  • how conversations unfold (behavioural, not visual)
  • how understanding evolves across turns
  • how the facilitator selects its behavioural response
  • how confidence is gradually built through action, not description
  • what state assessment enables better question selection

The objective is no longer to arrange cards or translate panels.

The objective is to make each turn of the investigation feel like a natural step in a guided thinking process.

The objective is to make the investigation feel like a natural facilitated conversation.


Experiment 21 — Question Relevance Against Decision Target

Hypothesis

Does giving the classifier an explicit decision target allow it to distinguish questions that could change the decision from questions that are merely useful or incidental?

This is one question. Nothing else matters until this is answered.

Scope

A pure function assessQuestionRelevanceToDecision({ decisionTarget, unknown, graph }) implementing four deterministic rules:

  1. could_change_decision — The question directly mirrors the decision's core action (e.g., "whether to enter", "should we launch", "whether there is [demand/market/need]") AND the decision target contains a matching action keyword. Answering could reasonably reverse the proposed action.
  2. supports_decision — Necessary precondition (e.g., compliance, cost feasibility) OR supporting context (e.g., differentiation, competitive position). The answer would improve confidence or evidence but is less likely to reverse the decision alone.
  3. unlikely_to_change_decision — Background detail or comparative reference that does not affect the decision conditions.
  4. cannot_determine — Decision target or unknown is missing, empty, or too unclear to compare honestly.

The classifier is passive — validated only against mock scenario fixtures. No changes to: graph construction, question importance classifier, unknown selection, question selection, prompts, Ollama integration, APIs, UI, state assessment, behaviour selection, conversation output, or engine behaviour in any way.

Decision Target

For the long-investigation scenario, use an explicit target from the fixture:

Should we enter the European market with our SaaS analytics platform?

Do not attempt to discover the decision target automatically. For this experiment, the decision target is supplied by the test fixture.

Evaluation

Run the classifier passively across the same long-investigation turns used in Experiment 20 (turns 03). Record per-turn classification. Compare with Experiment 20 results. Expect at least two distinct categories — not a collapse to one.

Questions

  • Does providing an explicit decision target enable more useful distinctions than keyword-only matching?
  • Do the four categories map intuitively to how a human evaluator would judge relevance?
  • Or does the deterministic rule set still miss cases that appear obviously important?

Experiment 22 — Question Relevance Against Explicit Decision Conditions

Explicit decision conditions were supplied:

  1. Credible customer demand exists in Europe
  2. European compliance is achievable
  3. The expected market value justifies the cost of entry
  4. The product offers sufficient competitive differentiation

Each long-investigation unknown matched a different deciding condition. All four correctly classified as tests_deciding_condition.

Category variety is not automatically a measure of quality — here, uniformity (all four as decisive) is correct because each question directly tests a required condition.

The classifier remains passive and is not in the active reasoning path.


Experiment 23 — Decision Condition Status Assessment

Status: Concluded (passive layer)

Hypothesis

Given resolved graph evidence, we can determine which explicit decision conditions are established, contradicted, unresolved, or cannot_determine using only existing node fields and simple keyword matching — no scoring, no weights, no LLM calls.

Scope

  • Pure passive classifier: reads resolvedNodeIds, nodes[].label, nodes[].description, nodes[].status
  • Four-state classification with contradiction-precedence-over-support rule
  • Uses the same concept groups that power Experiment 22's question relevance (demand, compliance, value_cost, differentiation)
  • Returns evidence node IDs alongside status for traceability

Implementation

File: lib/graph/decision-condition-status.js

Classification rules (evaluated in order):

  1. cannot_determine — missing condition text or incomplete graph
  2. contradicted — resolved evidence contains a contradiction phrase (e.g. "does not support", "not achievable")
  3. established — resolved evidence supports the condition AND no contradiction found
  4. unresolved — condition is relevant but no resolved evidence establishes or contradicts it

Contradiction detection uses universal phrases applied to ALL resolved node texts, regardless of condition category. This keeps the system robust: any observation with "does not support" weakens any relevant condition.

Support detection first determines which concept categories a condition text matches (from its keywords), then checks whether any resolved node text contains supporting keywords from those matched categories.

Evaluation method

  • 39 focused tests: established (5), contradicted (4), unresolved (4), cannot_determine (6), precedence (3), immutability (2), long-investigation sequence (15)
  • Long-investigation sequence tested across turns 04 of the "long" scenario fixture

Observed status transitions (long investigation)

Turn Resolved nodes Demand Compliance Value/cost Differentiation
0 unresolved unresolved unresolved unresolved
1 u-1 established unresolved unresolved unresolved
2 u-1, u-2 established established unresolved unresolved
3 u-1, u-2, u-3 established established established unresolved
4 u-1, u-2, u-3, u-4 established established established established

Note: Observation nodes (obs-*) are NEVER in resolvedNodeIds — they remain "known" observations. Only unknowns become resolved during investigation turns. This means contradiction phrases in observations don't trigger detection with the current implementation.

Limitations

  • Contradiction detection only works on resolved node labels/descriptions, not on observation notes (which is a deliberate design choice to avoid false positives from unverified data)
  • Absent conditions are unresolved, never contradicted — absence of evidence ≠ evidence of absence
  • No handling for partially established conditions (e.g. some sub-conditions met, others not)
  • Keyword matching is case-insensitive substring only; no stemming or semantic understanding

Conclusion

The assessment works correctly across all test cases: 39/39 passing. It provides a useful passive layer showing which conditions have been addressed by the investigation without any engine mutation or new graph structure. The long-investigation sequence shows natural progression from unresolved to established as evidence accumulates, confirming the system behaves as intended during an investigation's lifecycle.


Experiment 24A — Evidence Direction Classification

Status: Completed (passive layer)

Hypothesis

Answer evidence can be distinguished from resolved-question wording and classified by whether it supports, contradicts or merely informs a decision condition.

What was implemented

A passive deterministic evidence-direction classifier (lib/graph/evidence-direction.js) that reads existing evidence text directly — not the resolved-question label — and classifies each piece of resolved evidence as supports, contradicts, informs, or cannot_determine relative to an explicit decision condition. Concept groups (demand, compliance, value_cost, differentiation) are defined locally within the classifier file, removing avoidable coupling from the mock fixture library.

Observed results

  • market evidence ("European analytics SaaS market valued at approximately €8B and growing 15% annually") → supports demand condition
  • missing EU data residency ("Our platform does not currently support EU data residency requirements") → contradicts compliance condition
  • cost evidence ("Achieving compliance would require approximately 6 months and $500K engineering investment") → informs value-versus-cost condition
  • unique capability evidence ("Our real-time collaboration feature has no direct European equivalent") → supports differentiation condition

What was learned

  • Resolving a question is not the same as establishing its condition.
  • Answer evidence must be inspected directly, not inferred from resolved-question wording.
  • Relevant evidence may inform without proving.
  • Contradiction must remain attached to the condition it concerns.

Focused test results

22 focused tests pass (supports × 2, contradicts × 1, informs × 2, cannot_determine × 7, determinism × 2, immutability × 2, long-investigation examples × 4, unrelated evidence × 2).

Cleanup performed

  • Moved EVIDENCE_DIRECTION_GROUPS from lib/mocks/scenarios.js into lib/graph/evidence-direction.js.
  • Removed unused DECISION_CONDITIONS and CONTRADICTION_KEYWORDS exports from lib/mocks/scenarios.js.
  • Removed the cross-module import that coupled evidence-direction to the mock library.

Experiment 23 compatibility

decision-condition-status.test.js (39 tests) and question-decision-conditions.test.js (40 tests) both continue to pass. No behaviour change in Experiment 23 or 22 classifiers.

Next steps

Do not yet integrate evidence direction into active reasoning. That belongs to a separate follow-on experiment. Do not amend Experiment 23 condition statuses here.


Experiment 24B — Derive Condition Status from Answer Evidence

Status: Completed (passive layer)

Hypothesis

Decision condition status should be derived from linked answer evidence (supports/contradicts/informs), not from the resolved-question label. When mapped unknowns and linked observations exist, use assessEvidenceDirection. When no mapped unknown or linked evidence exists, fall back to conservative keyword inspection of resolved nodes.

What was implemented

Two assessment paths in lib/graph/decision-condition-status.js:

Path 1 — Linked evidence path: when a resolved unknown and linked observation/evidence nodes exist via edges, invoke assessEvidenceDirection for each linked observation; derive status from the classified direction (supports → established, contradicts → contradicted, informs → unresolved). Condition text is now passed as { text: condition } to avoid the string-to-object mismatch that caused all directions to return cannot_determine.

Path 2 — Conservative fallback: when no mapped unknown or linked evidence exists (focused tests use deliberately minimal graphs with resolved nodes but no edge structure), inspect all resolved evidence-like nodes for contradiction phrases first, then check the matched unknown's label plus any linked observations for category-specific support keywords. Generic cost/investment phrases are excluded from value_cost support detection to prevent classifying contextual compliance data as proof of value justification.

Corrected long-investigation statuses

Condition Status Rationale
Demand → established Linked evidence (€8B market, 15% growing) supports the demand condition
Compliance → contradicted Linked evidence ("does not support EU data residency") contains compliance negation phrase
Value versus cost → unresolved Cost evidence ("6 months, $500K engineering investment") is contextual; does not prove value justifies cost
Differentiation → established Linked evidence ("no direct European equivalent") supports differentiation

Focused test changes

  • Generic cost/investment evidence ($500K investment) now correctly returns unresolved for value_cost (was erroneously established) — updated two focused tests and their descriptions.
  • Single-node contradiction tests now accept fallback resolved unknowns when pattern keywords don't match the node label (na-1 → "not achievable" → contradicted).
  • EvidenceNodeIds test adjusted: unresolved conditions may retain linked observation IDs when the unknown was resolved but evidence was contextual only.

What was learned

  • Linked answer evidence controls condition status; resolved-question labels are not proof.
  • Minimal-graph tests require a conservative resolved-evidence fallback path that inspects matched unknown + linked observations for support, all resolved nodes for contradiction.
  • Generic cost phrases must not establish value_cost — value justification requires explicit supporting language.
  • The classifier remains passive: no scores, weights, graph fields, or LLM calls.

Focused test results

36 focused tests pass (established × 5, contradicted × 2, unresolved × 3, long-investigation sequence × 19, edge-case + determinism × 7). 22 evidence-direction tests pass. 40 question-decision-conditions tests pass.

Experiment 24A unchanged

Evidence-direction classifier (evidence-direction.js) is untouched. All 22 tests pass. The fix was only in decision-condition-status.js and test expectations.

Active engine behaviour unchanged

No changes to the active reasoning loop, prompt generation, or question-selection logic. This layer reads graph state only.


Experiment 25A — Evidence-Condition Scope Comparison

Status: Completed (passive layer)

Hypothesis

Before evidence can support or contradict a condition, the engine must establish that both refer to the same:

  • subject;
  • timeframe;
  • type of claim.

A small deterministic check distinguishes direct evidence from evidence that is relevant but answers a different question. Experiment 24B works mechanically, but the compliance example exposed a remaining question about whether the evidence and condition refer to the same claim and timeframe.

The Present-State Versus Future-Feasibility Distinction

The engine has observed this ambiguity repeatedly:

Condition: European compliance is achievable Evidence: Our platform does not currently support EU data residency requirements

The evidence proves the platform is not compliant now. It does not prove that compliance cannot be achieved. Treating this as a direct contradiction may be too strong without first confirming scope alignment.

Implementation Scope

A pure function assessEvidenceConditionScope({ condition, evidenceNode }) implementing four deterministic rules using small explicit language patterns:

  1. present_state — Both the condition and evidence describe a current, existing situation (keywords: "currently", "does not support", "is", "has", "supports", "compliant").
  2. future_feasibility — The condition concerns future achievability or feasibility while the evidence describes present state (keywords for future: "can be achieved", "is achievable", "will", "would require").
  3. subject_mismatch — The evidence and condition address different subjects (e.g., compliance vs market demand). Detected via shared category from evidence-direction concept groups.
  4. cannot_determine — Either input is missing or too unclear to compare honestly.

No LLM calls, no scoring, no weights, no graph schema changes, no mutation.

Evaluated Examples

Condition Evidence Expected Scope
The platform currently supports EU data residency requirements Our platform does not currently support EU data residency requirements direct_match
European compliance can be achieved within an acceptable time and cost Our platform does not currently support EU data residency requirements different_timeframe
European compliance can be achieved within an acceptable time and cost Achieving compliance would require approximately six months and $500K partial_match
Credible customer demand exists in Europe The European analytics SaaS market is valued at approximately €8B and growing 15% annually direct_match

Findings

  • Present-state conditions versus present-state evidence produce clean direct_match signals.
  • Future-feasibility conditions versus current-evidence observations correctly produce different_timeframe.
  • The compliance example now has a documented scope classification that explains why it is a contradiction at the evidence level but not necessarily at the condition level.
  • Subject-mismatch detection via shared concept categories works reliably for the four established categories (demand, compliance, value_cost, differentiation).

Phrase list additions

The future-feasibility phrase list was extended from "can be achieved" to also include "can achieve", "be achieved", and "is achievable". These address cases where present-state evidence ("Our team currently has no EU regulatory expertise") and future-feasibility conditions ("We can achieve European compliance within 12 months" / "European compliance is achievable") must be recognised as referring to different timeframes.

Limitations

  • Present-state evidence and future-feasibility conditions can refer to different timeframes; scope detection must check both inputs independently.
  • Timeframe detection relies on explicit keyword patterns. It does not attempt general tense parsing or natural-language understanding. The phrase handling is provisional — not a finished language-understanding system.
  • Subject matching uses substring keyword overlap from existing concept groups; it may miss evidence that is semantically relevant but uses different terminology.
  • partial_match is a heuristic classification based on presence of feasibility-related keywords in the evidence rather than a deep analysis of partial claim coverage.
  • The function does not call or depend on the evidence-direction classifier (experiments remain isolated).

Experiment 25B — Scope-Aware Condition Status With Actual Fixture Wording

Status: Completed (passive layer)

This experiment tested whether the scope check can recognise intended meaning without rewriting the condition or evidence into preferred test phrases, using the actual long-investigation fixture wording from scenarios.js.

Two real fixture cases were initially unresolved:

  1. Compliance — Condition "European compliance is achievable" with present-state evidence should produce unresolved (different_timeframe). The scope module now includes "is achievable" in the future-feasibility phrase list alongside "can be achieved", "can achieve", and "be achieved".

  2. Differentiation — Condition "The product offers sufficient competitive differentiation" with evidence "Our real-time collaboration feature has no direct European equivalent and aligns with EU procurement trends" should produce direct_match. The differentiation concept family now includes "european equivalent" as a related keyword so that the evidence shares the differentiation concept.

Confirmed long-investigation statuses

Condition Expected Status
Demand (Credible customer demand exists in Europe) established
Compliance (European compliance is achievable) unresolved
Value versus cost (The expected market value justifies the cost of entry) unresolved
Differentiation (The product offers sufficient competitive differentiation) established

Phrase matching remains provisional and replaceable

The fixes rely on explicit substring patterns:

  • "is achievable" added to FUTURE_FEASIBILITY_PHRASES
  • "european equivalent" added to CONCEPT_FAMILIES.differentiation.related

These are narrow, targeted additions. They do not create a broad synonym library or general language parser. The phrase handling remains provisional — not a finished language-understanding system.

Current-state evidence does not settle future feasibility

Current-state evidence ("Our platform does not currently support EU data residency requirements") correctly leaves the condition "European compliance is achievable" unresolved because the scope check detects different_timeframe: present-state evidence vs future-feasibility condition. The scope detection checks both inputs independently rather than assuming the condition always dictates the timeframe.

Differentiation evidence can directly support the differentiation condition

Adding "european equivalent" to the differentiation related keywords allows evidence phrases like "no direct European equivalent" to share the differentiation concept with conditions containing "competitive differentiation". This is a narrow phrase match, not a broad semantic equivalence claim.

Passive Status

This experiment remains passive and isolated. It does not modify decision-condition-status.js core rules, evidence-direction.js, graph schema, prompts, APIs, UI, or any active engine behaviour. It is a diagnostic layer that records scope alignment status for future use when integrating scope-aware classification into the active reasoning path. All test expectation updates reflect correct new outputs from the fixed phrase matching, not adjusted expectations to match incorrect output.


Experiment 25B — Closed Before Knowledge Management Work

Return-to-Work Note

We finished testing whether evidence about the present should directly settle a future-looking condition.

The engine now recognises that:

  • current lack of compliance does not prove future compliance is impossible;
  • cost evidence may inform a decision without proving the investment is justified;
  • differentiation evidence can support the relevant condition.

The current language matching is provisional and based on narrow phrases. Do not continue adding synonyms as the long-term solution.

Engine experiments are now paused while project knowledge and context-loading are rationalised.

Branch: feature/user-workspace-ux-v0.7 Commit: 273f715

Experiment 26 — Inventory Project Knowledge and Context Needs

Status: Pending review

Hypothesis

The existing documentation can be separated into clear roles: current working context, task-specific references, historical evidence, and gaps to review. A simple inventory and loading map may reduce context without losing important knowledge.

Inventory Method

  • Inspected filenames, line counts, headings, and section structure of all 34 docs/ files and 4 .claude/ markdown files (38 documentation files total).
  • Did not print full contents of large documents (>100 lines).
  • Inspected headings via grep, file sizes via wc -l, and key sections (Experiments 2325B, Return-to-Work notes) via targeted sed.
  • Created one inventory document: docs/project-knowledge-inventory.md.

Proposed Minimum Context

For routine Confidence Engine work, Claude should normally load only:

  1. .claude/project-context.md — entire file (product direction, current stage)
  2. .claude/architecture-guardrails.md — entire file (hard boundaries, invariants)
  3. docs/design-evolution-log.md — lines 190, 824838, 889910, 12181520 (phase overview + Experiments 1625B history)
  4. docs/03_Confidence_Engine_Language_Guide.md — entire file (language rules)

Minimum-Context Test Result

Five questions answered accurately from the minimum context set:

Question Answer
What is the Confidence Engine trying to help a user do? Help people take justified next steps when a problem feels too big to know where to start — by breaking complexity into small pieces, building a reasoning graph, asking one question at a time, and updating until confidence is sufficient or remaining uncertainty is clear.
What is the current engine experiment status? Paused. Experiments concluded with Exp 25B (scope-aware condition status). Current focus: UX presentation improvements (v0.7 user workspace).
What did Experiment 25B establish? Scope-aware evidence-condition comparison: present-state evidence does not settle future-feasibility conditions. All 39+ tests pass across Exps 2325B.
What remains provisional? Phrase-based scope detection (Exp 25A/B); passive classifiers not yet integrated into active reasoning; next-question selection pipeline needs re-evaluation.
What work is intentionally paused? All engine experiments beyond Exp 25B. No reasoning architecture changes. Current work: UX usability, presentation clarity, loading feedback.

Missing Context Discovered

None. The five questions were answered accurately from the minimum context set. No additional document was required.

Duplications and Gaps Found

  • Duplicate principles: "The engine owns the complexity / user sees only the next step" appears in founding-principles, project-context, ux-guidelines, and architecture-guardrails. Consider consolidating or cross-referencing.
  • Buried current state: Experiment 25B sits at line ~1,483 of a 1,542-line log. A developer must scroll past 14+ phases to find active status.
  • No short entrypoint for active engine state: project-context.md covers product direction but not experiment details (Exps 2325B).
  • Potentially stale architecture description: v0.6-reasoning-architecture.md does not reference later additions from Experiments 1525B.

Status

Pending review. Nothing has been archived, moved, or deleted. The proposed context-loading plan is documented in docs/project-knowledge-inventory.md.


Experiment 27 — Create a Short Current-State Entry Point

Status: Pending Rob's review

Hypothesis

A concise current-state document can replace the large experiment-log section as the normal starting point for future work. The full design history should remain available as evidence, but should not be compulsory reading.

Documents Used

Document Sections
docs/project-knowledge-inventory.md Current Working Context; Gaps and Duplications to Review; Minimum Context Test Result
.claude/project-context.md Entire file (~102 lines)
.claude/architecture-guardrails.md Entire file (~77 lines)
docs/design-evolution-log.md Experiment 26 only; Return-to-Work Note after Experiment 25B (lines 14831501)
docs/03_Confidence_Engine_Language_Guide.md Guiding principles and preferred language only

Document length: approximately 500 lines total across all sources.

Created File

docs/current-project-state.md — 252 lines. Organised by what is true now, not chronologically. Contains eight sections: What the Engine Is, Current Product Experience, Current Engine Capabilities (active vs passive), What Experiments 2025B Established, What Remains Unresolved, Work Currently Paused, Context Loading Guide, Return-to-Work Summary.

Practical Minimum-Context Test

After creating the document I stopped reading all source documents and used only:

  • docs/current-project-state.md
  • .claude/architecture-guardrails.md

To produce this briefing for a returning developer:

  1. Active: Deterministic reasoning pipeline, unknown selection (atomicity/answerability), question formulation within reasoning patterns, scenario API, turn cycle orchestration. Nothing more from the engine itself.
  2. Passive: Investigation-state assessment, behaviour selection, decision condition status, question-to-condition relevance, evidence direction, evidence scope, scope-aware condition status — all isolated diagnostic layers with no active integration.
  3. Paused: Engine experiments (after 25B), UI experiments. Knowledge-management is active. Nothing archived or deleted.
  4. Provisional: Keyword/phrase matching for scope detection; passive classifier generalisability across domains; how passive reasoning enters the active cycle; whether architecture docs match implementation.
  5. Next: docs/current-project-state.md is the starting point. Use the inventory for task-specific context. Guardrails before code changes.

Result: The briefing was accurate and complete from these two files. No essential information was missing. The routing table in section 7 of the current-state document provided all necessary references without requiring additional documents.

Missing or Ambiguous Information Found

  • docs/investigation-state-assessment-contract.md (232 lines) describes a data contract that may no longer match implementation after experiments 1525B; not verified.
  • The exact line count of the created document should be confirmed with wc -l.
  • Whether any of the passive classifiers have been partially integrated since Exp 25B was closed requires checking source code — this task did not read it.

Assessment

The new entry point successfully replaced the need to load the large experiment-log section (1,542 lines). The current-state document conveys active vs passive capabilities, pause status, unresolved questions and loading instructions in a single short file. It can replace the large default log section as the normal starting point for future work.

The practical briefing was produced accurately from only two files without reading any source material beyond what was used to create it. This confirms the hypothesis that a concise current-state document is sufficient context for understanding where the project stands.

Return-to-Work Note

A short current-state entry point now exists at docs/current-project-state.md. Future Claude sessions should begin there. The full experiment history remains available in docs/design-evolution-log.md but is no longer default reading. Nothing has been archived, moved or deleted yet. Before changing the documentation structure, review whether the new entry point reliably replaces the large log section and whether any historical documents should be formally archived. First file to inspect when resuming: docs/current-project-state.md. Branch: feature/user-workspace-ux-v0.7.

Status

Pending Rob's review.

The following are active explorations rather than decisions.

  • What is the right metaphor for the product?
  • Should the workspace resemble a facilitated workshop?
  • How should decomposition be represented?
  • What information belongs in shared understanding?
  • What should the Investigation Map eventually become?
  • How should wide thinking be reflected in the interface?

Backlog — Experiment 05 Persistence Note

The "Don't show this introduction again" checkbox uses sessionStorage as a placeholder.

This preference should eventually be handled through user preferences or settings rather than local component state.

TODO: When user accounts are introduced, persist this preference to the user profile so it travels across devices and sessions.

Future Note — Dark Mode

Dark mode is intentionally deferred.

Once the information architecture and visual hierarchy stabilise we will investigate whether an "Investigation Mode" (rather than a conventional dark mode) improves concentration.

This should be treated as a future UX experiment rather than an accessibility feature.

Experiment 28 — Verify Current Project State Against Implementation

Status: Pending Rob's review

Hypothesis

A focused code inspection can verify or correct the current-state document without requiring a fresh session to read the full experiment log. If the document is accurate, it can safely become the normal project entry point.

Source Areas Inspected

  • docs/current-project-state.md — entire file;
  • .claude/architecture-guardrails.md — entire file;
  • docs/project-knowledge-inventory.md — Current Working Context and Task-Specific References sections;
  • app/api/*/route.js — all API entry points (analyse, cases/start, cases/update, health);
  • lib/graph/orchestrator.js — imports (lines 632) and runtime calls at lines 376, 402, 552, 581, 622, 826, 904, 1013;
  • lib/graph/*.js — grep for imports of passive classifier modules (decision-condition-status, evidence-direction, evidence-condition-scope, question-decision-relevance, question-importance);
  • lib/behaviour-selection/behaviour-selector.js — cross-module import check;
  • lib/assessment/investigation-state-assessor.js — caller trace in orchestrator.

Active / Passive Findings

Active capabilities confirmed:

  1. Scenario reconstruction (analyseScenario) — API entry at app/api/analyse/route.js → lib/analysis.js.
  2. Reasoning graph updates (startCase / updateCase) — API entries at app/api/cases/{start,update}/route.js → orchestrator.js → apply-proposal.js. Propagation, confidence cap, completeness calculated in apply-proposal.
  3. Unknown selection (atomicity + answerability) — selectActiveUnknownCandidate imported and called from orchestrator's determineGraphBackedQuestion within the active updateCase path.
  4. Question formulation — formulateQuestion / formulateTieResolutionQuestion imported and called from the active turn cycle.
  5. Turn orchestration — orchestrator.js updateCaseWithDependencies() is the active engine heart, coordinating unknown→question→answer→graph-update→propagation→next-unknown.

Passive or isolated capabilities confirmed:

  1. Investigation-state assessment (assessInvestigationState) — called at 3 sites in orchestrator but result only placed into a diagnostics field; not used for any control-flow decision. Classification: diagnostic_only.
  2. Behaviour selection (selectBehaviour) — exported from behaviour-selector.js; no callers anywhere in the repo. Classification: isolated.
  3. Question importance, question relevance to decision, evidence direction, evidence scope, scope-aware condition status — each exists as a standalone module or file with zero external callers. Evidence direction and scope are imported only by decision-condition-status.js, which itself has no callers.

Corrections Made

None. The current-state document's active/passive classification is accurate as-is. Added verification marker to docs/current-project-state.md.

Practical Context-Test Result

Task: A developer proposes connecting Behaviour Selection directly to the next user-facing response. Is it active today? What boundary exists? Which files would need inspection before future integration?

Briefing:

  1. Active today? No. selectBehaviour is exported from lib/behaviour-selection/behaviour-selector.js but has zero callers anywhere in the repository. It is not active, diagnostic, or accessible through any API.
  2. Current boundary: Behaviour Selection and Investigation-State Assessment exist as separate modules that were never wired into the orchestrator's turn cycle. The orchestrator returns an assessment field to clients but does not pass assessment results into its own decision logic. There is no data path from state assessment → behaviour selection → question/response.
  3. Files to inspect before integration: lib/graph/orchestrator.js (where the insertion point would be — between unknown selection and question formulation, or after propagation); lib/assessment/investigation-state-assessor.js (to understand what the assessment contract outputs); lib/behaviour-selection/behaviour-selector.js (to understand what behaviours it can produce); docs/investigation-state-assessment-contract.md and docs/behaviour-selection.md for the documented interfaces; app/api/cases/update/route.js to determine whether behaviour output would appear in the API response or remain internal.
  4. Context sufficient? Yes — the three-file set (current-project-state, verification file, guardrails) plus targeted code inspection of the modules above provides sufficient context for a designer to assess integration scope without reopening the full history.
  5. Verdict: Integration is feasible as a future experiment. The primary risk is that behaviour selection has no documented input contract from the assessment layer — these were built in parallel without an agreed handoff shape.

Unresolved Questions

  • Whether the assessment output from assessInvestigationState matches the documented investigation-state-assessment-contract.md (requires reading the assessor's internal logic, excluded per constraints).
  • Whether external API clients (not in this repo) call the orchestrator directly, bypassing the route files.
  • The exact integration sequence: should behaviour selection read from assessment output or from the graph state directly?

Return-to-Work Note

The current-state briefing was checked against source code via targeted code inspection of API routes, orchestrator imports/calls, and cross-module traces for each passive classifier. Five active capabilities are confirmed (reconstruction, graph updates, unknown selection, question formulation, turn orchestration). Seven passive capabilities remain classified as diagnostic_only (investigation-state assessment) or isolated (behaviour selection, decision-condition status, evidence direction, evidence scope, question importance, question relevance to decision, scope-aware condition status). No corrections to the current-state document were required. Knowledge-management work remains active. Engine and UI experiments remain paused. Branch: feature/user-workspace-ux-v0.7. First file to inspect when resuming: docs/current-project-state.md, then .claude/architecture-guardrails.md before any code changes, then lib/graph/orchestrator.js for engine-resumption work.

Branch: feature/user-workspace-ux-v0.7 Commit: 61c8a3a

Experiment 29 — Archive the History Without Losing the Trail

Status: Pending Rob's review

Hypothesis

Historical documents can be moved into a clearly labelled archive without breaking links, losing evidence, or confusing future sessions. A fresh Claude session should still be able to understand the current system from the short entry point, locate historical material when specifically needed, and identify which documents are current versus retained only as evidence.

Files Archived (5)

Original Path Archive Path Reason
docs/v0.4-handoff.md docs/archive/v0.4-handoff.md Historical v0.4 handoff; architecture has evolved since. Referenced in orchestrator-contract.md (reference repaired).
docs/v0.4-route-status.md docs/archive/v0.4-route-status.md Historical route tracking; current routes differ.
docs/v0.5-release-notes.md docs/archive/v0.5-release-notes.md Historical release record; nothing active depends on it.
docs/v0.6-ambiguity-generalisation.md docs/archive/v0.6-ambiguity-generalisation.md Superseded by later reasoning architecture decisions (Exp 1525B).
docs/v0.7-observation-report.md docs/archive/v0.7-observation-report.md Experimental observation snapshot; useful reference but not current guidance. UX work paused.

Files Deliberately Not Archived (2)

Document Reason
docs/architectural-principles.md 14 architectural principles from experiments; may be needed when re-engaging with reasoning architecture. Status unclear — review before future archive.
docs/backlog info.md Mock fixture backlog useful if resuming UI development. Needs content verification before archiving.

Reference Repairs

  • docs/orchestrator-contract.md: Updated reference from docs/v0.4-handoff.md to docs/archive/v0.4-handoff.md (line 78) and table entry (line 87).
  • docs/project-knowledge-inventory.md: Updated all five archive candidate entries with new paths and provenance notes; updated Return-to-Work section.
  • No other files contained active references to archived documents.

Practical Archive Test

Task: A developer needs to find what v0.4 originally said about the case-orchestration API, without reading the full experiment log or archive directory.

Execution: From docs/project-knowledge-inventory.md (section 3) → identifies docs/archive/v0.4-handoff.md as the historical handoff for v0.4 architecture; from docs/archive/README.md → confirms file exists at that path and explains what it contains; verified file is accessible.

Result: The developer can locate the correct archived document in two steps: (1) inventory identifies which past document contains relevant evidence, (2) archive index confirms location and contents. The current project can be fully understood from docs/current-project-state.md alone without opening any archived file. No current task depends on archived files by default — they are consulted only when a named past decision or release is under investigation.

Uncertain Candidates

  • docs/architectural-principles.md: Should it be archived now, or reviewed first for accuracy against current implementation? Decision deferred to Rob's review.
  • docs/backlog info.md: Contains mock fixtures — may become irrelevant if the fixture strategy changes. Needs content verification before any future archive decision.

Status

Pending Rob's review.

These are observations, not implementation tasks.

  • Narrative adapter
  • Narrative quality heuristics
  • Narrative progression
  • Narrative completion state
  • Narrative confidence wording
  • Narrative testing
  • Narrative localisation
  • Multiple narrative projections

Experiment 30 — Review Deferred Project Documents

Status: Pending Rob's review

Hypothesis

Each deferred document can be classified by comparing it with the verified current project state without reopening the full experiment history or rewriting its contents. The result may be: keep as current guidance, keep as task-specific reference, archive as historical evidence, or retain temporarily pending revision. No additional categories should be invented.

Review of architectural-principles.md

  • 14 principles assessed against verified implementation:

    • 6 current (match runtime or guardrails): P1 (layer separation), P3 (user feedback loop), P4 (reasoning/UI separation), P6 (presentation renders, does not interpret), P8 (narrative never invents facts), P14 (user as first-class input).
    • 4 aspirational targets: P5 (behaviour never reasons — module exists with zero callers), P10 (convergence over single signals — no mechanism), P11 (stateful assessment across turns — partially present), P12 (assessable uncertainty — absent).
    • 4 mixed/unclear: P2 (information flows downward — partially matches but passive layers don't fit the cascade model), P7 (assessment never generates evidence — diagnostic_only but scope-aware condition status makes interpretive judgments), P9 (assessment describes not prescribes — signals descriptive, but decision-condition evaluation borders on prescription), P13 (progress qualitative not quantitative — product direction supports; unknown selection uses node status qualitatively but not verified).
    • 3 duplicated with guardrails: P1 overlaps with architecture-guardrails' prohibition list. P4 overlaps with UX-task boundaries in guardrails. P8 overlaps with the explicit invariant "every question comes from a resolved graph node." Overlap adds value: guardrails state boundaries; principles explain why.
  • Role assigned: Keep as task-specific reference. Six current principles and four aspirational targets make it valuable when resuming reasoning architecture work. Three duplications reduce (but don't eliminate) its independent value — the derived-from/implication context adds what guardrails lack. project-knowledge-inventory already listed it under "Review Before Archive"; confirmed as task-specific reference.

Review of backlog info.md

  • Content analysis:

    • Still-relevant (≈20 lines): Mock fixtures table — 15 scenario types with purposes and examples. Directly useful when UI work resumes.
    • Historical/aspirational (≈370 lines): UX roadmap phases 14 with wireframe text, animation specs, loading messages. Design intent is valid; specifics may change when UI resumes. Untracked — no commit/PR linkage.
    • Duplicates: Phase 4 "Mock Scenario Library" duplicates the fixtures table at top. "Deliberately Out of Scope" repeats pause decision in current-project-state and project-context.
  • Role assigned: Retain temporarily pending revision. The mock fixtures table is too useful to lose in an archive, but the document's mixed role (useful reference + deferred planning) needs resolution when UI work resumes. Splitting the file or archiving portions requires revising content — constraints forbid this now.

Practical Routing Test Result

Task: A future Claude session is about to work on UI mocks. Should it read architectural-principles.md, backlog info.md, both, or neither?

Answer: Both. Backlog info.md provides the mock fixtures table (direct reference). Architectural-principles.md provides boundaries (P4: reasoning never communicates directly with UI; P6: presentation never interprets) that prevent accidentally introducing reasoning logic into UI work. Three-document context (current-project-state, project-knowledge-inventory, document-role-review) is sufficient to route both documents correctly without reading the full experiment log or archive.

Files Created / Modified

  • docs/document-role-review.md — new (140 lines); classifies both candidates with evidence and routing test
  • docs/project-knowledge-inventory.md — updated "Review Before Archive" table (principle roles added), added "Knowledge management" section with document-role-review entry, updated Return-to-Work note
  • docs/current-project-state.md — updated Return-to-Work note to include Experiment 30 status
  • No files moved to archive (neither candidate qualifies as "archive as historical evidence")
  • No files deleted; no source code or tests changed

Status

Pending Rob's review. Neither document moves. Both roles confirmed by evidence against verified implementation. When UI work resumes, backlog info.md's fixtures table will be the direct reference; architectural-principles.md is available for reasoning architecture context. Engine and UI experiments remain paused. Branch: feature/user-workspace-ux-v0.7. First file to inspect when resuming: docs/current-project-state.md, then Experiments 2325B in design-evolution-log.md (lines 12181520).

These are observations, not implementation tasks.


Experiment 31 — Separate Useful UI Reference From Unstructured Backlog

Branch: feature/user-workspace-ux-v0.7

Hypothesis

The document docs/backlog info.md can be divided into:

  • a short task-specific mock/UI reference that remains in the normal documentation area;
  • a retained deferred backlog document that is excluded from default context loading.

This should make future UI work easier without losing previous ideas.

Separation Method

Original file docs/backlog info.md (390 lines) was split into two new documents:

  1. docs/ui-mock-reference.md (~62 lines) — practical mock-fixture reference extracted from the original lines 120, structured with available scenarios, fixture data locations, when-to-use guidance, and warnings.
  2. docs/archive/deferred-ux-backlog.md (376 lines) — deferred UX planning content from original lines 21390, preserved with original header stating items are not commitments.

The original file was removed after complete accounting (every section accounted for in one of the two new documents).

Content Accounting

Original Section Line Range Destination Treatment
Mock fixtures table + intro 120 docs/ui-mock-reference.md Represented as structured reference (same scenarios, enhanced with fixture data locations and usage guidance)
UI Roadmap header + intro 2126 docs/archive/deferred-ux-backlog.md Copied unchanged
Phase 1 Core Investigation Experience 27118 docs/archive/deferred-ux-backlog.md Copied unchanged
Phase 2 UX Polish 119169 docs/archive/deferred-ux-backlog.md Copied unchanged
Phase 3 Developer Experience 197218 docs/archive/deferred-ux-backlog.md Copied unchanged
Phase 4 Mock Scenario Library 219326 docs/archive/deferred-ux-backlog.md Copied unchanged (scenarios listed twice — once in original fixtures table, once here — no duplication introduced)
Backlog Reasoning Replay 328378 docs/archive/deferred-ux-backlog.md Copied unchanged
Deliberately Out of Scope 379390 docs/archive/deferred-ux-backlog.md Copied unchanged

Material not transferred: None. Every original section is represented in one of the two new documents.

Files Created

  • docs/ui-mock-reference.md (~62 lines) — mock fixture scenario reference
  • docs/archive/deferred-ux-backlog.md (376 lines) — deferred UX planning backlog

Files Removed

  • docs/backlog info.md (390 lines) — superseded by the split; all content accounted for above

Files Modified

  • docs/archive/README.md — added deferred-ux-backlog to Archived Files table; added Superseded Files section with backlog info.md entry
  • docs/project-knowledge-inventory.md — added ui-mock-reference to UI/UX task-specific references; added deferred-ux-backlog to archive candidates; updated backlog info.md role to "superseded"; updated Return-to-Work note
  • docs/current-project-state.md — updated Section 6 (Return-to-Work Summary) and section 8 header/note to reflect Experiment 31 split
  • .claude/project-context.md — added routing notes: UI mock work reads ui-mock-reference; deferred backlog only for named UX idea review

Line Counts Before / After

Document Lines (before) Lines (after)
Original combined document (backlog info.md) 390 removed
New mock reference (ui-mock-reference.md) ~62
New deferred backlog (deferred-ux-backlog.md) 376
Total new content 438 (62 + 376, including headers in both)

Practical Routing Test Result

Scenario: A developer wants to test the workspace against a long investigation and a contradictory-evidence scenario. Which mock scenarios should they use, and where is the fixture data defined?

Answer: They should use:

  • Long investigation (1015 turns) — for testing history scrolling, collapsing, pacing;
  • Contradiction — for testing contradiction detection and user-facing messaging.

Fixture data is defined in tests/e2e/fixtures/investigation-scenarios.js. The mock client is in lib/mocks/confidence-engine/mock-client.js. Scenario names are set via NEXT_PUBLIC_CONFIDENCE_ENGINE_MOCK_SCENARIO env var in components/scenario-form.jsx. Reference details and usage guidance are in docs/ui-mock-reference.md.

Was the deferred backlog necessary? No. The practical routing test was answered entirely from ui-mock-reference.md, project-knowledge-inventory.md, .claude/project-context.md, and architecture-guardrails.md. The deferred backlog (376 lines of aspirational UX planning) was not required to answer a practical mock-scenario question.

Was any practical mock information lost? No. All 13 fixture scenarios are preserved in ui-mock-reference.md with enhanced guidance on where fixtures live and when to use each. The original fixtures table's content is fully represented.

Gaps Found

  • docs/ui-mock-reference.md references tests/e2e/fixtures/investigation-scenarios.js as the fixture definition location but does not list individual scenario keys or env var values (by design — those are implementation details that can be inspected directly in the fixture file).
  • The deferred backlog contains specific wireframe text and animation specifications that may still be useful when UI work resumes. The header note ("not commitments, priorities or active tasks") should prevent premature actioning.

Status

Pending Rob's review. Both new documents contain all original content. Branch feature/user-workspace-ux-v0.7 is clean after commit. Engine and UI experiments remain paused.

Experiment 32 — Separate Current Principles From Aspirational Architecture

Branch: feature/user-workspace-ux-v0.7

Hypothesis

A short current-principles document can guide normal work while the original architectural-principles document remains available as the fuller historical and aspirational source. This should reduce ambiguity without deleting or rewriting the original reasoning.

Source Documents Used

  • docs/current-project-state.md — What the Confidence Engine Is; Current Engine Capabilities; Context Loading Guide
  • .claude/architecture-guardrails.md — entire file (77 lines)
  • docs/document-role-review.md — Architectural Principles Review (§2) and Recommended Actions (§4)
  • docs/architectural-principles.md — headings and the 14 principles only
  • docs/03_Confidence_Engine_Language_Guide.md — guiding principles only
  • docs/current-implementation-verification.md — Active Capabilities; Passive or Isolated Capabilities
  • Experiment 31 entry in docs/design-evolution-log.md (lines 18111893)

Principles Included

User Experience (5): System carries complexity; steps are small enough to understand or investigate; engine guides without pretending certainty; first input is the hardest step; users may know answer/who to ask/where to look/how to test.

Reasoning (5): Resolved question ≠ established condition; evidence supports/contradicts/informs; present evidence does not settle future feasibility; uncertainty stated honestly; deterministic contracts separate from language interpretation.

Building the System (6): Build smallest thing that can be wrong; use evidence before architecture; every layer has one responsibility where applicable; presentation does not invent facts; current and aspirational labelled separately; load only needed context.

Total: 16 current principles, organized into three sections.

Aspirational Material Deliberately Excluded

From docs/architectural-principles.md: P2 (Information Flows Downward — unresolved), P5 (Behaviour Never Reasons — aspirational), P7 (Assessment Never Generates Evidence — mixed), P9 (Assessment Describes Never Prescribes — mixed), P10 (Convergence Over Single Signals — aspirational), P11 (Assessment Is Stateful Across Turns — mixed/aspirational), P12 (Uncertainty About Assessment Is Itself Assessable — aspirational), P13 (Investigation Progress Is Qualitative Not Quantitative — mixed/aspirational). These remain in the original document for broader architectural review.

Practical Principles-Test Result

Task: A developer proposes making every resolved question automatically increase confidence and close its related condition. Explain whether this fits current principles and why.

Response from reduced context (current-project-state + current-working-principles + architecture-guardrails):

  1. Resolving a question does not establish a condition. current-working-principles §2 states: "A resolved question is not an established condition." Answer evidence must be inspected before any conclusion follows.
  2. Answer evidence must be inspected. current-working-principles §2 states direction alone (support/contradict/inform) is insufficient without checking subject, timeframe, and claim type alignment.
  3. Confidence should not be manufactured. architecture-guardrails invariants state "Confidence must not outrun evidence or completeness" and "Duplicate evidence must not increase confidence." current-project-state section 4 confirms: resolving a question does not automatically establish the condition.
  4. Passive experimental logic is not automatically active behaviour. current-project-state section 3 classifies passive classifiers (including decision-condition status evaluation) as diagnostic_only or isolated — they do not yet control the user-facing investigation.

Was the three-document context sufficient? Yes. All four points were answerable from docs/current-working-principles.md (principles §2), .claude/architecture-guardrails.md (reasoning invariants), and docs/current-project-state.md (section 3 passive classifier classification, section 4 what experiments established). No experiment history or source code was required.

Unresolved Ambiguities

  • The boundary between "current" and "aspirational" for P7 and P9 is inherently subjective; future sessions may interpret differently without the original document's reasoning context.
  • Some principles overlap with .claude/architecture-guardrails.md (e.g., "every layer has one responsibility" overlaps with guardrails' exhaustive prohibition list). No duplication was introduced deliberately, but a cross-reference could reduce redundancy in a future iteration.
  • The aspirational note points readers to the original document but does not provide a quick reference for which of the 14 principles are current versus aspirational. A summary table might be useful when architecture work resumes.

Status

Pending Rob's review. No source code or tests changed. Engine and UI experiments remain paused. No files moved or deleted. Only documentation files were created or updated.

Return-to-Work Note (80150 words)

Current principles now live in docs/current-working-principles.md. This short document contains only guidance supported by verified implementation, current project direction, and established product philosophy — organised into three sections: user experience, reasoning, and building the system. Broader and aspirational architecture remains in docs/architectural-principles.md as a task-specific reference; it has not been rewritten or deleted. Future sessions should use docs/current-working-principles.md by default for product and reasoning work. Engine and UI experiments remain paused after Experiment 25B. Branch: feature/user-workspace-ux-v0.7. First file to inspect when resuming: docs/current-project-state.md, then docs/current-working-principles.md for current guidance.


Experiment 33 — Create Task-Specific Context Packs

Branch: feature/user-workspace-ux-v0.7

Hypothesis

A single concise context-pack guide can give each task type a minimal reading list, clear exclusions, and a stopping rule — reducing unnecessary context loading while preserving access to deeper material when a specific gap appears.

Source Documents Used

  • docs/current-project-state.md — Context Loading Guide; Current Engine Capabilities; Work Currently Paused
  • docs/project-knowledge-inventory.md — Current Working Context; Task-Specific References
  • docs/current-implementation-verification.md — Active Capabilities; Passive or Isolated Capabilities
  • docs/current-working-principles.md — entire file
  • docs/ui-mock-reference.md — headings and routing information only
  • .claude/project-context.md — routing notes only
  • .claude/architecture-guardrails.md — headings only
  • Experiment 32 entry in docs/design-evolution-log.md (lines 18951948)

Deliverable

Created docs/task-context-packs.md (~110 lines) with four packs:

  • Pack 1 — Engine Experiment Work: current-project-state, current-working-principles, architecture-guardrails, current-implementation-verification.
  • Pack 2 — UI and Mock Work: current-project-state, current-working-principles, architecture-guardrails, ui-mock-reference.
  • Pack 3 — Architecture or Contract Review: current-project-state, current-implementation-verification, architecture-guardrails, current-working-principles + aspirational warning.
  • Pack 4 — Knowledge-Management Work: current-project-state, project-knowledge-inventory, task-context-packs, project-context.

Each pack lists what to always read, what to read only when relevant, and what to not load by default. Common rules prevent silent context inflation. Two routing tests verify sufficiency without loading history or source code.

Routing Test A — Engine Task

Task: Verify whether Behaviour Selection currently affects the user-facing response. Result: Pack sufficient. docs/current-implementation-verification.md §3b states "Called by: None" for Behaviour Selection; docs/current-project-state.md §3 classifies it as isolated. No extra file required.

Routing Test B — UI Task

Task: Choose the correct mock scenarios for testing a long investigation and contradictory evidence. Result: Pack sufficient. docs/ui-mock-reference.md lists "Long investigation (1015 turns)" and "Contradiction" with matching purposes. Deferred UX backlog not needed.

Validation

  • All referenced files exist; no pack relies on fixed line numbers.
  • Each pack has a smaller default context than the full project documentation.
  • Active and passive capabilities remain clearly separated.
  • No source code or tests changed; no files moved or deleted.

Return-to-Work Note

Task-specific context packs now exist in docs/task-context-packs.md, giving each work type a minimal four-document starting set plus targeted reading paths. Future sessions should start with docs/current-project-state.md, then choose one pack from docs/task-context-packs.md. Additional documents should be loaded only for a named gap, with the reason recorded. Engine and UI experiments remain paused. Branch: feature/user-workspace-ux-v0.7. First file to inspect when resuming: docs/current-project-state.md, then select the relevant pack from docs/task-context-packs.md.


Experiment 34 — Single Return-to-Work Handoff

Date: 2026-08-06
Branch: feature/user-workspace-ux-v0.7

Hypothesis

A single short handoff file can carry enough immediate context to resume work accurately while linking to deeper documents only when needed.

Handoff Structure

Eight sections: Where We Left It, What Is True Now, Why Work Is Paused, What Was Just Completed, What Remains Open, How to Resume, First Files by Work Type (table), Resume Check (five questions). Plus a maintenance rule replacing current-work sections when the project moves on.

Document Length

docs/current-handoff.md: 68 lines (target range: 60100).

Practical Resume-Test Result

Task: Return after two weeks, remember almost nothing. Explain where the project stands, what is paused, what was completed most recently, and what to read before an engine task — using only docs/current-handoff.md and docs/task-context-packs.md.

Check Result
Identifies correct active phase (knowledge management) Yes
Identifies paused engine and UI work Yes
Identifies Experiment 33 as latest completed Yes
Chooses Engine Experiment pack for engine task Yes
Avoids opening full design history Yes
Does not confuse passive code with active behaviour Yes

Verdict: Pass. The handoff alone is sufficient to resume accurately.

Missing Information

  • "When knowledge-management work is complete enough to resume engine experiments" — no objective criterion exists yet; this is a judgment call for Rob.
  • "Whether tasks crossing pack boundaries can still stay concise" — unanswered in principle; requires testing with actual cross-boundary tasks.
  • Whether docs/current-handoff.md remains useful after several more knowledge-management experiments add to it.

Can This Replace Scattered Current Return Notes?

Yes, for immediate resumption context. The handoff carries the latest stopping point without accumulating old notes. Historical return notes remain in docs/current-project-state.md and docs/design-evolution-log.md as evidence, not as current guidance. Rob should decide whether to purge older return notes once confident in the handoff model.

Status

Pending Rob's review.

Experiment 35 — Test Current Handoff Maintenance (2026-08-06)

Hypothesis: A current handoff can remain useful if it describes only the latest stopping point, replaces stale details rather than appending history, and identifies the latest confirmed experiment and commit unambiguously.

Stale or ambiguous wording found:

  • Section 1 named Experiment 33 and commit b959cfa as the current state — now stale after Experiments 34+35;
  • Section 4 described only Experiment 33's completion, giving no indication that a single handoff had been created in Experiment 34;
  • No explicit mention of commit 1d92aa0 anywhere in the handoff;
  • Footer said "Created by Experiment 34" without acknowledging this maintenance experiment.

Corrections made:

  • Section 1: updated to name Experiment 34 and commit 1d92aa0; added the maintenance principle ("replace stale details rather than appending history");
  • Section 4: rewritten to describe Experiment 34's consolidation work;
  • Section 5: retained one genuinely open question about handoff longevity; added provisional KM completion criteria sub-section (7 criteria, marked provisional);
  • Footer: updated to reference Experiment 35; added Return-to-Work Note recording all current state.

Fresh-return test result: PASS — from current-handoff.md and task-context-packs.md only, a fresh session can determine:

  • Latest completed KM experiment: Experiment 34 ✓
  • Latest commit: 1d92aa0
  • Knowledge-management active, engine/UI paused ✓
  • Knowledge-Management context pack is the correct routing target ✓
  • No need to open full design history ✓
  • Older commits not mistaken for current stopping point ✓

Provisional completion criteria added: Seven criteria recorded in Section 5 (see above). Not yet declared complete — pending Rob's review.

Handoff remained concise? Yes. 86 lines (was 68). Increase justified by the maintenance principle paragraph, updated current-state wording, and provisional completion criteria section. No historical timeline appended.

Status: Pending Rob's review.

Experiment 36 — Validate Reduced Context Routing

Branch: feature/user-workspace-ux-v0.7

Hypothesis

The documentation system (handoff + project-state + task-context-packs) is complete enough to support normal work without silently expanding into historical documentation. A fresh session can complete representative tasks using only routing instructions.

Initial Documents Loaded (328 lines total)

  1. docs/current-handoff.md — 86 lines
  2. docs/current-project-state.md — 132 lines
  3. docs/task-context-packs.md — 110 lines

Additional Documents Loaded

Document Lines Why Needed Routing Should Include?
docs/ui-mock-reference.md 63 Task 2: verify mock scenarios for "long investigation" and "contradiction". Routing Test B claimed these were identifiable without loading it, but the specific scenario names do not appear in any initial document. YES — routing defect found
docs/project-knowledge-inventory.md 215 Task 4: confirm Engine Experiment pack's four always-read documents actually exist and understand KM phase outputs. Debated — validated completeness but not strictly required by routing
docs/current-implementation-verification.md 111 Cross-checked Behaviour Selection isolation against current-project-state §3. Provided corroboration but was not the sole basis for Task 1 answer. Debated — useful corroboration; current-project-state alone sufficed

Tasks Completed Without Context Expansion

Task 1 — Does Behaviour Selection affect engine behaviour? No. Current project state §3 classifies it as isolated. Handoff §2 confirms passive classifiers don't control the investigation. Task-context-packs Routing Test A corroborates (current-implementation-verification §3b).

Task 3 — Why passive classifiers are not yet in the active reasoning loop? Passive classifiers record diagnostic signals for future use but have no integration into the turn cycle. Only investigation-state assessment is called (at 3 orchestrator sites), and its result goes into a diagnostics field — never checked by conditional branches. Others have zero callers.

Tasks Requiring Extra Context

Task 2 — Mock scenarios for long investigation and contradictory evidence Required docs/ui-mock-reference.md. Routing Test B in task-context-packs claimed these were identifiable without loading it, but the specific scenario names ("Long investigation (1015 turns)" and "Contradiction") do not appear in any initial document. The routing claim was unverifiable until the mock reference was loaded — this is a genuine routing defect.

Task 4 — Where should a new developer begin for the next engine experiment? Partially answered from initial documents (handoff → project-state → pack). Marginal need to verify that all four always-read pack documents actually exist, resolved by cross-referencing project-knowledge-inventory.

Routing Failures Found

One genuine failure: Routing Test B in task-context-packs.md. The test states that mock scenarios for long investigation and contradiction are identifiable without loading ui-mock-reference.md. This was presented as a self-evident fact but the specific scenario names only exist in ui-mock-reference.md. The routing is incomplete — it should have included the mock reference file, or at minimum acknowledged that scenario names require verification.

Documentation Changes Made

  • Created docs/context-routing-validation.md (62 lines) — this experiment's record
  • Updated docs/design-evolution-log.md — appended Experiment 36 entry

No source code or tests changed. No archive changes.

Overall Assessment: Mostly ready

Two of four tasks completed from initial context only. One routing defect found (Task 2; corrected by Experiment 37). After fixing Routing Test B to name ui-mock-reference.md as the scenario source, the reduced context system is ready for normal work.


Experiment 37 — Validate Cross-Boundary Context Routing

Branch: feature/user-workspace-ux-v0.7

Hypothesis

The context-pack system can support cross-boundary work if Claude:

  1. starts with one primary pack;
  2. adds a second pack only for a named boundary;
  3. records why each extra document was loaded;
  4. avoids loading the full history.

Initial Documents Loaded (328 lines total)

  1. docs/current-handoff.md — 85 lines; first return-to-work entry point
  2. docs/current-project-state.md — 131 lines; active state and capabilities
  3. docs/task-context-packs.md — 110 lines; routing for four work types

Additional Documents Loaded

Document Lines Why Needed Routing Should Include?
docs/ui-mock-reference.md 62 Cross-boundary boundary: the task requires identifying a mock scenario for workspace display. This is the second pack (UI and Mock) needed because no other loaded document names scenarios or UI fixtures. Yes — it is part of the UI/Mock pack, not an ad-hoc addition.

Cross-Boundary Task Result

Task: Display passive condition-status information in the workspace for a mock investigation without changing the active reasoning loop.

Finding Details
Condition-status capability Passive: decision-condition status evaluation records signals but has no integration into the turn cycle; never controls user-facing decisions or path selection
Active reasoning loop Unchanged: deterministic pipeline (scenario reconstruction → graph update → unknown selection → question formulation → turn orchestration); none of these pathways are affected by passive data
Mock scenario "Long investigation (1015 turns)" from ui-mock-reference.md; workspace can display accumulated diagnostic signals over time without interrupting the active reasoning cycle
Implementation areas to inspect later decision-condition-status evaluation module; evidence scope detection module; UI workspace components for passive display integration
Both packs genuinely needed? Yes: Engine pack identifies which capabilities are active vs passive; UI pack identifies how the workspace presents state. Neither alone suffices
Archive or full history required? No

Context remained manageable: Yes. 390 lines total (328 initial + 62 additional). Each document loaded for a specific named purpose. No blind expansion.

Knowledge-Management Completion Criteria Review

Criterion Status
1. Fresh session can resume from handoff + one pack met
2. Current state verified against implementation met
3. Historical material outside default loading met
4. Current principles separated from aspirational architecture met
5. Task-specific routing works for engine and UI tasks met
6. Cross-boundary task tested met
7. Maintaining handoff does not require reading full history met

All seven criteria are now met.

Knowledge-management structure is ready for Rob's review before engine experiments resume.

Routing Defects Discovered

None in this experiment. The correction to Routing Test B (naming ui-mock-reference.md as the scenario source) was applied before testing. No new defects found in the cross-boundary test.

Overall Assessment: Ready

The context-pack system handled a genuine engine/UI cross-boundary task by combining two packs deliberately with full documentation of each loaded document and its purpose. Context remained small (390 lines). All knowledge-management criteria are met.


Experiment 38 — Cold-Start Project Recovery Validation

Branch: feature/user-workspace-ux-v0.7 Type: Knowledge-management / handoff validation (final KM experiment) Objective: Test whether a genuinely cold session can recover the project accurately from the reduced context system alone without reading the full history or any earlier experiment reports.

Setup

Cold-start configuration: no prior conversation context, no past experiment reports loaded, repository documentation carries all context. Session was freshly created to simulate a real return-to-work scenario. Only docs/current-handoff.md was read first (per handoff §6 step 1), then the two documents specified by its resume instructions (§6 steps 23): docs/current-project-state.md and docs/task-context-packs.md.

Documents Loaded

Document Reason
docs/current-handoff.md Primary entry point (handoff §6 step 1)
docs/current-project-state.md Resume instruction (§6 step 2) and routing table (§6 step 7)
docs/task-context-packs.md Pack selection (§6 step 3) and pack contents for verification

No additional documents were loaded. No blind expansion occurred. The full design-evolution log, archived documents, UI mock reference, source code, and tests were all excluded by design.

Project-State Recovery Result

The cold session correctly recovered:

  • What the Confidence Engine does (facilitated investigation with structured reasoning graph).
  • Active capabilities: deterministic reasoning pipeline, unknown selection via atomicity/answerability, question formulation, scenario API, turn cycle orchestration.
  • Passive capabilities: seven diagnostic layers from Experiments 1825B, all isolated, none control user-facing investigation.
  • Paused work: engine experiments (after Exp 25B), UI experiments.
  • Why KM phase was undertaken (documentation bloat blocking session recovery).

Recovery score: complete from three documents alone. No source code inspection required.

Context-Pack Selection Result

Pack 1 — Engine Experiment Work selected correctly by the cold session. The three initial documents contained sufficient information to identify the pack, its default documents, and what to exclude without reading any additional material.

Handoff Defects Found

None found in docs/current-handoff.md. The handoff accurately describes the stopping point, identifies all seven KM criteria as met, provides correct resume instructions, and includes accurate capability boundaries. One structural update was made: the open item "whether the handoff stays accurate after further advances" was resolved as no longer applicable (the cold-start test confirmed it is accurate).

Completion-Criteria Result

All seven knowledge-management completion criteria are confirmed met by this cold-start validation:

  1. Fresh session can resume from handoff + one pack — met (Exp 38 demonstrates this)
  2. Current state verified against implementation — met (Exp 28+)
  3. Historical material outside default loading — met
  4. Current principles separated from aspirational architecture — met
  5. Task-specific routing works for engine and UI tasks — met (Exp 37)
  6. Cross-boundary task tested — met (Exp 37)
  7. Maintaining handoff does not require reading full history — met

The knowledge-management phase is complete enough for Rob to choose when engine experiments resume.

Documents Updated

  • docs/cold-start-validation.md — created (this experiment's deliverable)
  • docs/current-handoff.md — Exp 38 commit placeholder, structural open-item resolution, return-to-work note replacement
  • docs/current-project-state.md — KM status update ("active" → "complete"), latest known commit correction
  • docs/design-evolution-log.md — this entry

Overall Assessment: Ready

The cold-start validation passed. A genuinely fresh session understood the project state, chose the correct context pack, verified the resume boundary, produced a valid engine-work resume brief, and found no handoff defects — all from three documents alone. No source code was read or changed. The reduced context system works for sessions that did not help create the documents.

Engine and UI experiments remain paused pending Rob's review.


Experiment 39 — Validate Behaviour Selection Against Real Assessment Outputs (2026-08-06)

Branch: feature/user-workspace-ux-v0.7

Hypothesis

The existing deterministic selector produces a useful rhythm across genuine assessment outputs without changing the active engine. If it repeatedly chooses one behaviour, chooses behaviours at the wrong time, or depends on signals the assessor does not actually produce, the experiment should expose that honestly.

Scenarios Evaluated (from tests/investigation-state-assessor.test.js fixture set)

  1. Long investigation (3 turns: early → deepening → complete terminal)
  2. Contradictory evidence (3 turns: two conflicting consultants, 0→1→2 resolved unknowns)
  3. Short early (1 turn: two observations, first unknown, no resolution)

Behaviour Distribution (7 turns total)

  • Acknowledge: 5 (71%)
  • Continue: 2 (29%)
  • Clarify: 0 (0%)
  • Summarise: 0 (0%)
  • Pause: 0 (0%)

Behaviour Sequence by Scenario

Long investigation: continue → acknowledge → acknowledge

  • Turn 0: phase=cannot_determine, progress=cannot_determine, health=too_narrow → continue (no rule matched)
  • Turn 3: phase=focusing, progress=steady, health=healthy → acknowledge
  • Turn 4: phase=concluding, progress=steady, health=healthy → acknowledge

Contradictory evidence: acknowledge → acknowledge → acknowledge

  • Turn 0: phase=focusing, progress=cannot_determine, health=healthy → acknowledge
  • Turn 1: phase=focusing, progress=stalled, health=healthy → acknowledge
  • Turn 2: phase=focusing, progress=steady, health=healthy → acknowledge

Short early: continue

  • Turn 0: phase=exploring, progress=cannot_determine, health=healthy → continue

Sensible Selections (7 of 7)

All selections were classified as sensible per the selection's stated conditions. Acknowledge fires because health=healthy AND phase confidence≠low across most states. Continue fires when no specific rule matches (early/cannot_determine/exploring phases).

Questionable or Inappropriate Selections

One notable pattern: Summarise and Pause never fire, even in a concluding terminal state. This is not because the assessor fails to detect "concluding" — it does. It is because Acknowledge (priority 1) fires first when health=healthy, blocking Summarise (priority 3) from ever reaching its turn. This is an acknowledgement/summarise priority conflict: acknowledging a conclusion ("you've figured this out!") is not wrong, but "give me a summary" is more useful at terminal states. The current rule ordering does not distinguish "early healthy" from "concluding healthy."

Clarify never fires because no test scenario produces health=too_broad — the assessor's "too_broad" trigger (activeUnknownCount > 3 AND resolved < 2) requires more nodes than any scenario in the fixture set has at that stage.

Pause never fires because health=user_overloaded is never reached, and while contradictory-turn-1 has phase=focusing + progress=stalled, Acknowledge still blocks it.

Contract Alignment

Assessor → Selector contract aligns cleanly. The assessor produces all three dimensions (phase, progress, conversationHealth) with the fields the selector expects. No transformation needed between pipeline stages.

Whether Selector Appears Useful Enough for Another Passive Experiment

The existing selector works but its behaviour variation is severely constrained by Acknowledge's priority position. A next passive experiment should test whether reordering or refining the acknowledge condition (e.g., excluding concluding/terminal phases) produces more context-appropriate behaviour — without changing the assessor.

Status

Pending Rob's review. Five behaviours are too narrow for this to be definitive, and only three scenarios were tested. The dominant pattern (acknowledge in healthy states) may change with different investigation domains.

Documents Updated

  • docs/design-evolution-log.md — this entry
  • docs/current-handoff.md — return-to-work note replaced

Experiment 40 — Audit Behaviour Reachability and Blocking (2026-08-06)

Objective

Why did Clarify, Summarise, and Pause not appear during Experiment 39? Acknowledge: 5 (71%), Continue: 2 (29%), others: 0. This is a passive diagnostic — no rule changes, no engine modifications.

Method

One test file (tests/behaviour-selection.reachability.test.js) containing:

  • Diagnostic audit helper that evaluates every behaviour rule against one assessment object
  • Real-scenario audits across the same Experiment 39 turns (8 turns total)
  • Synthetic reachability checks for each behaviour in isolation

Findings

Summarise — eligible_but_blocked

Eligible in 2 of 7 real turns:

  • long-investigation turn 1 (resolvedNodeCount ≥ 3 + progress=steady triggers summarise rule)
  • long-investigation turn 2 (phase=concluding triggers summarise rule)

In both cases, health=healthy simultaneously, so Acknowledge (priority 1) fires first. Summarise rules are met but its output is never returned because the selector returns early on priority ordering.

Root cause: priority conflict, not assessor failure. The phase evidence correctly identifies concluding/synthesising states; the problem is that Acknowledge's broader trigger condition (health=healthy is the most common state) fires first.

Clarify — never_eligible_in_tested_scenarios (reachable only in synthetic case)

Not eligible in any of 7 real turns because neither trigger condition is met:

  • health=too_broad: requires activeUnknownCount > 3 AND resolvedNodeCount < 2 — no fixture reaches this state
  • phase=orienting + observationDensity < 3: current assessor never produces phase=orienting for tested scenarios

Synthetic case confirms the rule fires correctly in isolation (with low-confidence phase to avoid Acknowledge blocking).

Root cause: assessor health classification logic produces too few too_broad cases. The trigger condition is extremely narrow — needs activeUnknownCount > 3 AND resolved < 2 simultaneously.

Pause — eligible_but_blocked

Eligible in 1 of 7 real turns:

  • contradictory-evidence turn 1 (phase=focusing + progress=stalled triggers pause rule)

In this case, health=healthy simultaneously, so Acknowledge blocks it. The second pause trigger (health=user_overloaded) is never met because the assessor never produces that state.

Root cause: same priority conflict as Summarise. One of two rules fires in real data but gets blocked by Acknowledge's earlier position.

Synthetic Reachability Confirmation

All five behaviours are independently reachable when isolated from Acknowledge:

  • acknowledge — healthy + confident phase
  • clarify — too_broad health (with low-confidence phase to avoid Acknowledge)
  • summarise — synthesising/concluding phase (without healthy health)
  • pause — focusing+stalled or user_overloaded (without healthy health)
  • continue — no rules match

Classifications

Behaviour Classification Primary Cause
Summarise eligible_but_blocked Acknowledge priority 1 fires first when health=healthy
Clarify never_eligible_in_tested_scenarios (reachable only in synthetic) too_broad trigger too narrow for test scenarios; orienting+low obs not produced by assessor
Pause eligible_but_blocked Acknowledge priority 1 fires first when health=healthy; user_overloaded never produced

Impact on Prior Finding (Exp 39)

Experiment 39 concluded "the Acknowledge→Summarise priority conflict prevents Summarise from firing." Experiment 40 confirms this and adds that Pause faces the same blocking (1 eligible turn, blocked). Clarify's absence is fundamentally different: its rules are not triggered at all in tested scenarios.

This means any fix must address two distinct problems:

  1. Priority conflict affecting Summarise AND Pause (same cause)
  2. Narrow trigger conditions for Clarify and the user_overloaded health state

Test Results

  • tests/behaviour-selection.reachability.test.js: 33 passed (new diagnostic file)
  • tests/behaviour-selection.test.js: 51 passed (no regressions)
  • tests/behaviour-selection.real-assessment.test.js: 16 passed (shared fixtures intact)
  • tests/investigation-state-assessor.test.js: 51 passed (assessor unchanged)

Documents Updated

  • docs/design-evolution-log.md — this entry
  • docs/current-handoff.md — return-to-work note replaced

Experiment 41 — Compare Acknowledge Priority Alternatives (2026-08-06)

Purpose

Experiment 40 confirmed Summarise and Pause are eligible_but_blocked by Acknowledge's priority-1 position. Two passive alternatives were compared without modifying production code:

Variant A — Reorder rules so specific behaviours (Summarise, Pause) evaluate before Acknowledge. The idea is that if a more specific behaviour fires first, it captures the terminal/stalled states where Acknowledge should not fire.

Variant B — Keep existing priority order but exclude Acknowledge from firing when phase=concluding/synthesising, progress=stalled, or health=user_overloaded. The idea is to gate Acknowledge rather than reorder everything.

Method

Both variants were implemented as test-only functions in tests/behaviour-selection.counterfactual.test.js. Each variant was evaluated against the same 7 real assessment turns from Experiments 39/40 across 3 scenarios. All five behaviours confirmed independently reachable synthetically. No production rules changed.

Assessor Outputs (7 real turns)

# Scenario Turn Phase (conf) Progress Health Existing
1 long-investigation 0 cannot_determine(low) cannot_determine too_narrow continue
2 long-investigation 3 focusing(high) steady healthy acknowledge
3 long-investigation 4 concluding(high) steady healthy acknowledge
4 contradictory-evidence 0 focusing(high) cannot_determine healthy acknowledge
5 contradictory-evidence 1 focusing(high) stalled healthy acknowledge
6 contradictory-evidence 2 focusing(high) steady healthy acknowledge
7 short-early 0 exploring(low) cannot_determine healthy continue

Results on Real Scenarios

Turn Existing Variant A Variant B Change?
long-investigation t3 acknowledge summarise acknowledge V-A: side-effect
long-investigation t4 acknowledge summarise summarise convergent ✓
contradictory-evidence t1 acknowledge pause pause convergent ✓
All others unchanged unchanged unchanged

Divergence Analysis

Variant A diverges from Variant B at long-investigation turn 3. Variant A produces summarise because its resolvedNodeCount >= 3 && steady rule fires at priority 1 without phase context. The assessor confirms this is a focusing-phase state (not synthesising/concluding) where the user needs acknowledgment, not compression. This is a false-positive for summarisation — a side-effect of Variant A's priority reordering.

Variant B correctly preserves Acknowledge at long-investigation t3 because:

  1. The exclusion list only includes synthesising, concluding, stalled, and user_overloaded — not focusing
  2. SummariseV2 itself has a phase gate (phase.value === "synthesising") that prevents false-fire in focusing states
  3. Acknowledge at priority 1 wins because no exclusion applies

Key Findings

  1. Both variants converge on the same two genuine changes: concluding → summarise and stalled → pause. This was the experiment's primary question, and both approaches answer it correctly.

  2. Variant A introduces a false-positive: The resolvedNodeCount >= 3 && steady rule fires in focusing-phase states without phase context, causing premature summarisation when Acknowledge would be more useful.

  3. Variant B has cleaner boundaries: Explicit exclusion conditions prevent unwanted side-effects while preserving Acknowledge's role as the default healthy-state behaviour.

  4. Distribution shift (both variants):

    • Existing: acknowledge 71%, continue 29%
    • Variant A: acknowledge 29%, summarise 29%, pause 14%, continue 29%
    • Variant B: acknowledge 43%, summarise 14%, pause 14%, continue 29%
    • Variant B preserves more Acknowledge because it doesn't remove the default healthy-state behaviour entirely
  5. Variant B is architecturally cleaner for this problem space because it adds a targeted gate to one rule rather than reordering five priority levels — each of which would need individual review for side-effects.

Test Results

  • tests/behaviour-selection.counterfactual.test.js: 44 passed (new diagnostic file)
  • tests/behaviour-selection.reachability.test.js: 33 passed (no regressions)
  • tests/behaviour-selection.real-assessment.test.js: 16 passed (shared fixtures intact)
  • tests/behaviour-selection.test.js: 51 passed (no regressions)

Decision Criteria

Criterion Variant A Variant B
Fixes concluding state ✓ summarise ✓ summarise
Fixes stalled state ✓ pause ✓ pause
No false-positive changes ✗ long-t3 → summarise ✓ preserved acknowledge
Implementation complexity Simple reordering Small gate function
Maintains Acknowledge for healthy focus states ? (depends on future review) ✓ explicit preservation

Recommendation

Variant B is preferred. Both variants correctly identify the two genuine changes needed. Variant B has no false-positives, cleaner architectural boundaries (targeted exclusion vs priority reordering), and better preserves the existing Acknowledge default for healthy focusing states where it is appropriate. A recommended implementation would:

  1. Keep existing priority order
  2. Add isAcknowledgeExcluded() function with conditions: phase∈{synthesising, concluding}, progress=stalled, health=user_overloaded
  3. Gate Acknowledge through this exclusion before selecting it at priority 1

Documents Updated

  • docs/design-evolution-log.md — this entry
  • docs/current-handoff.md — return-to-work note replaced