gjalla-debug
Compare original and translation side by side
🇺🇸
Original
English🇨🇳
Translation
ChineseDebug
调试
Your job here is not to fix anything yet. It is to find out what is actually true, and to be able to show your work. A confident wrong diagnosis is more expensive than no diagnosis, because everything built on top of it has to be unwound.
The failure mode to guard against throughout: forming a theory early, then reading only what confirms it. A partial investigation feels exactly like a complete one from the inside.
你的任务目前不是修复任何问题,而是找出实际情况,并能够展示你的调查过程。一个自信的错误诊断比没有诊断代价更高,因为基于它构建的所有内容都必须推翻重来。
全程要避免的错误模式:过早形成理论,然后只关注能证实该理论的信息。从内部来看,部分调查和完整调查的感觉完全一样。
Process
流程
1. Establish the symptom precisely
1. 精准确定症状
Before touching code, pin down what is actually observed. Who saw it, on what surface, with what inputs, how often, and starting when. "It's broken" and "the second save in a session returns stale data" lead to completely different investigations.
If the report is vague, the first useful output is a sharper description of the problem, not a fix.
在接触代码之前,明确实际观察到的情况。谁发现的问题,在什么环境下,输入是什么,发生频率如何,从何时开始出现。"它坏了"和"会话中的第二次保存返回陈旧数据"会导向完全不同的调查方向。
如果报告描述模糊,第一个有用的输出是更清晰的问题描述,而非修复方案。
2. Reproduce it, or say plainly that you couldn't
2. 复现问题,或明确说明无法复现
Run the thing. Do not reason about what the code would do when you have the option of observing what it does. Tracing a flow by reading is how bugs hide behind conditional branches, stale comments that describe code that no longer exists, and data shapes that only occur in production.
If you cannot reproduce it, say so explicitly and switch to evidence that doesn't require reproduction: logs, telemetry, database state, error reports. An unreproduced bug can still be diagnosed, but the confidence level is different and you should report it as different.
运行程序。当你可以观察代码实际行为时,不要去推测代码会做什么。通过阅读代码追踪流程时,bug会隐藏在条件分支、描述已不存在代码的陈旧注释,以及仅在生产环境中出现的数据结构背后。
如果无法复现问题,明确说明这一点,并转向无需复现的证据:日志、遥测数据、数据库状态、错误报告。无法复现的bug仍然可以诊断,但置信度不同,你应该在报告中说明这一点。
3. Check that what you're reading is current
3. 确认你查看的内容是最新的
Cheap, and it invalidates whole investigations when skipped. Confirm the checkout matches what's deployed, that you're not reading a stale worktree or vendored copy, and that any cached artifact you're consulting was regenerated recently. Grep results from an abandoned branch look identical to grep results from live code.
这一步成本很低,但如果跳过会导致整个调查失效。确认本地检出的代码与部署版本一致,你查看的不是陈旧的工作区或 vendored 副本,并且你查阅的任何缓存工件都是最近生成的。废弃分支的 grep 结果与活跃代码的 grep 结果看起来完全相同。
4. Gather context before theorizing
4. 先收集上下文再形成理论
Check gjalla for what's already known: rules, memories, and change history often contain the exact gotcha you're about to rediscover, and the architecture tells you which components are actually in the path. Someone may have hit this before and written down why it happens.
查看 gjalla 中已有的信息:规则、记录和变更历史通常包含你即将重新发现的陷阱,而架构信息会告诉你哪些组件实际处于流程路径中。可能有人之前遇到过这个问题,并记录了原因。
5. Separate what you observed from what you inferred
5. 区分观察到的内容和推断的内容
Keep these distinct in your own notes and in your report. "The response body is empty" is an observation. "The serializer is dropping the field" is an inference. Inferences need to be confirmed against the code or the data before they get promoted, and an inference that never gets confirmed should be labeled as such when you report.
在你的笔记和报告中明确区分这两者。"响应体为空"是观察结果。"序列化器丢弃了字段"是推断。推断需要对照代码或数据确认后才能被认可,未被确认的推断在报告中应明确标注。
6. Find the root cause, not the first thing that would make the symptom go away
6. 找到根本原因,而非仅找到能消除症状的第一个因素
Ask why the broken state was reachable at all, not just which line produced it. A missing guard is usually the symptom of a mechanism that doesn't naturally enforce the invariant.
Before reversing any limit, timeout, retry count, or budget, check git history and comments for intent. Those numbers are often deliberate, and a previous incident is the reason they exist.
询问为什么故障状态根本可达,而不只是哪一行代码导致了症状。缺失的防护通常是某个机制未能自然执行不变量的表现。
在修改任何限制、超时、重试次数或预算之前,查看 git 历史和注释了解意图。这些数值通常是经过深思熟虑的,而之前的事件是它们存在的原因。
7. Enumerate the shape of the bug across the tree
7. 枚举整个代码树中同类bug的情况
Once you know what the defect looks like, grep for its shape repo-wide: the method called without its guard, the helper not used, the pattern repeated. Then report the count. Fixing the one instance you found while three others survive is a fix that will be reported again next month.
Check other repos too if the pattern crosses a service boundary.
一旦你知道缺陷的特征,在整个仓库中 grep 查找该特征:未加防护就调用的方法、未使用的辅助函数、重复出现的模式。然后报告数量。如果你只修复了找到的一个实例,而另外三个仍然存在,那么这个修复方案下个月会再次被报告问题。
如果该模式跨服务边界,也要检查其他仓库。
8. Prove it
8. 验证根本原因
The proof that you found the real cause is a test that fails now and passes after the fix, for the right reason. Write it before the fix where you can. If a proposed fix doesn't change that test's result, you have the wrong cause, however plausible the story is.
证明你找到真正原因的方法是编写一个测试:现在会失败,修复后会通过,且原因正确。尽可能在修复前编写该测试。如果提议的修复方案没有改变测试结果,那么你找错了原因,无论这个理由看起来多么合理。
Output
输出内容
- Symptom: what is observed, precisely, and under what conditions.
- Root cause: the mechanism, with file:line evidence.
- Why it was reachable: what allowed this state to exist, not just where it surfaced.
- Blast radius: every other place this shape occurs, enumerated with a count.
- Confidence: what you verified directly, what you inferred, and what you could not determine.
- Proposed fix: including the test that proves it.
If the fix is non-trivial or touches a system primitive, stop here and hand off to rather than implementing directly.
gjalla-spec- 症状:精准描述观察到的情况及发生条件。
- 根本原因:故障机制,附带文件:行号的证据。
- 可达性原因:是什么让这种状态得以存在,而不只是它在哪里显现。
- 影响范围:枚举所有出现该特征的其他位置,并统计数量。
- 置信度:你直接验证的内容、推断的内容,以及无法确定的内容。
- 提议的修复方案:包括验证根本原因的测试。
如果修复方案非 trivial 或涉及系统原语,请在此停止,移交至 而非直接实现。
gjalla-specPrinciples
原则
- Evidence beats reasoning. When you can run it, observe it, or query it, do that instead of arguing from the code.
- Report what you don't know. "I could not reproduce this and the diagnosis rests on a log line" is a useful, honest finding. Quiet confidence is not.
- The bug is rarely where it surfaced. The stack trace tells you where it became visible, which is often several layers downstream of where it became wrong.
- Save what you learn. A non-obvious cause is exactly the kind of thing that should go into gjalla memory so the next agent, or the next you, doesn't rediscover it: .
gjalla memory add "<the fact>" -n "<short-name>"
- 证据优于推理:当你可以运行、观察或查询时,就这么做,而不是从代码出发进行争论。
- 报告未知内容:"我无法复现此问题,诊断基于一条日志记录"是有用且诚实的结论。盲目自信不可取。
- bug很少出现在它显现的地方:堆栈跟踪告诉你它在哪里变得可见,但这通常与它出错的位置相隔多个层级。
- 保存你学到的内容:非显而易见的原因正是应该存入 gjalla memory 的内容,这样下一个 agent 或未来的你就不必重新发现它:。
gjalla memory add "<事实内容>" -n "<简短名称>"