| name | cross-agent-safety |
| description | Safety checks before modifying shared bot services. Verify imports, check downstream consumers, run the suite. Use when editing anything in bot/shared/services/ or bot/workers/ — files many features depend on. |
| paths | bot/shared/services/**,bot/workers/** |
| user-invocable | false |
Cross-Agent Safety Skill
Up: .claude/CLAUDE.md (config & skills router) · See also: coaching, pre-merge-checklist
A checklist for editing shared code — services and workers that many features import. A careless change
to one of these crashes features far from the file you touched. Run these before you push.
MANDATORY steps before modifying anything in bot/shared/services/
1. Verify ALL imports
If you add a function call (e.g. logEvent()), confirm its import exists at the top of the file:
grep -n "logEvent" path/to/file.js
2. Check downstream consumers BEFORE renaming or removing
grep -rn "methodName" bot/shared/ bot/workers/ --include="*.js"
Count the call sites; update all of them, not just the definition.
3. Run the test suite BEFORE and AFTER
npm test
This catches ReferenceError / TypeError from a missing import. Run it before every push.
4. Verify column names before using them in queries
The users table uses phone_number (not phone) and first_name (not name). Always confirm a column
exists before referencing it in .select() / .update().
5. Don't chain .update().eq().in().select().single()
A chained Supabase update with multiple WHERE conditions + .select().single() can return
{ data: null, error: null } even when the WHERE matches a row — silently swallowing constraint violations.
Split it (fetch → JS-check → plain update → check error). Full pattern + the failure modes it hides:
pre-merge-checklist/reference/db-mutation-safety.md.
Apply when: any UPDATE with two or more WHERE conditions beyond eq('id', ...), or where the new value
is enum-like (status, kind, type).
High-blast-radius files
Never bundle critical-path and best-effort DB writes
If one column in an atomic update doesn't exist (or violates a constraint), the entire update fails —
taking the critical write down with the best-effort one.
await supabase.from('t').update({ sent_at: new Date(), best_effort_col: x }).eq('id', id);
await supabase.from('t').update({ sent_at: new Date() }).eq('id', id);
await supabase.from('t').update({ best_effort_col: x }).eq('id', id);
Pre-push checklist
npm test
grep -rn "functionYouChanged" bot/shared/ bot/workers/ --include="*.js"
Related Skills