45 lines
1.4 KiB
Bash
Executable file
45 lines
1.4 KiB
Bash
Executable file
#!/usr/bin/env bash
|
|
# on-stop-matrix.sh — Stop hook: post Claude response to Matrix thread.
|
|
#
|
|
# Called by Claude Code after each assistant turn. Reads the response from
|
|
# the hook JSON and posts it to the Matrix thread for this action session.
|
|
#
|
|
# Requires env vars: MATRIX_THREAD_ID, MATRIX_TOKEN, MATRIX_HOMESERVER, MATRIX_ROOM_ID
|
|
#
|
|
# Usage (in .claude/settings.json):
|
|
# {"type": "command", "command": "/path/to/on-stop-matrix.sh"}
|
|
|
|
# Exit early if Matrix thread not configured
|
|
if [ -z "${MATRIX_THREAD_ID:-}" ] || [ -z "${MATRIX_TOKEN:-}" ] \
|
|
|| [ -z "${MATRIX_HOMESERVER:-}" ] || [ -z "${MATRIX_ROOM_ID:-}" ]; then
|
|
cat > /dev/null
|
|
exit 0
|
|
fi
|
|
|
|
input=$(cat)
|
|
|
|
# Extract response text from hook JSON
|
|
response=$(printf '%s' "$input" | jq -r '.last_assistant_message // empty' 2>/dev/null)
|
|
[ -z "$response" ] && exit 0
|
|
|
|
# Truncate long output for readability (keep to ~4000 chars)
|
|
MAX_LEN=4000
|
|
if [ "${#response}" -gt "$MAX_LEN" ]; then
|
|
response="${response:0:$MAX_LEN}
|
|
... [truncated]"
|
|
fi
|
|
|
|
# Post to Matrix thread
|
|
room_encoded="${MATRIX_ROOM_ID//!/%21}"
|
|
txn="$(date +%s%N)$$"
|
|
|
|
body=$(jq -nc \
|
|
--arg m "$response" \
|
|
--arg t "$MATRIX_THREAD_ID" \
|
|
'{msgtype:"m.text",body:$m,"m.relates_to":{rel_type:"m.thread",event_id:$t}}')
|
|
|
|
curl -s -X PUT \
|
|
-H "Authorization: Bearer ${MATRIX_TOKEN}" \
|
|
-H "Content-Type: application/json" \
|
|
"${MATRIX_HOMESERVER}/_matrix/client/v3/rooms/${room_encoded}/send/m.room.message/${txn}" \
|
|
-d "$body" > /dev/null 2>&1 || true
|