docs+heartbeat: paperclip quirks + temp-file pattern + self-recovery
All checks were successful
Build & Deploy / build-and-deploy (push) Successful in 7s

Two latent issues surfaced today while watching the case 8174-24
end-to-end run, both worth documenting and engineering around because
they will recur on every future case.

Bug 1 — issue.released flips done→todo
  After an agent successfully PATCHes its issue to "done", Paperclip's
  internal issue.released action reverts the status to "todo" within
  ~30 seconds. This triggers a fresh wakeup of the same agent on a
  task that is already complete.
  Reproduced on CMPA-18 (30/04/26):
      18:14:57  agent PATCH → status: done
      18:15:35  Paperclip   → issue.released → status: todo
      18:15:54  new researcher run started
  The fix at the right altitude (Paperclip itself) is outside our repo.
  Mitigation in HEARTBEAT.md §3 — when an agent boots and finds the
  issue in `todo` while expected outputs (file, DB rows) already exist,
  it must short-circuit: post a "no change" comment, PATCH back to done,
  and exit. Costs ~$0.20 per false wakeup but breaks the loop.

Bug 2 — Bash backtick trap on long comment bodies
  Researcher agent built a curl pipeline like:
      curl ... -d "$(python3 -c "body = '''...
        📁 קובץ מחקר: `/path/to/file.md`
        '''")"
  The backticks around the file path (markdown convention) get
  evaluated by the OUTER bash $(...) as command substitution. Bash
  then tries to exec /path/to/file.md, which is not executable, and
  prints "Permission denied" — a misleading error since the actual
  file ownership is fine. The curl itself succeeded; only the bash
  prelude noised up the log.
  Fix in HEARTBEAT.md §4א: long bodies must go via Write→tempfile
  then `curl -d @file`. Avoids every shell quoting edge case.

Files:
  • docs/paperclip-quirks.md — new. Full writeup of both bugs plus
    two prior known-quirks (CEO auto-block in_progress, INSERT vs
    API for wakeups). Each section: what happens, empirical evidence
    from logs, impact, workaround, status.
  • .claude/agents/HEARTBEAT.md — added the self-recovery section to
    §3 and the temp-file pattern to §4א. The temp-file pattern is the
    canonical answer for any agent posting markdown comments —
    applies to all 7 agents in this skill set.
  • CLAUDE.md — referenced the new doc from the docs index.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-04-30 18:23:32 +00:00
parent fa70944ed4
commit 6a38789379
3 changed files with 195 additions and 0 deletions

View File

@@ -85,11 +85,30 @@ curl -s -X POST -H "Authorization: Bearer $PAPERCLIP_API_KEY" \
- עבוד על המשימה לפי ההוראות ב-AGENTS.md שלך
- השתמש בכלים המשפטיים (legal-ai MCP)
### ⚠️ self-recovery — issue ב-`todo` עם תוצרים קיימים
ל-Paperclip יש באג ידוע: לאחר ש-issue מתעדכן ל-`done`, מנגנון `issue.released` מחזיר אותו ל-`todo` תוך כ-30 שניות (תועד ב-`docs/paperclip-quirks.md §1`). זה גורם ל-wakeup חוזר של אותו סוכן על משימה שכבר בוצעה.
**לפני שאתה מתחיל עבודה — בדוק שהמשימה לא בוצעה כבר**:
1. **בדוק תוצרים בדיסק**: `Glob` על תיקיות ה-output הצפויות (`{case_dir}/documents/research/*.md` לחוקר, `analysis-and-research.md` למנתח, וכו')
2. **בדוק תוצרים ב-DB**: דרך MCP — `precedent_list`, `get_claims`, `extract_appraiser_facts` (status=completed)
3. **בדוק comments קודמים על ה-issue** — אם הסוכן הקודם פרסם "הושלם בהצלחה" מסוף-מצב
**אם הכל קיים ותקין**: אל תבצע עבודה כפולה. במקום זאת:
- פרסם comment קצר: "אין שינוי — כל התוצרים קיימים מהריצה הקודמת (X פריטים ב-DB, קובץ Y בדיסק). סוגר את ה-issue."
- `PATCH /api/issues/{id}``done`
- צא נקי
**אם משהו חסר/שונה**: עבוד על מה שחסר בלבד, לא על הכל מחדש.
## 4. דיווח — חובה!
**לפני שאתה מסיים, תמיד:**
### 4א. פרסם comment על ה-issue
**ל-body קצר (<500 תווים, בלי backticks/קוד/נתיבים):**
```bash
curl -s -X POST -H "Authorization: Bearer $PAPERCLIP_API_KEY" \
-H "Content-Type: application/json" \
@@ -97,6 +116,24 @@ curl -s -X POST -H "Authorization: Bearer $PAPERCLIP_API_KEY" \
-d '{"body": "סיכום העבודה..."}'
```
**ל-body ארוך / markdown עם נתיבים בbacktick / קוד — חובה שתי פעולות נפרדות:**
1. כתוב את ה-JSON לקובץ זמני דרך **Write tool** (לא דרך bash heredoc):
```
Write(file_path="/tmp/comment-{issue-id}.json",
content=json.dumps({"body": markdown_body}, ensure_ascii=False))
```
2. אז `curl -d @file` שקורא את הקובץ ישירות — בלי shell expansion:
```bash
curl -s -X POST -H "Authorization: Bearer $PAPERCLIP_API_KEY" \
-H "Content-Type: application/json" \
"$PAPERCLIP_API_URL/api/issues/{issue-id}/comments" \
-d @/tmp/comment-{issue-id}.json
```
**⚠️ למה לא bash heredoc / `python3 -c`:** backticks ב-markdown (`` `path/to/file` ``) ייפרשו על ידי bash כ-command substitution גם כשהם בתוך מחרוזת Python. תקבל שגיאת `Permission denied` מטעה (`bash` מנסה להריץ את הנתיב כפקודה). הפתרון של temp-file חוסם את כל ה-shell quoting traps. תועד ב-`docs/paperclip-quirks.md §2`.
### 4ב. קבע סטטוס — done או blocked
**אם המשימה הושלמה בהצלחה** (כל המסמכים חולצו, כל הבדיקות עברו, אין חסימות):