fathom-mcp 0.4.4 → 0.4.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "fathom-mcp",
3
- "version": "0.4.4",
3
+ "version": "0.4.5",
4
4
  "description": "MCP server for Fathom — vault operations, search, rooms, and cross-workspace communication",
5
5
  "type": "module",
6
6
  "bin": {
@@ -33,29 +33,23 @@ if [ "$HOOK_ENABLED" != "True" ] && [ "$HOOK_ENABLED" != "true" ]; then
33
33
  exit 0
34
34
  fi
35
35
 
36
- # Toast: start multi-stage
37
- "$TOAST" memento --status precompact &>/dev/null
38
- "$TOAST" --update precompact "⏳ Getting context..." &>/dev/null
36
+ # Toast: progress via queue (one-shot)
37
+ "$TOAST" fathom "⏳ Snapshotting vault..." &>/dev/null
39
38
 
40
39
  # Read PreCompact input (contains transcript_path)
41
40
  INPUT=$(cat)
42
41
  TRANSCRIPT_PATH=$(echo "$INPUT" | python3 -c "import json,sys; print(json.load(sys.stdin).get('transcript_path',''))" 2>/dev/null || echo "")
43
42
 
44
43
  if [ -z "$TRANSCRIPT_PATH" ] || [ ! -f "$TRANSCRIPT_PATH" ]; then
45
- "$TOAST" --update precompact "✗ No transcript found" &>/dev/null
46
- "$TOAST" --close precompact &>/dev/null &
44
+ "$TOAST" fathom "✗ No transcript found" &>/dev/null
47
45
  exit 0
48
46
  fi
49
47
 
50
- # Toast: extracting
51
- "$TOAST" --update precompact "⏳ Extracting memories..." &>/dev/null
52
-
53
48
  # Extract vault file paths from transcript
54
49
  VAULT_FILES=$(grep -oP 'vault/[a-zA-Z0-9_/.-]+\.md' "$TRANSCRIPT_PATH" 2>/dev/null | sort -u || echo "")
55
50
 
56
51
  if [ -z "$VAULT_FILES" ]; then
57
- "$TOAST" --update precompact "✓ No vault files to record" &>/dev/null
58
- ("$TOAST" --close precompact &>/dev/null &)
52
+ "$TOAST" fathom "✓ No vault files to record" &>/dev/null
59
53
  exit 0
60
54
  fi
61
55
 
@@ -75,8 +69,7 @@ done
75
69
  FILE_COUNT=$(echo "$VAULT_FILES" | wc -l)
76
70
 
77
71
  # Toast: done
78
- "$TOAST" --update precompact "✓ Stored ${FILE_COUNT} vault file(s)" &>/dev/null
79
- ("$TOAST" --close precompact &>/dev/null &)
72
+ "$TOAST" fathom "✓ Stored ${FILE_COUNT} vault file(s)" &>/dev/null
80
73
 
81
74
  python3 -c "
82
75
  import json, sys
@@ -2,7 +2,7 @@
2
2
  # hook-toast.sh — tmux popup notifications for agent hooks.
3
3
  #
4
4
  # Usage:
5
- # hook-toast.sh <system> <message> # one-shot toast (auto-closes after 2s)
5
+ # hook-toast.sh <system> <message> # queued toast (shows for 2s each)
6
6
  # hook-toast.sh <system> --status <id> # start a multi-stage toast (poll mode)
7
7
  # hook-toast.sh --update <id> <message> # update a running toast
8
8
  # hook-toast.sh --close <id> # close a running toast (after delay)
@@ -13,6 +13,11 @@
13
13
  #
14
14
  # Any other system name works too — gets a default icon and grey border.
15
15
  #
16
+ # One-shot toasts are queued per-session — multiple hooks can fire toasts
17
+ # without clobbering each other. A single popup reads from the queue,
18
+ # showing each message for 2s before advancing. Popups target the session
19
+ # that spawned them via -t, so they stay in the right terminal.
20
+ #
16
21
  # Multi-stage example (PreCompact):
17
22
  # hook-toast.sh memento --status precompact
18
23
  # hook-toast.sh --update precompact "⏳ Getting context..."
@@ -20,14 +25,22 @@
20
25
  # hook-toast.sh --update precompact "✓ Stored 7 memories"
21
26
  # hook-toast.sh --close precompact
22
27
 
23
- TOAST_DIR="/tmp/hook-toast"
24
- mkdir -p "$TOAST_DIR"
25
-
26
28
  # Bail silently if not in tmux
27
29
  if ! tmux info &>/dev/null; then
28
30
  exit 0
29
31
  fi
30
32
 
33
+ # Derive session name — used for per-session queue isolation and -t targeting
34
+ SESSION=$(tmux display-message -p '#{session_name}' 2>/dev/null)
35
+ if [ -z "$SESSION" ]; then
36
+ exit 0
37
+ fi
38
+
39
+ TOAST_DIR="/tmp/hook-toast/${SESSION}"
40
+ QUEUE_FILE="$TOAST_DIR/queue"
41
+ READER_PID_FILE="$TOAST_DIR/reader.pid"
42
+ mkdir -p "$TOAST_DIR"
43
+
31
44
  get_style() {
32
45
  case "$1" in
33
46
  memento) echo "colour37" ;;
@@ -52,21 +65,55 @@ get_title() {
52
65
  esac
53
66
  }
54
67
 
55
- # One-shot toast
68
+ # Check if the queue reader popup is still alive
69
+ reader_alive() {
70
+ local pid
71
+ pid=$(cat "$READER_PID_FILE" 2>/dev/null) || return 1
72
+ [ -n "$pid" ] && kill -0 "$pid" 2>/dev/null
73
+ }
74
+
75
+ # Queued one-shot toast — append to queue, spawn reader if needed
56
76
  toast_oneshot() {
57
77
  local system="$1"
58
78
  local message="$2"
59
- local colour icon title
60
- colour=$(get_style "$system")
79
+ local icon
61
80
  icon=$(get_icon "$system")
62
- title=$(get_title "$system")
63
81
 
64
- (tmux display-popup -x R -y 0 -w 42 -h 3 \
65
- -s "fg=$colour" -T " $icon $title " -E \
66
- "echo ' $message'; sleep 2" &>/dev/null &)
82
+ # Append to queue: icon|colour|title|message
83
+ echo "${icon}|$(get_style "$system")|$(get_title "$system")|$message" >> "$QUEUE_FILE"
84
+
85
+ # If reader is already running, it will pick up the new entry
86
+ if reader_alive; then
87
+ return
88
+ fi
89
+
90
+ # Spawn a reader popup targeting this session
91
+ (tmux display-popup -t "$SESSION" -x R -y 0 -w 42 -h 3 \
92
+ -s "fg=colour245" -E "
93
+ echo \$\$ > '$READER_PID_FILE'
94
+ while true; do
95
+ LINE=\$(head -1 '$QUEUE_FILE' 2>/dev/null)
96
+ if [ -z \"\$LINE\" ]; then
97
+ rm -f '$READER_PID_FILE'
98
+ break
99
+ fi
100
+ TAIL=\$(tail -n +2 '$QUEUE_FILE' 2>/dev/null)
101
+ if [ -n \"\$TAIL\" ]; then
102
+ echo \"\$TAIL\" > '$QUEUE_FILE'
103
+ else
104
+ > '$QUEUE_FILE'
105
+ fi
106
+ ICON=\$(echo \"\$LINE\" | cut -d'|' -f1)
107
+ MSG=\$(echo \"\$LINE\" | cut -d'|' -f4-)
108
+ clear
109
+ echo \" \$ICON \$MSG\"
110
+ sleep 2
111
+ done
112
+ rm -f '$QUEUE_FILE' '$READER_PID_FILE'
113
+ " &>/dev/null &)
67
114
  }
68
115
 
69
- # Start a multi-stage toast (polling status file)
116
+ # Start a multi-stage toast (polling status file) — targets this session
70
117
  toast_start() {
71
118
  local system="$1"
72
119
  local id="$2"
@@ -78,7 +125,7 @@ toast_start() {
78
125
 
79
126
  echo "⏳ Starting..." > "$status_file"
80
127
 
81
- (tmux display-popup -x R -y 0 -w 42 -h 3 \
128
+ (tmux display-popup -t "$SESSION" -x R -y 0 -w 42 -h 3 \
82
129
  -s "fg=$colour" -T " $icon $title " -E "
83
130
  LAST=''
84
131
  while [ -f '$status_file' ]; do
@@ -104,7 +151,6 @@ toast_update() {
104
151
  # Close a running toast (remove status file — popup exits on next poll)
105
152
  toast_close() {
106
153
  local id="$1"
107
- # Give the popup time to display the final message
108
154
  sleep 2
109
155
  rm -f "$TOAST_DIR/$id"
110
156
  }