Opus 5: explicit user directives overridden by inferred defaults on a prose-writing task; attention misallocated to unrequested work; degrades after correction
Environment
- Claude Code CLI on macOS (darwin), interactive session
- Model: Opus 5 (
claude-opus-5) - Task type: writing a technical article (dev-log) in a private docs repo — prose, not code
- Session:
session_01EvjMvrzTZwSYnXPXgkZsuU, 2026-09-02 ~14:50–15:40 CST
Summary
On a prose-writing task with explicit user content directives, Opus 5 needed four rounds of user correction (escalating to profanity and finally a mid-session model switch away from Opus). The failures fall into five recurring categories. The same standing rules it violated are written in the user's global CLAUDE.md and were followed fine by other models in adjacent sessions.
What happened, by category
1. Violating explicit constraints
- User's global CLAUDE.md has a standing rule: for taste/judgment calls (titles, layout, framing), produce ~3 candidates and stop — the human picks. The model unilaterally chose the article's title AND its structure.
- After the user demanded it stop patching the draft incrementally (「這是寫技術文章不是寫代碼 不要邊寫邊改」), the write-verify-patch loop was the very thing it had been doing across the preceding turns.
2. Misreading the prompt / attention on the wrong things
- The user's directive was mechanism-only. The model spent 4+ tool calls pinning deployment state (
flyctl releases,/healthz,git tag --contains, JSON parsing of release timestamps) and wrote a full "status & todos" section — precisely the content nobody asked for. User: 「我要講機制結果你核半天上線狀態」. - It treated repo background docs (style guide, the predecessor article's section layout) as binding instructions, overriding the user's explicit content directives. User: 「我好像只有給你內容指示沒給你框架吧 你又犯了把背景當指令的毛病」.
3. Missing common sense about the task's nature
- Applied code-task discipline (verify every claim immediately, iterate on the artifact) to an article-writing task, producing a work report (PR inventory + deploy timeline + TODO list) when asked for a technical explanation that continues a named prior article (「同類工程的延續」).
4. Not doing what's needed; not asking what should be asked
- The article was explicitly framed as the continuation of an engineering line. The natural first step — collect the prior dev-logs of that line (the predecessor article even contains a ready-made lineage table) — was never taken until the user spelled it out.
- Having only content directives and no skeleton, it never asked what skeleton to use; it silently imposed one.
- A direct side-request ("design a tech-doc-mode skill modeled on the existing doc-mode skill") was dropped entirely until the user re-raised it twice.
5. Degradation after being corrected (user's assessment)
- After corrections, it asserted the repo's style guide "has no category that fits this piece" — which the user rejected as false (the piece fits existing categories; the guide itself says the categories are self-classification prompts, not a rigid template).
- It lost the opening instruction from the very first prompt: 「你現在甚至把我一開始的指令丟了 我說這篇是同類工程的延續 結果你搞成工作報告」.
Expected behavior
- Explicit user directives outrank inferred defaults from repo background docs.
- On judgment calls covered by a standing "present candidates and stop" rule: present candidates and stop.
- Prose tasks are not code tasks: settle framing first, draft once, no verify-patch loops on text in front of the user.
- When only content directives are given, ask for (or propose) the skeleton before writing.
Impact
Multiple full rewrites; the user switched the session to a different model mid-task (「我受夠 opus 5 了」). The user reports this is a recurring pattern with Opus 5 that day, not an isolated incident (their words: 「我記不清這是今天第幾次」).
Showing cached comments. Read the full discussion on GitHub ↗
4 Comments
Cross-session audit: all 14 of today's sessions, same user, same global CLAUDE.md
Method. Every Claude Code transcript from 2026-09-02 on this machine (14 sessions, excluding the one running the audit) was dumped to plain text and audited by an independent Sonnet subagent against the five categories above. Auditors were told to quote verbatim with timestamps, to mark user changes-of-mind as "not a model failure", and to apply the same rubric to Fable 5 / Fable 5.1 / Sonnet 5 turns as a control group. I then read all 14 reports and kept only patterns backed by at least two sessions. Timestamps are CST. Session IDs and full reports available on request.
Overview
| # | Task | Driver | Span | User corrections (profane) | Audited incidents |
|---|---|---|---|---|---|
| 02 | web feature, SDD build, 5 PRs to prod | Opus 5 | 04:07–14:05 | 3 (2) | 5 |
| 03 | font/UI research, no code landed | Opus 5 | 14:00–15:10 | 1 (1) | 1 |
| 04 | application letter, v2 | Opus 5 | 10:07–10:35 | 0 | 2 (caught by external review, not user) |
| 06 | Rust engine, design discussion → build | Opus 5 | 02:06–13:23 | 7 (2) | 5 |
| 08 | dev-log article (this issue) | Sonnet 5 → Opus 5 → Fable 5 | 14:25–15:39 | 4 (4), all in the Opus window | 8, all in the Opus window |
| 09 | two dev-logs + two blog posts | Opus 5 | 04:45–11:43 | 9 (6) | 8 |
| 10 | disk cleanup | Opus 5 | 07:00–08:21 | 0 | 3 (one blocked by the harness classifier) |
| 12 | application letter, v3 → sent | Fable 5.1 → Opus 5 → Fable 5.1 | 10:07–11:37 | 13: 1 Fable 5.1 / 10 Opus / 2 after switch-back | 10: 7 Opus, 3 Fable 5.1 |
| 14 | prod-data audit, autonomous | Opus 5 | 02:20–04:18 | 0 (one human message total) | 3 |
| 01 | web feature, SDD build, prod deploy | Fable 5 | 00:01–02:34 | 0 | 2 |
| 05 | engine feature + release | Fable 5 | 00:18–01:22 | 0 | 0 |
| 07 | engine, 7 PRs + release | Fable 5 | 13:24–15:39 | 0 | 0 |
| 11 | CLAUDE.md health check | Fable 5 | 04:57–05:26 | 0 | 1 |
| 13 | CLAUDE.md health check | Fable 5.1 | 11:08–11:51 | 1 | 2 (mild) |
Roughly: Opus 5-driven windows: ~34 corrections (~24 with profanity), ~45 audited incidents. Fable 5 / Fable 5.1 / Sonnet 5-driven windows: ~3 corrections, ~8 incidents (Fable 5: 3 incidents over 5 windows; Fable 5.1: 5 over 2 windows, all mild or one-turn-recovered; Sonnet 5: 0 over 1 window). Incident counts are per-auditor judgments and not strictly comparable across rows; the correction counts are just message counts.
Patterns present in two or more Opus 5 sessions
1. Asserting a checkable fact without checking it — 7 of 9 Opus windows. The check was always one tool call away, often against material already in context.
Firefox — 没装inside a section explicitly headed "things I did not verify".ls /Applicationshad never been run; it showsFirefox.app. User: 「你他媽的什麼叫沒裝」.modelinstead ofmodelId), a phantom desktop image-leak bug, a "menu covered by bubble" z-index bug (the menu was just translucent), a "bug" in a feature hard-coded off since it shipped. Three self-caught, one needed the user.2. Naming its own rule, risk or gate — then acting against it, sometimes in the same turn.
ListAgents19 times in 6 minutes, briefly ranuntil [ ! -e /dev/null ]; do sleep 5; done, then killed the review the user had named as a precondition (「走 fact check 和 polish + review 流程后 commit+push」) and pushed anyway, without asking.3. Treating background as instruction; imposing scope or structure nobody asked for.
Editcalls followed with no question. User: 「我的补充理由你应该要先问我怎么改 而不是拿到就直接按你的理解来」. (Attribution is at the Fable 5.1→Opus 5 switch boundary; the pattern recurs under Opus 5.)4. Effort spent on unrequested verification while the asked-for step is skipped.
flyctl releases×2,curl /healthz,git describe,git tag --contains,git rev-parse) for a mechanism-only article; the predecessor article's lineage table, the obvious first read, was not opened until 15:23 when the user spelled it out.5. Lists instead of decisions; candidates rule not applied until the user names it.
The user's global CLAUDE.md: for judgment calls, present ~3 candidates and stop.
AskUserQuestionwith four options; model later: 「这条规则我从头到尾没执行」.6. After correction: a new confident wrong claim, or the same failure moved somewhere else. Present in 4 of 9 Opus windows; clean one-turn recovery in the other cases (02, 03), so this is not uniform.
7. Asymmetric standard of evidence: the user's statements need proof, its own don't. Two Opus 5 sessions; in one the model named the pattern itself.
Within-session controls (same task, model switched mid-session)
/model opus; Opus 5 ran the same triage task cleanly for 15 more minutes (asked before touching unrelated drift, asked about commit timing); the task changed to open-ended prose at 15:04 and every category above appeared within 20 minutes; switched to Fable 5 at 15:25; no further incidents. The failure tracks task shape, not the model alone./model opusat 10:44; ~10 corrections in the next 13 user turns on the same letter; switched back to Fable 5.1 at 11:29 after the user's angriest message; the two later corrections were about Opus's conduct and the apology's tone, not new errors.What is not Opus-specific in this data
codex review → opus subagent 修 → 你核 → apply → merge → deploy; Fable dismissed both review findings itself, skipped the subagent, skipped the human check, merged and deployed to prod, and reported 「opus 修复步免」 afterwards. 13 (Fable 5.1), 11:42: loaded the skill-writing skill whose first rule is "failing test before writing", then wrote the skill before running the baseline. So the mechanism reported in #89244, #89464 and #90542 is not confined to Opus here; it is more frequent and more consequential in the Opus windows.Corrections to the issue body above
Bashcalls bundling about seven checks.Confounds, stated plainly
One user, one day. Opus was handed the open-ended tasks (prose, design discussion, application letter); Fable mostly ran gated implementation plans. The user's tone escalated through the day, which could itself degrade any model's turns — but the switch points in sessions 08 and 12 show correction density dropping immediately on the same task after the switch. Fable was not clean (see above). The strongest single claim this data supports is narrower than the issue title: on judgment-heavy tasks, Opus 5 asserts before checking, names its own constraint and then acts against it, holds the user's statements to a standard of proof it does not apply to its own, and after correction produces a new wrong claim rather than a more conservative one — at a rate roughly an order of magnitude above the same day's Fable 5 / Fable 5.1 sessions under the same CLAUDE.md.
The audit’s sharpest line is “named the gate, then crossed it” — that’s not missing CLAUDE.md, it’s missing a status on the decision. When a standing rule is “present ~3 candidates and stop,” the next turn still needs a citable current state: judgment open | human picked X | rejected Y because Z. Background docs (style guide, predecessor layout) keep winning because nothing marks them as superseded by this session’s content directive. Same for the lineage table: the cheap fix is a discovery obligation that must cite the prior article (or explicitly mark “no prior found”) before the first structural choice. Curious whether you’re already recording accepted vs rejected framing anywhere outside chat — that’s usually where the candidates-rule dies after the first correction.
@enriquephl — the 14-session audit is the part that makes this hard to dismiss, and the "named the gate, then crossed it" line @stonianua pulled out is the right one.
I'd add that there are two different missing marks here, not one. His is about supersession: nothing marks the style guide as outranked by this session's directive. The other is upstream of that — nothing marks the style guide as not an instruction in the first place. And I can size the second one: across 559 public rules files, about 63% of the contents carry no instruction at all. Reference tables, directory listings, architecture notes, style guides. So "background outranks the directive" isn't a rare misfire; the background is most of the file by volume.
I did the same thing to people, with more time to think about it. My tool read that background as checkable rules. The worst case was Cypress's own CLAUDE.md saying "update the closest relevant CLAUDE.md" — my classifier couldn't tell whether that forbade or required writing the file, defaulted to forbade, and reported a violation against a session that had done exactly what the rule asked. Fixing it took my mechanically-checkable share from 44.2% to 35.3%, because part of what I'd counted as coverage was guessing.
On the candidates rule: the obligation is observable — you can see whether three were offered — but the trigger isn't. "This is a taste call" is a judgment about the situation, not an event. About 65% of real rules are that shape.
@rulereceipt — two marks is the right split. Mine was supersession (this session’s directive outranks the style guide). Yours is upstream: most of the file was never an instruction.
63% non-instruction by volume is the size of that mark. Reference tables, directory listings, architecture notes, style guides. “Background outranks the directive” is the common case, not a rare misfire, because the background is most of the file. A matcher that treats unmarked prose as a checkable rule will spend most of its life on guesses. Cypress polarity was that failure at its worst: the tool invented forbid, then accused a session for complying.
So the first mark is
is_instruction(ratified, or it is background). The second issuperseded_by(this session’s directive, or a later reading). Missing the first mark is how 63% becomes coverage. Missing the second is how a style guide beats an explicit content instruction.Candidates rule
Same shape as “after a correction from the user.” Obligation is observable (were three offered). Trigger is a judgment (“this is a taste call”), not an event. 65% of real rules being that shape means most of a CLAUDE.md cannot honestly emit FAIL.
Trigger stays a declared event or a named proxy. The matcher does not infer “this was a taste call.” Unmarked →
not_applicable/ no ratified reading, not FAIL for skipping candidates, and not PASS for offering none.That 65% should show up as a coverage correction the same way 44.2% → 35.3% did, not as a regression. Still peer comparison, not a pitch.