Files
claudetools/.claude/standards/syncro/comment-dedup.md
Mike Swanson dd0ef45645 feat: implement agent-os standards system and feature planning tools
- Split CODING_GUIDELINES.md into 19 indexed standards files under .claude/standards/
  - 9 from CODING_GUIDELINES (conventions, powershell, security, api, git, gururmm)
  - 10 from session log tribal knowledge (syncro, ssh, gitea, python, client, gururmm)
- Add .claude/standards/index.yml for cheap relevance-based lookup
- Add /inject-standards command: load targeted standards per task instead of full guidelines
- Add /shape-spec command: pre-implementation spec for GuruRMM features (plan.md,
  shape.md, references.md, standards.md) with mandatory out-of-scope gate
- Add docs/tech-stack.md and docs/mission.md for ClaudeTools API
- Add projects/msp-tools/guru-rmm/docs/tech-stack.md and mission.md for GuruRMM
- Update CLAUDE.md commands table with /inject-standards and /shape-spec

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-16 12:59:49 -07:00

2.7 KiB

name, description, applies-to
name description applies-to
comment-dedup Never retry POST /comment without first GET /tickets/{id} to confirm it didn't land; always use heredoc payloads syncro, all

Syncro Comment Deduplication

The rule

Never retry a POST /comment call without first doing a GET /tickets/{id} to confirm the first attempt did not land.

Syncro has no DELETE endpoint for comments. A duplicate comment cannot be removed via the API — only manually through the Syncro GUI by an admin. Duplicate comments are visible to clients (public comments) and to all technicians (hidden comments), and the content cannot be redacted without deleting the entire comment.

Incident that established this rule

2026-05-01: A comment with completely wrong content ("Karen Rossini" and the ALDOCS Cascades share) was posted to a Sombra Residential ticket. Root cause: a /tmp path mismatch on Windows caused curl to read a stale payload from a previous session rather than the newly written one. The wrong comment could not be deleted via API — Howard had to manually delete it through the Syncro GUI.

Required pattern

Before retrying any failed comment POST:

# Check if the comment landed before retrying
curl -s "https://computerguru.syncromsp.com/api/v1/tickets/${TICKET_ID}?api_key=${API_KEY}" \
  | jq '.ticket.comments[-1]'

If the comment is there, do not retry. If it is missing, diagnose why before retrying (network failure, wrong API key, wrong ticket ID).

Payload pattern — use heredocs, not temp files

Do not write comment payloads to /tmp/ files and read them back with curl. On Windows, /tmp resolves differently in Git Bash vs. the Claude Code Write tool, causing stale-file reads.

Correct — heredoc piped directly to curl:

curl -s -X POST "${BASE}/tickets/${TICKET_ID}/comment?api_key=${API_KEY}" \
  -H "Content-Type: application/json" \
  --data-binary @- <<'JSON'
{"subject": "Resolution", "body": "...", "hidden": false, "do_not_email": false}
JSON

Use <<'JSON' (single-quoted, literal) for static payloads. Use <<JSON (double-quoted, interpolating) when the payload includes shell variables like ${TIMER_ID}.

Wrong — temp file approach (prone to path mismatch):

# Write tool writes to C:\tmp\, Git Bash reads from %LOCALAPPDATA%\Temp\
# These are different directories on Windows
cat > /tmp/comment.json << 'EOF'
{"subject": "Resolution", ...}
EOF
curl ... -d @/tmp/comment.json  # May read wrong file

Applies also to

All Syncro POST endpoints, not just comments. Timer entries, line items, and invoices all have the same no-retry-without-check rule since duplicates are visible and often cannot be deleted via API.