---
phase: quick-260520-uc2
plan: 01
status: complete
subsystem: owl/version_changelog + docs/DEPLOY
tags: [changelog, version-change, auq, ux-language, bts-filter]
requires: []
provides:
  - Canonical `### BTS` section name for behind-the-scenes CHANGELOG content
  - DEPLOY.md bucket-discipline contract for stub fill-in
  - BTS-omit directive in both resolved-branch AUQ options
affects:
  - docs/DEPLOY.md
  - src/owl/version_changelog.rs (build_block_reason resolved branch + inline test)
  - tests/version_changelog.rs (block_reason_matches_reference_invariants invariants)
tech-stack:
  added: []
  patterns:
    - "Raw-string delimiter escalation (r# -> r####) when embedded sequences contain `\"#` / `\"###`"
key-files:
  created: []
  modified:
    - docs/DEPLOY.md
    - src/owl/version_changelog.rs
    - tests/version_changelog.rs
decisions:
  - Keep all K-a-C 1.1.0 categories; add `### BTS` as a sibling section (not a category replacement)
  - Migration policy: legacy entries left as-is; filter is no-op on entries without `### BTS`
  - Force-level: imperative ALL-CAPS verb anchors (`OMIT`, `Do NOT draw from`) match the existing DEGRADED-branch wording pattern
metrics:
  duration: ~15 min
  completed: 2026-05-20
  tasks: 3
  files_modified: 3
  commits: 3
---

# Quick Task 260520-uc2: Limit Changelog to UX Language — Summary

One-liner: Introduced canonical `### BTS` sibling section in CHANGELOG vocabulary and added an OMIT/Do-NOT-draw-from directive in the version-change AUQ resolved-branch instructions so behind-the-scenes content never surfaces to the user.

## What Was Built

1. **docs/DEPLOY.md** gained a `### Bucket discipline for stub fill-in (quick-260520-uc2)` subsection between the existing "Two-phase changelog authoring" block and `### Parameters`. The subsection teaches the deploying agent:
   - Section vocabulary table covering all 8 buckets (Added / Changed / Fixed / Removed / Deprecated / Security / Reverted / BTS) with surfaced-to-user column.
   - UX-language rule for the 7 surfaced buckets (phrase as what the user sees/does/runs; forbid code-path / fn-name / struct-name / commit-SHA / planning-doc references; one-sentence target).
   - BTS rule listing repo-management changes, deploy-sequence tweaks, code reverts the user never saw, doc-string drift, test-only changes, internal refactors, naming/signature changes.
   - "Would a user typing `/spt:live` notice the difference?" heuristic.
   - Worked examples reframing real v1.10.20 / v1.10.18 / v1.10.17 bullets.
   - Backward-compat note: pre-v1.10.21 entries untouched, filter is a no-op on them.

2. **src/owl/version_changelog.rs::build_block_reason resolved branch** updated:
   - Option 1 (`Yes, full changelog`): now preserves the user-facing H3 subsections (Added / Changed / Fixed / Removed / Deprecated / Security / Reverted) verbatim and OMITs any `### BTS` subsection entirely. Bare-H2 fallback added for the BTS-only-version edge case.
   - Option 2 (`Yes, highlights only`): now draws ONLY from the 7 user-facing subsections and is explicitly forbidden to draw from `### BTS`.
   - Option 3 (`Skip`), the AskUserQuestion preamble, the "Other" continuation-phrase rule, and the multi-version rendering rule are UNCHANGED.
   - DEGRADED branch UNTOUCHED (REVIEW-FIX #9 invariant preserved).
   - Inline test `build_block_reason_single_step_resolved_branch_substitutes_correctly` updated: stale `Pick 2-5 most impactful` assertion removed, replaced with stronger `Do NOT draw from` + `### BTS` invariants.

3. **tests/version_changelog.rs::block_reason_matches_reference_invariants** invariants array gained `"### BTS"` and `"behind-the-scenes"` entries, locking the canonical section spelling and the discriminator phrase.

## Tasks Executed

| Task | Type | Files | Commit |
|------|------|-------|--------|
| 1: Add bucket-discipline subsection to DEPLOY.md | docs | docs/DEPLOY.md | bde5516 |
| 2: Update resolved-branch AUQ wording + inline test | feat | src/owl/version_changelog.rs | 4e2a7e8 |
| 3: Pin BTS-filter invariants in integration test | test | tests/version_changelog.rs | 6ad4f40 |

## Verification

- `cargo test --lib version_changelog`: **46 passed, 0 failed, 1 ignored** (the `print_canonical_block_reason_for_reference` regeneration helper, intentionally `#[ignore]`).
- `cargo test --test version_changelog`: **16 passed, 0 failed** — including the integration test `block_reason_matches_reference_invariants` with the new BTS invariants.
- DEGRADED-branch invariant preserved: `build_block_reason_unresolved_branch_does_not_instruct_read_for_yes_options` still passes (REVIEW-FIX #9).
- Canonical `### BTS` spelling case-sensitive count across the three modified files: **13** (plan expected >= 5).
- Variant-spelling hit count (case-sensitive `### bts`, `### Behind the Scenes`, `### Internal`): **0**.

## Deviations from Plan

### Auto-fixed Issues

**1. [Rule 1 - Bug] Escalated raw-string delimiter from `r#"..."#` to `r####"..."####`**
- **Found during:** Task 2 build after applying the new Option 1 / Option 2 wording.
- **Issue:** The original resolved-branch `format!` body uses an `r#"..."#` (single-hash) raw string. The new wording embeds the literal sequence `"### BTS"` (and similar `"### Added"`, `"### Changed"`, etc.) inside the body. Rust's lexer terminates an `r#"..."#` raw string at the first `"#`, which is the `"` followed by `#` inside `"### BTS"`. Result: 13 compile errors ("unknown prefix `BTS`", "expected `,`, found `#`", etc.).
- **Fix:** Escalated the delimiter to `r####"..."####` (quad-hash). The body contains no `"####` sequence (max embedded run is `"###`), so quad-hash is safe. Added a 5-line `// NOTE:` comment above the `format!` call documenting why the delimiter is non-default — future editors who add more `### Foo` references will see why touching the delimiter is significant.
- **Files modified:** `src/owl/version_changelog.rs` (delimiter + comment).
- **Commit:** 4e2a7e8 (rolled into the Task 2 commit — the wording change and the delimiter fix are inseparable: the wording cannot compile without the delimiter escalation).
- **Rule classification:** Rule 1 (correctness bug — the code didn't compile). Note: this is auto-fixable per the in-scope rule because the bug was DIRECTLY caused by the task's wording change.

## Key Decisions

- **K-a-C category preservation:** Kept all seven K-a-C 1.1.0 user-facing categories (Added / Changed / Fixed / Removed / Deprecated / Security / Reverted) untouched. `### BTS` is a sibling, not a replacement. This preserves the existing DEPLOY.md authoring contract and the semantic distinction between `### Fixed` and `### Reverted` that v1.10.20's entry currently leverages.
- **Migration:** Legacy CHANGELOG entries (pre-v1.10.21) left as-is per RESEARCH Q5. The filter is a no-op on entries without a `### BTS` section, so the full-changelog path surfaces them verbatim — same as today.
- **Directive force-level:** Imperative ALL-CAPS verb anchors (`OMIT`, `Do NOT draw from`) match the existing pattern used in the DEGRADED branch (`Do NOT attempt to read`), which has performed reliably downstream.
- **Section-name spelling:** `### BTS` (all-caps) is canonical and case-sensitive. All three modified files use this exact spelling; variant spellings (`### bts`, `### Behind the Scenes`, `### Internal`) confirmed zero across the touch surface.
- **Raw-string delimiter:** Quad-hash (`r####"..."####`) chosen over triple-hash because the body's max `"<#>` run is three (e.g., `"###` inside `"### BTS"`); triple-hash would terminate on `"###`. Quad-hash terminates only on `"####`, which never appears.

## Known Stubs

None.

## Threat Flags

None — pure prose / directive-text change; no new network endpoints, auth paths, file access patterns, or schema changes.

## Self-Check

- **DEPLOY.md subsection:** FOUND (1 hit for the exact header `### Bucket discipline for stub fill-in`).
- **src/owl/version_changelog.rs::build_block_reason resolved branch:** FOUND (option 1 contains `OMIT any "### BTS"`; option 2 contains `Do NOT draw from "### BTS"`).
- **tests/version_changelog.rs invariants:** FOUND (`"### BTS"` and `"behind-the-scenes"` present in the array).
- **Commits:** all three commits present in `git log --oneline` (bde5516, 4e2a7e8, 6ad4f40).
- **Tests:** lib `version_changelog` 46/46 pass; integration `version_changelog` 16/16 pass.
- **DEGRADED branch invariant:** preserved (no change to the `else` branch of `build_block_reason`).

## Self-Check: PASSED
