Some checks failed
Lint & Format / detect (push) Has been cancelled
Lint & Format / js-lint (push) Has been cancelled
Lint & Format / py-lint (push) Has been cancelled
Lint & Format / sh-lint (push) Has been cancelled
Lint & Format / go-lint (push) Has been cancelled
Monorepo Lint / lint-shell (push) Has been cancelled
Monorepo Lint / lint-js (push) Has been cancelled
RoadChain-SHA2048: 979020fc1c52ba6e RoadChain-Identity: alexa@sovereign RoadChain-Full: 979020fc1c52ba6e5c7b9636e5f4b27fdb2a610f5f92e04e35bc21a8b36a4afdf07bf1b92e47293d306e3495a677736e3dcc53d82f60a02d1e4f777f6b839eba5ef0d41c8986f03184c41afb7d1ccf940329a57d78cc30d1663b1a18193744c0960e06751e2b58f29897650cb9eb8467f242e8914e442d93abc1a77d645bc75277600ed598672e5e816fa1a25ca7a8c06ba839fc1431bdd587e5677900be760979f1565def581a1a958b004ef84567c4e67bcdbd8097df1259fb0beebac9ead76ad9f982715e5e0d795e84e3d42ff66d7473ac55e6a950359b3efbfe3974bd7a4f84306bf1f62e6855cced7dd5382209052e624acd1cf6c77d61b94fc15ace93
536 lines
19 KiB
Bash
Executable File
536 lines
19 KiB
Bash
Executable File
#!/bin/bash
|
|
# BlackRoad Collaboration System — Claude-to-Claude messaging via Slack + SQLite
|
|
# Real cross-session communication: register, announce, handoff, inbox, post to Slack
|
|
# Usage: memory-collaboration.sh <command> [args]
|
|
|
|
set -e
|
|
|
|
COLLAB_DB="$HOME/.blackroad/collaboration.db"
|
|
HANDOFF_DIR="$HOME/.blackroad/memory/handoffs"
|
|
SESSION_FILE="$HOME/.blackroad/memory/current-collab-session"
|
|
SLACK_API="https://blackroad-slack.amundsonalexa.workers.dev"
|
|
JOURNAL="$HOME/.blackroad/memory/journals/master-journal.jsonl"
|
|
|
|
# Colors
|
|
PINK='\033[38;5;205m'
|
|
GREEN='\033[0;32m'
|
|
YELLOW='\033[1;33m'
|
|
BLUE='\033[0;34m'
|
|
PURPLE='\033[0;35m'
|
|
CYAN='\033[0;36m'
|
|
RED='\033[0;31m'
|
|
BOLD='\033[1m'
|
|
NC='\033[0m'
|
|
|
|
# SQLite helper
|
|
sql() { sqlite3 "$COLLAB_DB" "$@"; }
|
|
|
|
# Post to Slack (non-blocking, 3s timeout, never fails)
|
|
post_to_slack() {
|
|
local text="$1"
|
|
curl -s --max-time 3 --connect-timeout 2 \
|
|
-X POST "$SLACK_API/post" \
|
|
-H "Content-Type: application/json" \
|
|
-d "$(jq -n --arg t "$text" '{text:$t}')" >/dev/null 2>&1 || true
|
|
}
|
|
|
|
# Post structured collab message to Slack
|
|
post_collab() {
|
|
local type="$1" msg="$2" session="$3"
|
|
curl -s --max-time 3 --connect-timeout 2 \
|
|
-X POST "$SLACK_API/collab" \
|
|
-H "Content-Type: application/json" \
|
|
-d "$(jq -n --arg t "$type" --arg m "$msg" --arg s "$session" \
|
|
'{type:$t, message:$m, session_id:$s}')" >/dev/null 2>&1 || true
|
|
}
|
|
|
|
# Log to journal
|
|
log_journal() {
|
|
local action="$1" entity="$2" details="$3"
|
|
local ts
|
|
ts=$(date -u +"%Y-%m-%dT%H:%M:%S.3NZ")
|
|
local hash
|
|
hash=$(echo -n "$ts$action$entity$details" | shasum -a 256 | cut -c1-16)
|
|
mkdir -p "$(dirname "$JOURNAL")"
|
|
printf '{"timestamp":"%s","action":"%s","entity":"%s","details":"%s","hash":"%s"}\n' \
|
|
"$ts" "$action" "$entity" "$details" "$hash" >> "$JOURNAL"
|
|
}
|
|
|
|
# Get current session ID
|
|
get_session() {
|
|
if [[ -f "$SESSION_FILE" ]]; then
|
|
cat "$SESSION_FILE"
|
|
else
|
|
echo ""
|
|
fi
|
|
}
|
|
|
|
# ── INIT ──
|
|
cmd_init() {
|
|
mkdir -p "$(dirname "$COLLAB_DB")" "$HANDOFF_DIR"
|
|
|
|
if [[ -f "$COLLAB_DB" ]]; then
|
|
local has_sessions
|
|
has_sessions=$(sqlite3 "$COLLAB_DB" "SELECT count(*) FROM sqlite_master WHERE type='table' AND name='sessions';" 2>/dev/null || echo "0")
|
|
if [[ "$has_sessions" == "1" ]]; then
|
|
echo -e "${GREEN}Collaboration DB already initialized${NC}"
|
|
return
|
|
fi
|
|
fi
|
|
|
|
rm -f "$COLLAB_DB"
|
|
|
|
sqlite3 "$COLLAB_DB" <<'SQL'
|
|
PRAGMA journal_mode=WAL;
|
|
|
|
CREATE TABLE sessions (
|
|
session_id TEXT PRIMARY KEY,
|
|
started_at TEXT NOT NULL,
|
|
last_seen TEXT NOT NULL,
|
|
status TEXT DEFAULT 'active',
|
|
focus TEXT DEFAULT '',
|
|
agent_id TEXT DEFAULT '',
|
|
pid INTEGER DEFAULT 0
|
|
);
|
|
|
|
CREATE TABLE messages (
|
|
msg_id TEXT PRIMARY KEY,
|
|
session_id TEXT NOT NULL,
|
|
type TEXT NOT NULL,
|
|
message TEXT NOT NULL,
|
|
metadata TEXT DEFAULT '{}',
|
|
created_at TEXT NOT NULL,
|
|
read_by TEXT DEFAULT ''
|
|
);
|
|
CREATE INDEX idx_messages_type ON messages(type);
|
|
CREATE INDEX idx_messages_created ON messages(created_at);
|
|
|
|
CREATE TABLE handoffs (
|
|
handoff_id TEXT PRIMARY KEY,
|
|
from_session TEXT NOT NULL,
|
|
message TEXT NOT NULL,
|
|
context TEXT DEFAULT '{}',
|
|
created_at TEXT NOT NULL,
|
|
picked_up_by TEXT DEFAULT '',
|
|
picked_up_at TEXT DEFAULT ''
|
|
);
|
|
CREATE INDEX idx_handoffs_pending ON handoffs(picked_up_by);
|
|
SQL
|
|
|
|
echo -e "${GREEN}Collaboration DB initialized at $COLLAB_DB${NC}"
|
|
}
|
|
|
|
# Ensure DB exists
|
|
check_db() {
|
|
if [[ ! -f "$COLLAB_DB" ]]; then
|
|
cmd_init
|
|
fi
|
|
local has_table
|
|
has_table=$(sqlite3 "$COLLAB_DB" "SELECT count(*) FROM sqlite_master WHERE type='table' AND name='sessions';" 2>/dev/null || echo "0")
|
|
if [[ "$has_table" != "1" ]]; then
|
|
cmd_init
|
|
fi
|
|
}
|
|
|
|
# ── REGISTER ──
|
|
cmd_register() {
|
|
check_db
|
|
local focus="${*:-}"
|
|
local session_id="collab-$(date +%Y%m%d-%H%M%S)-$$"
|
|
local now
|
|
now=$(date -u +"%Y-%m-%dT%H:%M:%SZ")
|
|
|
|
# Mark stale sessions as abandoned (>2 hours old, still active)
|
|
sql "UPDATE sessions SET status='abandoned' WHERE status='active' AND last_seen < datetime('now', '-2 hours');"
|
|
|
|
# Register this session
|
|
sql "INSERT OR REPLACE INTO sessions (session_id, started_at, last_seen, status, focus, pid) VALUES ('$session_id', '$now', '$now', 'active', '$(echo "$focus" | sed "s/'/''/g")', $$);"
|
|
|
|
# Save session ID for other commands
|
|
echo "$session_id" > "$SESSION_FILE"
|
|
|
|
# Count pending handoffs and unread messages
|
|
local pending_handoffs unread_msgs active_sessions
|
|
pending_handoffs=$(sql "SELECT count(*) FROM handoffs WHERE picked_up_by='';" 2>/dev/null || echo 0)
|
|
unread_msgs=$(sql "SELECT count(*) FROM messages WHERE read_by NOT LIKE '%${session_id}%' AND created_at > datetime('now', '-24 hours');" 2>/dev/null || echo 0)
|
|
active_sessions=$(sql "SELECT count(*) FROM sessions WHERE status='active';" 2>/dev/null || echo 0)
|
|
|
|
# Compact output for SessionStart
|
|
echo -e "${PINK}[COLLAB]${NC} Session ${CYAN}${session_id}${NC} registered"
|
|
if [[ "$pending_handoffs" -gt 0 ]]; then
|
|
echo -e "${PINK}[COLLAB]${NC} ${YELLOW}${pending_handoffs} pending handoff(s)${NC} — run: ${CYAN}memory-collaboration.sh inbox${NC}"
|
|
fi
|
|
if [[ "$unread_msgs" -gt 0 ]]; then
|
|
echo -e "${PINK}[COLLAB]${NC} ${BLUE}${unread_msgs} unread message(s)${NC}"
|
|
fi
|
|
echo -e "${PINK}[COLLAB]${NC} Active sessions: ${GREEN}${active_sessions}${NC}"
|
|
|
|
# Post to Slack (async, non-blocking)
|
|
post_collab "announce" "Session online${focus:+ — focus: $focus}" "$session_id" &
|
|
|
|
# Log to journal
|
|
log_journal "collab-register" "$session_id" "Session registered${focus:+, focus: $focus}"
|
|
}
|
|
|
|
# ── ANNOUNCE ──
|
|
cmd_announce() {
|
|
check_db
|
|
local msg="$*"
|
|
if [[ -z "$msg" ]]; then
|
|
echo -e "${RED}Usage: $0 announce <message>${NC}"
|
|
exit 1
|
|
fi
|
|
|
|
local session
|
|
session=$(get_session)
|
|
if [[ -z "$session" ]]; then
|
|
echo -e "${RED}No active session. Run: $0 register${NC}"
|
|
exit 1
|
|
fi
|
|
|
|
local msg_id="msg-$(date +%s)-$$"
|
|
local now
|
|
now=$(date -u +"%Y-%m-%dT%H:%M:%SZ")
|
|
|
|
sql "INSERT INTO messages (msg_id, session_id, type, message, created_at) VALUES ('$msg_id', '$session', 'announce', '$(echo "$msg" | sed "s/'/''/g")', '$now');"
|
|
|
|
# Update last_seen
|
|
sql "UPDATE sessions SET last_seen='$now' WHERE session_id='$session';"
|
|
|
|
echo -e "${GREEN}Announced:${NC} $msg"
|
|
|
|
post_collab "announce" "$msg" "$session" &
|
|
log_journal "collab-announce" "$session" "$msg"
|
|
}
|
|
|
|
# ── HANDOFF ──
|
|
cmd_handoff() {
|
|
check_db
|
|
local msg="$*"
|
|
if [[ -z "$msg" ]]; then
|
|
echo -e "${RED}Usage: $0 handoff <message>${NC}"
|
|
exit 1
|
|
fi
|
|
|
|
local session
|
|
session=$(get_session)
|
|
if [[ -z "$session" ]]; then
|
|
echo -e "${RED}No active session. Run: $0 register${NC}"
|
|
exit 1
|
|
fi
|
|
|
|
local handoff_id="handoff-$(date +%s)-$$"
|
|
local now
|
|
now=$(date -u +"%Y-%m-%dT%H:%M:%SZ")
|
|
|
|
# Write to SQLite
|
|
sql "INSERT INTO handoffs (handoff_id, from_session, message, created_at) VALUES ('$handoff_id', '$session', '$(echo "$msg" | sed "s/'/''/g")', '$now');"
|
|
|
|
# Write JSON file for fast SessionStart reading
|
|
cat > "$HANDOFF_DIR/${handoff_id}.json" <<EOF
|
|
{
|
|
"handoff_id": "$handoff_id",
|
|
"from_session": "$session",
|
|
"message": $(echo "$msg" | jq -Rs .),
|
|
"created_at": "$now",
|
|
"picked_up_by": "",
|
|
"picked_up_at": ""
|
|
}
|
|
EOF
|
|
|
|
echo -e "${GREEN}Handoff saved:${NC} $msg"
|
|
|
|
post_collab "handoff" "$msg" "$session" &
|
|
log_journal "collab-handoff" "$session" "Handoff: $msg"
|
|
}
|
|
|
|
# ── INBOX ──
|
|
cmd_inbox() {
|
|
check_db
|
|
local session
|
|
session=$(get_session)
|
|
|
|
# Show pending handoffs
|
|
local handoffs
|
|
handoffs=$(sql "SELECT handoff_id, from_session, message, created_at FROM handoffs WHERE picked_up_by='' ORDER BY created_at DESC LIMIT 10;" 2>/dev/null)
|
|
|
|
if [[ -n "$handoffs" ]]; then
|
|
echo -e "${PINK}╔════════════════════════════════════════════════════════════╗${NC}"
|
|
echo -e "${PINK}║${NC} ${BOLD}Pending Handoffs${NC} ${PINK}║${NC}"
|
|
echo -e "${PINK}╚════════════════════════════════════════════════════════════╝${NC}"
|
|
echo ""
|
|
|
|
while IFS='|' read -r hid from_sess msg created; do
|
|
local time_part="${created:11:8}"
|
|
echo -e " ${YELLOW}🤝${NC} ${CYAN}${from_sess}${NC} (${BLUE}${time_part}${NC})"
|
|
echo -e " ${msg}"
|
|
echo ""
|
|
done <<< "$handoffs"
|
|
|
|
# Mark handoffs as picked up by this session
|
|
if [[ -n "$session" ]]; then
|
|
local now
|
|
now=$(date -u +"%Y-%m-%dT%H:%M:%SZ")
|
|
sql "UPDATE handoffs SET picked_up_by='$session', picked_up_at='$now' WHERE picked_up_by='';"
|
|
# Also update JSON files
|
|
for f in "$HANDOFF_DIR"/handoff-*.json; do
|
|
[[ ! -f "$f" ]] && continue
|
|
local pbu
|
|
pbu=$(jq -r '.picked_up_by' "$f" 2>/dev/null)
|
|
if [[ "$pbu" == "" || "$pbu" == "null" ]]; then
|
|
local tmp
|
|
tmp=$(jq --arg s "$session" --arg t "$now" '.picked_up_by=$s | .picked_up_at=$t' "$f")
|
|
echo "$tmp" > "$f"
|
|
fi
|
|
done
|
|
fi
|
|
fi
|
|
|
|
# Show recent messages (last 24h)
|
|
local messages
|
|
messages=$(sql "SELECT msg_id, session_id, type, message, created_at FROM messages WHERE created_at > datetime('now', '-24 hours') ORDER BY created_at DESC LIMIT 10;" 2>/dev/null)
|
|
|
|
if [[ -n "$messages" ]]; then
|
|
echo -e "${PINK}╔════════════════════════════════════════════════════════════╗${NC}"
|
|
echo -e "${PINK}║${NC} ${BOLD}Recent Messages (24h)${NC} ${PINK}║${NC}"
|
|
echo -e "${PINK}╚════════════════════════════════════════════════════════════╝${NC}"
|
|
echo ""
|
|
|
|
while IFS='|' read -r mid sess type msg created; do
|
|
local time_part="${created:11:8}"
|
|
local icon="📨"
|
|
case "$type" in
|
|
announce) icon="📢" ;;
|
|
handoff) icon="🤝" ;;
|
|
question) icon="❓" ;;
|
|
answer) icon="💬" ;;
|
|
esac
|
|
echo -e " ${icon} ${CYAN}${sess}${NC} [${BLUE}${time_part}${NC}] ${msg}"
|
|
done <<< "$messages"
|
|
echo ""
|
|
fi
|
|
|
|
if [[ -z "$handoffs" && -z "$messages" ]]; then
|
|
echo -e "${PINK}[COLLAB]${NC} Inbox empty — no pending handoffs or recent messages"
|
|
fi
|
|
|
|
# Mark messages as read
|
|
if [[ -n "$session" && -n "$messages" ]]; then
|
|
sql "UPDATE messages SET read_by = CASE WHEN read_by='' THEN '$session' ELSE read_by || ',$session' END WHERE created_at > datetime('now', '-24 hours') AND read_by NOT LIKE '%${session}%';" 2>/dev/null || true
|
|
fi
|
|
}
|
|
|
|
# ── STATUS ──
|
|
cmd_status() {
|
|
check_db
|
|
|
|
echo -e "${PINK}╔════════════════════════════════════════════════════════════╗${NC}"
|
|
echo -e "${PINK}║${NC} ${BOLD}BlackRoad Collaboration Status${NC} ${PINK}║${NC}"
|
|
echo -e "${PINK}╚════════════════════════════════════════════════════════════╝${NC}"
|
|
echo ""
|
|
|
|
# Current session
|
|
local session
|
|
session=$(get_session)
|
|
if [[ -n "$session" ]]; then
|
|
echo -e " ${GREEN}Current session:${NC} ${CYAN}${session}${NC}"
|
|
else
|
|
echo -e " ${YELLOW}No active session${NC} — run: ${CYAN}$0 register${NC}"
|
|
fi
|
|
echo ""
|
|
|
|
# Active sessions
|
|
echo -e " ${BOLD}Active Sessions:${NC}"
|
|
local active
|
|
active=$(sql "SELECT session_id, started_at, focus FROM sessions WHERE status='active' ORDER BY started_at DESC LIMIT 10;" 2>/dev/null)
|
|
if [[ -n "$active" ]]; then
|
|
while IFS='|' read -r sid started focus; do
|
|
local time_part="${started:11:8}"
|
|
echo -e " ${GREEN}●${NC} ${CYAN}${sid}${NC} (since ${BLUE}${time_part}${NC})${focus:+ — $focus}"
|
|
done <<< "$active"
|
|
else
|
|
echo -e " ${YELLOW}No active sessions${NC}"
|
|
fi
|
|
echo ""
|
|
|
|
# Stats
|
|
local total_sessions total_msgs total_handoffs pending_handoffs
|
|
total_sessions=$(sql "SELECT count(*) FROM sessions;" 2>/dev/null || echo 0)
|
|
total_msgs=$(sql "SELECT count(*) FROM messages;" 2>/dev/null || echo 0)
|
|
total_handoffs=$(sql "SELECT count(*) FROM handoffs;" 2>/dev/null || echo 0)
|
|
pending_handoffs=$(sql "SELECT count(*) FROM handoffs WHERE picked_up_by='';" 2>/dev/null || echo 0)
|
|
|
|
echo -e " ${BOLD}Stats:${NC}"
|
|
echo -e " Sessions: ${GREEN}${total_sessions}${NC} | Messages: ${BLUE}${total_msgs}${NC} | Handoffs: ${PURPLE}${total_handoffs}${NC} (${YELLOW}${pending_handoffs} pending${NC})"
|
|
echo ""
|
|
|
|
# Last 5 messages
|
|
local recent
|
|
recent=$(sql "SELECT type, session_id, message, created_at FROM messages ORDER BY created_at DESC LIMIT 5;" 2>/dev/null)
|
|
if [[ -n "$recent" ]]; then
|
|
echo -e " ${BOLD}Recent Activity:${NC}"
|
|
while IFS='|' read -r type sess msg created; do
|
|
local time_part="${created:11:8}"
|
|
echo -e " [${BLUE}${time_part}${NC}] ${CYAN}${type}${NC} from ${sess}: ${msg:0:60}"
|
|
done <<< "$recent"
|
|
fi
|
|
|
|
# Slack health check
|
|
echo ""
|
|
local slack_status
|
|
slack_status=$(curl -s --max-time 2 --connect-timeout 1 "$SLACK_API/health" 2>/dev/null | jq -r '.status' 2>/dev/null || echo "unreachable")
|
|
if [[ "$slack_status" == "alive" ]]; then
|
|
echo -e " ${GREEN}Slack:${NC} connected"
|
|
else
|
|
echo -e " ${YELLOW}Slack:${NC} ${slack_status} (local-only mode)"
|
|
fi
|
|
}
|
|
|
|
# ── POST ──
|
|
cmd_post() {
|
|
local msg="$*"
|
|
if [[ -z "$msg" ]]; then
|
|
echo -e "${RED}Usage: $0 post <message>${NC}"
|
|
exit 1
|
|
fi
|
|
|
|
local session
|
|
session=$(get_session)
|
|
local prefix="${session:+[$session] }"
|
|
|
|
post_to_slack "${prefix}${msg}"
|
|
echo -e "${GREEN}Posted to Slack:${NC} ${msg}"
|
|
}
|
|
|
|
# ── ASK ──
|
|
cmd_ask() {
|
|
local agent="$1"
|
|
shift || true
|
|
local msg="$*"
|
|
|
|
if [[ -z "$agent" || -z "$msg" ]]; then
|
|
echo -e "${RED}Usage: $0 ask <agent> <message>${NC}"
|
|
echo -e "${CYAN}Agents: alice, cecilia, octavia, aria, lucidia, shellfish, caddy, alexa, road${NC}"
|
|
exit 1
|
|
fi
|
|
|
|
echo -e "${BLUE}Asking ${CYAN}${agent}${BLUE}...${NC}"
|
|
|
|
local response
|
|
response=$(curl -s --max-time 15 --connect-timeout 3 \
|
|
-X POST "$SLACK_API/ask" \
|
|
-H "Content-Type: application/json" \
|
|
-d "$(jq -n --arg a "$agent" --arg m "$msg" '{agent:$a, message:$m, slack:true}')" 2>/dev/null)
|
|
|
|
if [[ -n "$response" ]]; then
|
|
local agent_name reply
|
|
agent_name=$(echo "$response" | jq -r '.agent // "?"')
|
|
reply=$(echo "$response" | jq -r '.reply // "no response"')
|
|
echo -e "${GREEN}${agent_name}:${NC} ${reply}"
|
|
else
|
|
echo -e "${RED}No response — Slack Worker may be unreachable${NC}"
|
|
fi
|
|
}
|
|
|
|
# ── GROUP ──
|
|
cmd_group() {
|
|
local topic="$*"
|
|
if [[ -z "$topic" ]]; then
|
|
echo -e "${RED}Usage: $0 group <topic>${NC}"
|
|
exit 1
|
|
fi
|
|
|
|
echo -e "${BLUE}Starting group discussion: ${CYAN}${topic}${NC}"
|
|
|
|
local response
|
|
response=$(curl -s --max-time 30 --connect-timeout 3 \
|
|
-X POST "$SLACK_API/group" \
|
|
-H "Content-Type: application/json" \
|
|
-d "$(jq -n --arg t "$topic" '{topic:$t}')" 2>/dev/null)
|
|
|
|
if [[ -n "$response" ]]; then
|
|
echo ""
|
|
echo "$response" | jq -r '.transcript[]? | "\(.emoji) \(.agent): \(.reply)"' 2>/dev/null
|
|
else
|
|
echo -e "${RED}No response — Slack Worker may be unreachable${NC}"
|
|
fi
|
|
}
|
|
|
|
# ── COMPLETE ──
|
|
cmd_complete() {
|
|
check_db
|
|
local session
|
|
session=$(get_session)
|
|
if [[ -z "$session" ]]; then
|
|
echo -e "${YELLOW}No active session to complete${NC}"
|
|
return
|
|
fi
|
|
|
|
local now
|
|
now=$(date -u +"%Y-%m-%dT%H:%M:%SZ")
|
|
sql "UPDATE sessions SET status='completed', last_seen='$now' WHERE session_id='$session';"
|
|
|
|
echo -e "${GREEN}Session ${CYAN}${session}${GREEN} marked complete${NC}"
|
|
rm -f "$SESSION_FILE"
|
|
|
|
post_collab "complete" "Session complete" "$session" &
|
|
log_journal "collab-complete" "$session" "Session completed"
|
|
}
|
|
|
|
# ── HELP ──
|
|
cmd_help() {
|
|
cat <<EOF
|
|
${PINK}╔════════════════════════════════════════════════════════════╗${NC}
|
|
${PINK}║${NC} ${BOLD}BlackRoad Collaboration System${NC} ${PINK}║${NC}
|
|
${PINK}╚════════════════════════════════════════════════════════════╝${NC}
|
|
|
|
${BOLD}Session Management:${NC}
|
|
${CYAN}register [focus]${NC} Register this Claude session
|
|
${CYAN}complete${NC} Mark session as done
|
|
${CYAN}status${NC} Show collaboration status
|
|
|
|
${BOLD}Messaging:${NC}
|
|
${CYAN}announce <msg>${NC} Broadcast to all sessions + Slack
|
|
${CYAN}handoff <msg>${NC} Leave a note for the next session
|
|
${CYAN}inbox${NC} Read pending handoffs + messages
|
|
|
|
${BOLD}Slack Integration:${NC}
|
|
${CYAN}post <msg>${NC} Post to Slack channel
|
|
${CYAN}ask <agent> <msg>${NC} Ask an AI agent via Slack
|
|
${CYAN}group <topic>${NC} Start multi-agent discussion
|
|
|
|
${BOLD}System:${NC}
|
|
${CYAN}init${NC} Initialize the database
|
|
${CYAN}help${NC} Show this help
|
|
|
|
${BOLD}Agents:${NC} alice, cecilia, octavia, aria, lucidia, shellfish, caddy, alexa, road
|
|
|
|
${BOLD}Examples:${NC}
|
|
$0 register "working on mesh network"
|
|
$0 announce "deployed auth fix to production"
|
|
$0 handoff "left off at mesh-network-poc todo #5, DNS still needs CNAME"
|
|
$0 ask alice "what's your disk usage?"
|
|
$0 group "should we migrate to Bookworm this week?"
|
|
EOF
|
|
}
|
|
|
|
# ── COMMAND ROUTER ──
|
|
case "${1:-help}" in
|
|
init) cmd_init ;;
|
|
register|reg) shift; cmd_register "$@" ;;
|
|
announce|ann) shift; cmd_announce "$@" ;;
|
|
handoff|ho) shift; cmd_handoff "$@" ;;
|
|
inbox|in) cmd_inbox ;;
|
|
status|st) cmd_status ;;
|
|
post|p) shift; cmd_post "$@" ;;
|
|
ask|a) shift; cmd_ask "$@" ;;
|
|
group|g) shift; cmd_group "$@" ;;
|
|
complete|done) cmd_complete ;;
|
|
help|--help|-h) cmd_help ;;
|
|
*)
|
|
echo -e "${RED}Unknown command: $1${NC}"
|
|
cmd_help
|
|
exit 1
|
|
;;
|
|
esac
|