{"record":{"id":"42d1c183d15498f0","repo":"gastownhall/beads","slug":"standalone-expansion-q-w","errorCode":null,"errorMessage":"standalone expansion %q: %w","messagePattern":"standalone expansion %q: %w","errorType":"console","errorClass":null,"httpStatus":null,"severity":"error","filePath":"cmd/bd/cook.go","lineNumber":815,"sourceCode":"\n\t// Handle standalone expansion formulas (bd-qzb).\n\t// Expansion formulas store content in Template, not Steps. Materialize\n\t// the template into Steps using a synthetic \"main\" target so the normal\n\t// cooking pipeline can process them.\n\tif resolved.Type == formula.TypeExpansion && len(resolved.Template) > 0 {\n\t\texpansionVars := make(map[string]string)\n\t\tfor name, def := range resolved.Vars {\n\t\t\tif def != nil && def.Default != nil {\n\t\t\t\texpansionVars[name] = *def.Default\n\t\t\t}\n\t\t}\n\t\tif conditionVars != nil {\n\t\t\tfor k, v := range conditionVars {\n\t\t\t\texpansionVars[k] = v\n\t\t\t}\n\t\t}\n\t\tif err := formula.MaterializeExpansion(resolved, \"main\", expansionVars); err != nil {\n\t\t\treturn nil, fmt.Errorf(\"standalone expansion %q: %w\", formulaName, err)\n\t\t}\n\t}\n\n\t// Cook to in-memory subgraph, including variable definitions for default handling\n\treturn cookFormulaToSubgraphWithVars(resolved, resolved.Formula, resolved.Vars)\n}\n\n// cookFormulaToSubgraphWithVars creates an in-memory subgraph with variable info attached\nfunc cookFormulaToSubgraphWithVars(f *formula.Formula, protoID string, vars map[string]*formula.VarDef) (*TemplateSubgraph, error) {\n\tsubgraph, err := cookFormulaToSubgraph(f, protoID)\n\tif err != nil {\n\t\treturn nil, err\n\t}\n\t// Attach variable definitions to the subgraph for default handling during pour\n\t// Convert from *VarDef to VarDef for simpler handling\n\tif vars != nil {\n\t\tsubgraph.VarDefs = make(map[string]formula.VarDef)\n\t\tfor k, v := range vars {","sourceCodeStart":797,"sourceCodeEnd":833,"githubUrl":"https://github.com/gastownhall/beads/blob/71377f276968b452ee607177637970a4ff888584/cmd/bd/cook.go#L797-L833","documentation":"Thrown when formula.MaterializeExpansion fails to materialize a standalone expansion formula (bd-qzb). Standalone expansions keep content in Template rather than Steps; before cooking, the template is materialized into cookable steps using expansionVars (formula vars merged with conditionVars). Failure here aborts the cook.","triggerScenarios":"Cooking a formula of type expansion: MaterializeExpansion errors because the template is invalid/empty, variable substitution fails (missing required var, malformed placeholder), or the target ID wiring cannot be produced from the template.","commonSituations":"Invocation omits a variable the expansion template requires (bd pour with insufficient --var flags); expansion template edited with a bad placeholder like {{varName without closing braces}; expansion formula's template references another formula unavailable at materialize time.","solutions":["Read the wrapped cause; fix the template placeholder or supply the missing variable","Pass all required variables at invocation (bd pour --var key=value) or set defaults in the formula's vars section","Validate the expansion template syntax (balanced {{ }} placeholders)","Confirm the formula's type is expansion and its Template field is non-empty","Test materialization via verifyFormula before running the real cook/pour"],"exampleFix":"# before\nbd pour my-expansion   # template needs $TARGET, not provided\n# after\nbd pour my-expansion --var TARGET=svc-api","handlingStrategy":"validation","validationCode":"// Before pour/cook, ensure all template placeholders have values\nrequired := expansionTemplateVars(f.Template) // extract {{ var }} names\nfor _, v := range required {\n    if _, ok := expansionVars[v]; !ok {\n        return fmt.Errorf(\"expansion requires variable %q\", v)\n    }\n}","typeGuard":null,"tryCatchPattern":"if err := runPour(); err != nil && strings.Contains(err.Error(), \"standalone expansion\") {\n    var missing = extractFromCause(err) // e.g. missing var name\n    log.Printf(\"expansion materialization failed: %v — pass --var %s=...\", err, missing)\n}","preventionTips":["Always pass --var for every placeholder the expansion template uses","Keep expansion templates' {{ }} placeholders balanced and named","Set defaults in the formula's vars section for optional placeholders","Verify expansion formulas with bd verify before invoking via pour"],"tags":["formula","expansion","template"],"backgroundTag":"template-variable-missing","analyzedSha":"71377f276968b452ee607177637970a4ff888584","analyzedAt":"2026-08-30T18:55:39.744Z","schemaVersion":2},"datasetVersion":"2026-08-30T23:17:21.991Z"}