Lossless Changelog
component

Dimension-Grouped Questions for 12Ps Framework

Fixed a critical issue where Perplexity was returning garbage/meta-commentary for non-standard section names like "Opening" and "Organization" in the 12Ps outline.

Changelog - 2025-12-06 (#1)

Dimension-Grouped Questions for 12Ps Framework

Overview

Fixed a critical issue where Perplexity was returning garbage/meta-commentary for non-standard section names like "Opening" and "Organization" in the 12Ps outline. The root cause was that guiding questions were passed as a flat list without context about which dimension each question belonged to.


Problem

When the perplexity_section_researcher processed sections with non-standard names (like "Opening" instead of "Market Context"), Perplexity returned responses like:

"Let me fetch the Stratosphere company website and search for more specific market data:"

Or:

"I notice that you've asked me to add citations to an 'Opening section' but you haven't
provided the actual text content of that section..."

Root cause: The outline YAML had rich dimension-grouped structure:

YAML
guiding_questions:
  # Problem (P4)
  - "How many target customers exist?"
  # Possibility (P5)
  - "What is the TAM?"

But the YAML comments (# Problem (P4)) were lost during parsing, so Perplexity received a flat list with no context about what "Opening" or "Organization" meant.


Solution: Dimension-Grouped Questions

1. Schema Update (src/schemas/outline_schema.py)

Added new dataclass for dimension-organized questions:

PYTHON
@dataclass
class DimensionQuestions:
    """Questions organized by dimension for 12Ps framework."""
    dimension: str  # e.g., "problem", "possibility", "positioning"
    dimension_label: Optional[str] = None  # e.g., "Problem (P4)"
    questions: List[str] = field(default_factory=list)

Added field to SectionDefinition:

PYTHON
questions_by_dimension: Optional[Dict[str, DimensionQuestions]] = None

2. Loader Update (src/outline_loader.py)

Added parse_questions_by_dimension() function to parse the new YAML structure.

Updated parse_section() to:

  • Parse questions_by_dimension when present

  • Generate flat guiding_questions from dimensions for backward compatibility

3. Researcher Update (src/agents/perplexity_section_researcher.py)

Updated build_section_research_query() to format questions by dimension:

PYTHON
if section_def.questions_by_dimension:
    for dim_key, dim_q in section_def.questions_by_dimension.items():
        label = dim_q.dimension_label or dim_key.title()
        questions_text += f"\n### {label}\n"
        for q in dim_q.questions:
            questions_text += f"- {q}\n"

Also added:

  • Section description extraction

  • Group question extraction (e.g., "How big is this problem?")

  • Structure template extraction

  • Required elements extraction

  • Garbage response detection with auto-retry

4. Outline YAML Restructure

Converted sections 2, 3, 4, 6 in direct-early-stage-12Ps.yaml from:

YAML
guiding_questions:
  # Problem (P4)
  - "How many target customers exist?"
  - "How is the market experiencing this pain?"

To:

YAML
questions_by_dimension:
  problem:
    label: "Problem (P4)"
    questions:
      - "How many target customers exist?"
      - "How is the market experiencing this pain?"
  possibility:
    label: "Possibility (P5)"
    questions:
      - "What is the TAM?"
      - "What is the SAM?"

Updated all three firm copies: dark-matter, hypernova, emerge.


Results

Before (Garbage Responses)

SectionFile SizeContent
Opening87 bytes"Let me fetch the Stratosphere company website..."
Organization109 bytes"Let me fetch the company website..."
Risks132 bytesMeta-commentary asking for clarification

After (Rich Research Content)

SectionWordsCitationsContent Quality
Opening2,01114Problem/Possibility/Positioning with TAM/SAM/SOM, competitor analysis
Organization1,6668People/Process/Product with team gaps, engineering culture
Risks1,69611Structured risk analysis by dimension group

Sample Output (Opening Section)

Now includes:

  • Problem (P4): Market size $17.9B, 1.17M firefighters, CAGR projections

  • Possibility (P5): TAM $1.5-3B, SAM $60-100M, SOM $3-10M ARR

  • Positioning (P6): Competitive analysis vs Hypoxico, Mile High, Loxy

  • Scorecard table with dimension scores and rationale

  • What Could Make These Scores Higher section


Additional Fix: Brand Config Loading

Fixed BrandConfig.load() in src/branding.py to use firm name as default brand when firm is provided but brand_name isn't.

Before: Auto-detected firm dark-matter but loaded default Hypernova branding After: Auto-detected firm dark-matter and loads brand-dark-matter-config.yaml


Files Changed

FileChange
src/schemas/outline_schema.pyAdded DimensionQuestions dataclass, added fields to SectionDefinition
src/outline_loader.pyAdded parse_questions_by_dimension(), updated parse_section()
src/agents/perplexity_section_researcher.pyDimension-grouped formatting, garbage detection, retry logic
src/branding.pyFixed firm-scoped brand config loading
io/dark-matter/templates/outlines/direct-early-stage-12Ps.yamlRestructured to questions_by_dimension
io/hypernova/templates/outlines/direct-early-stage-12Ps.yamlSynced with dark-matter
io/emerge/templates/outlines/direct-early-stage-12Ps.yamlSynced with dark-matter

Impact

This change transforms the 12Ps outline from producing garbage for non-standard section names to producing high-quality, dimension-organized research that matches the framework's intent. The dimension labels (e.g., "Problem (P4)") give Perplexity clear context about what each set of questions is trying to answer.