When the bug is slippery, stop guessing and build observability.
This skill is for situations where:
- the visible symptom is known, but the actual failure layer is not
- static code reading is no longer enough
- one execution with good logs can collapse a large search space
The workflow is simple:
- decide where to instrument
- add high-signal logs
- have the user rerun the scenario
- analyze the returned logs
- only then propose or implement the real fix
First move
Use the log prefix supplied by the user or established by the repository. If neither exists, choose a short, searchable prefix that is unique in the current codebase and tell the user which prefix to collect. This routine choice does not need confirmation.
Ask only when the user's requirements or repository logging conventions leave a material ambiguity that cannot be resolved by inspection.
Logging strategy
Do not scatter random prints everywhere. Instrument the execution path deliberately.
Choose logs around:
- entry points where the user action first enters the system
- state transitions where data changes shape
- serialization or conversion boundaries
- async handoff points
- final outbound effects such as send, save, render, request, or callback
For each log, include enough structure to reconstruct the flow:
- the shared prefix
- a timestamp
- a short tag for the subsystem or phase
- the minimum fields needed to compare expected vs actual behavior
Treat the timestamp as part of the standard format, not a nice-to-have. For tricky bugs, ordering is often as important as values.
Prefer logs that answer:
- Did this code path run?
- In what order did the steps happen?
- What data existed at this point?
- Where did duplication, loss, mutation, or branching first appear?
Avoid:
- giant object dumps unless they are truly needed
- vague messages like "here" or "called"
- logging so much that the signal disappears
What to log
The exact fields depend on the bug, but in general log:
- identifiers
- counts
- ranges or indexes
- booleans for state
- input and output summaries
- boundary transformations
Examples:
count=4state=editingrange={loc=12,len=3}contentList=[0] mention | [1] textrequestID=...
Prefer a consistent line shape such as:
[<PREFIX>][2026-03-28T13:45:27.870+08:00][Serializer] contentList=[0] mention | [1] text
When strings are important, escape newlines so one logical log stays on one physical line.
Handoff to the user
After instrumenting, tell the user exactly what to do next:
- rebuild or rerun the app/program
- reproduce the issue once
- collect the logs containing the chosen prefix
- send those logs back
Be explicit that they should return only the lines with the prefix when possible.
Recommend a filter like:
rg "\\[<PREFIX>\\]" <log-file>
or an equivalent grep/search flow in their environment.
Analysis pass
When the user sends logs back, do not jump straight to a fix. Reconstruct the path first.
Read the logs in order and answer:
- What is the first confirmed event?
- What state is proven correct?
- What is the first line where reality diverges from expectation?
- Which layer owns that divergence?
- Is the bug caused by duplication, missing data, wrong boundary detection, stale state, or ordering/race?
Call out the precise transition where the bug begins, not just where it becomes visible.
If the logs prove the current instrumentation is insufficient, ask for one more round and specify the next smallest set of logs needed. Do not ask for a broad second pass if one or two extra logs will do.
Output expectations
Your response after log analysis should be crisp and causal:
- what the logs prove
- where the root cause starts
- what is not the root cause
- what code should change next
If proposing a fix, tie it directly to the observed divergence in logs.
Scope
Keep this skill general. It applies to:
- app bugs
- backend handlers
- UI flows
- serialization problems
- async ordering issues
- duplicated side effects
- state machine bugs
It is not tied to any single language, framework, or repository.
Practical rule
The user runs the instrumented build. You analyze the prefixed logs.
That division of labor is the whole point of this skill.