@suwujs/codex-vault 0.1.0
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/LICENSE +21 -0
- package/README.md +174 -0
- package/README.zh-CN.md +155 -0
- package/bin/cli.js +90 -0
- package/package.json +29 -0
- package/plugin/VERSION +1 -0
- package/plugin/hooks/classify-message.py +240 -0
- package/plugin/hooks/session-start.sh +176 -0
- package/plugin/hooks/validate-write.py +113 -0
- package/plugin/install.sh +350 -0
- package/plugin/instructions.md +118 -0
- package/plugin/skills/dump.md +29 -0
- package/plugin/skills/ingest.md +63 -0
- package/plugin/skills/recall.md +54 -0
- package/plugin/skills/wrap-up.md +35 -0
- package/vault/.claude/settings.json +39 -0
- package/vault/.claude/skills/dump/SKILL.md +29 -0
- package/vault/.claude/skills/ingest/SKILL.md +63 -0
- package/vault/.claude/skills/recall/SKILL.md +54 -0
- package/vault/.claude/skills/wrap-up/SKILL.md +35 -0
- package/vault/.codex/config.toml +2 -0
- package/vault/.codex/hooks.json +39 -0
- package/vault/.codex/skills/dump/SKILL.md +29 -0
- package/vault/.codex/skills/ingest/SKILL.md +63 -0
- package/vault/.codex/skills/recall/SKILL.md +54 -0
- package/vault/.codex/skills/wrap-up/SKILL.md +35 -0
- package/vault/.codex-vault/hooks/classify-message.py +240 -0
- package/vault/.codex-vault/hooks/session-start.sh +176 -0
- package/vault/.codex-vault/hooks/validate-write.py +113 -0
- package/vault/AGENTS.md +118 -0
- package/vault/CLAUDE.md +118 -0
- package/vault/Home.md +21 -0
- package/vault/brain/Key Decisions.md +11 -0
- package/vault/brain/Memories.md +19 -0
- package/vault/brain/North Star.md +29 -0
- package/vault/brain/Patterns.md +11 -0
- package/vault/log.md +15 -0
- package/vault/reference/.gitkeep +0 -0
- package/vault/sources/.gitkeep +0 -0
- package/vault/sources/README.md +19 -0
- package/vault/templates/Decision Record.md +29 -0
- package/vault/templates/Reference Note.md +25 -0
- package/vault/templates/Source Summary.md +25 -0
- package/vault/templates/Thinking Note.md +26 -0
- package/vault/templates/Work Note.md +25 -0
- package/vault/work/Index.md +35 -0
- package/vault/work/active/.gitkeep +0 -0
- package/vault/work/archive/.gitkeep +0 -0
|
@@ -0,0 +1,350 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
set -eo pipefail
|
|
3
|
+
|
|
4
|
+
# Codex-Vault installer
|
|
5
|
+
# Detects installed LLM agents and generates the appropriate configuration.
|
|
6
|
+
# Supports: Claude Code, Codex CLI.
|
|
7
|
+
#
|
|
8
|
+
# Two modes:
|
|
9
|
+
# Standalone — run from within the codex-vault repo (vault/ is the working directory)
|
|
10
|
+
# Integrated — run from a user's project root (vault/ becomes a subdirectory)
|
|
11
|
+
|
|
12
|
+
SCRIPT_DIR="$(cd "$(dirname "$0")" && pwd)"
|
|
13
|
+
REPO_DIR="$(cd "$SCRIPT_DIR/.." && pwd)"
|
|
14
|
+
PROJECT_DIR="$(pwd)"
|
|
15
|
+
|
|
16
|
+
echo "=== Codex-Vault Installer ==="
|
|
17
|
+
echo ""
|
|
18
|
+
|
|
19
|
+
# --- Detect mode ---
|
|
20
|
+
# If CWD is the codex-vault repo (or vault/), use standalone mode.
|
|
21
|
+
# Otherwise, use integrated mode (install into user's project).
|
|
22
|
+
|
|
23
|
+
MODE="integrated"
|
|
24
|
+
if [ "$PROJECT_DIR" = "$REPO_DIR" ] || [ "$PROJECT_DIR" = "$REPO_DIR/vault" ]; then
|
|
25
|
+
MODE="standalone"
|
|
26
|
+
fi
|
|
27
|
+
# Also detect if inside repo subdirectories
|
|
28
|
+
case "$PROJECT_DIR" in
|
|
29
|
+
"$REPO_DIR"/*) MODE="standalone" ;;
|
|
30
|
+
esac
|
|
31
|
+
|
|
32
|
+
if [ "$MODE" = "standalone" ]; then
|
|
33
|
+
VAULT_DIR="$REPO_DIR/vault"
|
|
34
|
+
CONFIG_DIR="$VAULT_DIR" # configs go inside vault/
|
|
35
|
+
HOOKS_REL=".codex-vault/hooks" # relative to vault/
|
|
36
|
+
echo "[*] Standalone mode — vault is the working directory"
|
|
37
|
+
else
|
|
38
|
+
VAULT_DIR="$PROJECT_DIR/vault"
|
|
39
|
+
CONFIG_DIR="$PROJECT_DIR" # configs go at project root
|
|
40
|
+
HOOKS_REL="vault/.codex-vault/hooks" # relative to project root
|
|
41
|
+
echo "[*] Integrated mode — installing into $(basename "$PROJECT_DIR")/"
|
|
42
|
+
fi
|
|
43
|
+
|
|
44
|
+
echo ""
|
|
45
|
+
|
|
46
|
+
# --- Detect agents ---
|
|
47
|
+
|
|
48
|
+
AGENTS=()
|
|
49
|
+
|
|
50
|
+
if command -v claude &>/dev/null; then
|
|
51
|
+
AGENTS+=("claude")
|
|
52
|
+
echo "[+] Claude Code detected"
|
|
53
|
+
fi
|
|
54
|
+
|
|
55
|
+
if command -v codex &>/dev/null; then
|
|
56
|
+
AGENTS+=("codex")
|
|
57
|
+
echo "[+] Codex CLI detected"
|
|
58
|
+
fi
|
|
59
|
+
|
|
60
|
+
if [ ${#AGENTS[@]} -eq 0 ]; then
|
|
61
|
+
echo "[!] No supported agents found."
|
|
62
|
+
echo " Install Claude Code: https://docs.anthropic.com/en/docs/claude-code"
|
|
63
|
+
echo " Install Codex CLI: https://github.com/openai/codex"
|
|
64
|
+
echo ""
|
|
65
|
+
echo " You can still use the vault manually — just open it in Obsidian."
|
|
66
|
+
exit 0
|
|
67
|
+
fi
|
|
68
|
+
|
|
69
|
+
echo ""
|
|
70
|
+
|
|
71
|
+
# --- Copy vault template (integrated mode only) ---
|
|
72
|
+
|
|
73
|
+
if [ "$MODE" = "integrated" ]; then
|
|
74
|
+
if [ -d "$VAULT_DIR" ] && [ -f "$VAULT_DIR/Home.md" ]; then
|
|
75
|
+
echo "[*] Vault already exists at vault/ — skipping template copy"
|
|
76
|
+
else
|
|
77
|
+
echo "[+] Creating vault from template..."
|
|
78
|
+
mkdir -p "$VAULT_DIR"
|
|
79
|
+
# Copy vault contents, excluding agent-specific configs (we generate those)
|
|
80
|
+
# Use cp -r (universally available) instead of rsync
|
|
81
|
+
cp -r "$REPO_DIR/vault/"* "$VAULT_DIR/" 2>/dev/null || true
|
|
82
|
+
cp -r "$REPO_DIR/vault/".* "$VAULT_DIR/" 2>/dev/null || true
|
|
83
|
+
# Remove agent configs — we generate fresh ones for the target layout
|
|
84
|
+
rm -rf "$VAULT_DIR/.claude" "$VAULT_DIR/.codex" "$VAULT_DIR/CLAUDE.md" "$VAULT_DIR/AGENTS.md" 2>/dev/null || true
|
|
85
|
+
echo " Copied template to vault/"
|
|
86
|
+
fi
|
|
87
|
+
echo ""
|
|
88
|
+
fi
|
|
89
|
+
|
|
90
|
+
# --- Copy hooks into vault (makes vault self-contained) ---
|
|
91
|
+
|
|
92
|
+
HOOKS_DIR="$VAULT_DIR/.codex-vault/hooks"
|
|
93
|
+
mkdir -p "$HOOKS_DIR"
|
|
94
|
+
cp "$REPO_DIR/plugin/hooks/"* "$HOOKS_DIR/"
|
|
95
|
+
chmod +x "$HOOKS_DIR/"*.sh "$HOOKS_DIR/"*.py 2>/dev/null || true
|
|
96
|
+
echo "[+] Hook scripts copied to vault/.codex-vault/hooks/"
|
|
97
|
+
echo ""
|
|
98
|
+
|
|
99
|
+
# --- Helper: merge hooks into existing settings.json ---
|
|
100
|
+
# Uses python3 for reliable JSON manipulation.
|
|
101
|
+
|
|
102
|
+
merge_hooks_json() {
|
|
103
|
+
local target_file="$1"
|
|
104
|
+
local hooks_rel="$2"
|
|
105
|
+
|
|
106
|
+
# Pass data via env vars to python3 — no shell interpolation in python code.
|
|
107
|
+
CVAULT_TARGET_FILE="$target_file" CVAULT_HOOKS_REL="$hooks_rel" python3 <<'PYEOF'
|
|
108
|
+
import json, os
|
|
109
|
+
|
|
110
|
+
target_file = os.environ["CVAULT_TARGET_FILE"]
|
|
111
|
+
hooks_rel = os.environ["CVAULT_HOOKS_REL"]
|
|
112
|
+
|
|
113
|
+
new_hooks = {
|
|
114
|
+
"SessionStart": [{
|
|
115
|
+
"matcher": "startup|resume|compact",
|
|
116
|
+
"hooks": [{"type": "command", "command": f"bash {hooks_rel}/session-start.sh", "timeout": 30}]
|
|
117
|
+
}],
|
|
118
|
+
"UserPromptSubmit": [{
|
|
119
|
+
"hooks": [{"type": "command", "command": f"python3 {hooks_rel}/classify-message.py", "timeout": 15}]
|
|
120
|
+
}],
|
|
121
|
+
"PostToolUse": [{
|
|
122
|
+
"matcher": "Write|Edit",
|
|
123
|
+
"hooks": [{"type": "command", "command": f"python3 {hooks_rel}/validate-write.py", "timeout": 15}]
|
|
124
|
+
}],
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
if os.path.isfile(target_file):
|
|
128
|
+
with open(target_file) as f:
|
|
129
|
+
existing = json.load(f)
|
|
130
|
+
else:
|
|
131
|
+
existing = {}
|
|
132
|
+
|
|
133
|
+
if "hooks" not in existing:
|
|
134
|
+
existing["hooks"] = {}
|
|
135
|
+
|
|
136
|
+
# For each hook event, append entries (avoid duplicates by checking command)
|
|
137
|
+
for event, entries in new_hooks.items():
|
|
138
|
+
if event not in existing["hooks"]:
|
|
139
|
+
existing["hooks"][event] = entries
|
|
140
|
+
else:
|
|
141
|
+
existing_cmds = set()
|
|
142
|
+
for rule in existing["hooks"][event]:
|
|
143
|
+
for h in rule.get("hooks", []):
|
|
144
|
+
existing_cmds.add(h.get("command", ""))
|
|
145
|
+
for entry in entries:
|
|
146
|
+
cmds = [h.get("command", "") for h in entry.get("hooks", [])]
|
|
147
|
+
if not any(c in existing_cmds for c in cmds):
|
|
148
|
+
existing["hooks"][event].append(entry)
|
|
149
|
+
|
|
150
|
+
with open(target_file, "w") as f:
|
|
151
|
+
json.dump(existing, f, indent=2)
|
|
152
|
+
f.write("\n")
|
|
153
|
+
PYEOF
|
|
154
|
+
}
|
|
155
|
+
|
|
156
|
+
# --- Helper: append codex-vault section to instruction file ---
|
|
157
|
+
|
|
158
|
+
append_instructions() {
|
|
159
|
+
local target_file="$1"
|
|
160
|
+
|
|
161
|
+
# Generate instructions: heading + blank line + body (skip first 2 lines of instructions.md)
|
|
162
|
+
local section_content
|
|
163
|
+
section_content="$(printf '# Codex-Vault\n\n'; tail -n +3 "$REPO_DIR/plugin/instructions.md")"
|
|
164
|
+
|
|
165
|
+
if [ -f "$target_file" ]; then
|
|
166
|
+
# Check if section already exists
|
|
167
|
+
if grep -q "^# Codex-Vault" "$target_file"; then
|
|
168
|
+
echo " (codex-vault section already present — skipping)"
|
|
169
|
+
return
|
|
170
|
+
fi
|
|
171
|
+
# Append with separator
|
|
172
|
+
printf '\n---\n%s\n' "$section_content" >> "$target_file"
|
|
173
|
+
else
|
|
174
|
+
echo "$section_content" > "$target_file"
|
|
175
|
+
fi
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
# --- Setup functions ---
|
|
179
|
+
|
|
180
|
+
# --- Helper: install skills into .<agent>/skills/<name>/SKILL.md ---
|
|
181
|
+
|
|
182
|
+
install_skills() {
|
|
183
|
+
local target_dir="$1"
|
|
184
|
+
local agent_dir="$2" # .claude or .codex
|
|
185
|
+
local src_dir="$REPO_DIR/plugin/skills"
|
|
186
|
+
local count=0
|
|
187
|
+
|
|
188
|
+
if [ ! -d "$src_dir" ]; then
|
|
189
|
+
return
|
|
190
|
+
fi
|
|
191
|
+
|
|
192
|
+
for src_file in "$src_dir"/*.md; do
|
|
193
|
+
[ -f "$src_file" ] || continue
|
|
194
|
+
local skill_name
|
|
195
|
+
skill_name=$(basename "$src_file" .md)
|
|
196
|
+
local skill_dir="$target_dir/$agent_dir/skills/$skill_name"
|
|
197
|
+
mkdir -p "$skill_dir"
|
|
198
|
+
cp "$src_file" "$skill_dir/SKILL.md"
|
|
199
|
+
((count++))
|
|
200
|
+
done
|
|
201
|
+
|
|
202
|
+
echo " [+] $agent_dir/skills/ ($count skills)"
|
|
203
|
+
}
|
|
204
|
+
|
|
205
|
+
setup_claude() {
|
|
206
|
+
echo "--- Setting up Claude Code ---"
|
|
207
|
+
|
|
208
|
+
if [ "$MODE" = "integrated" ]; then
|
|
209
|
+
# Integrated: merge hooks into project root .claude/settings.json
|
|
210
|
+
mkdir -p "$CONFIG_DIR/.claude"
|
|
211
|
+
merge_hooks_json "$CONFIG_DIR/.claude/settings.json" "$HOOKS_REL"
|
|
212
|
+
echo " [+] .claude/settings.json (hooks merged at project root)"
|
|
213
|
+
|
|
214
|
+
# Append instructions to project root CLAUDE.md
|
|
215
|
+
append_instructions "$CONFIG_DIR/CLAUDE.md"
|
|
216
|
+
echo " [+] CLAUDE.md (codex-vault section appended at project root)"
|
|
217
|
+
|
|
218
|
+
# Install skills into project root .claude/skills/
|
|
219
|
+
install_skills "$CONFIG_DIR" ".claude"
|
|
220
|
+
else
|
|
221
|
+
# Standalone: write directly into vault/ (original behavior)
|
|
222
|
+
merge_hooks_json "$VAULT_DIR/.claude/settings.json" "$HOOKS_REL"
|
|
223
|
+
echo " [+] .claude/settings.json (3 hooks)"
|
|
224
|
+
|
|
225
|
+
# Install skills into vault/.claude/skills/
|
|
226
|
+
install_skills "$VAULT_DIR" ".claude"
|
|
227
|
+
|
|
228
|
+
append_instructions "$VAULT_DIR/CLAUDE.md"
|
|
229
|
+
echo " [+] CLAUDE.md"
|
|
230
|
+
fi
|
|
231
|
+
echo ""
|
|
232
|
+
}
|
|
233
|
+
|
|
234
|
+
# --- Helper: enable codex hooks feature flag in config.toml ---
|
|
235
|
+
|
|
236
|
+
enable_codex_hooks() {
|
|
237
|
+
local config_file="$1/.codex/config.toml"
|
|
238
|
+
mkdir -p "$(dirname "$config_file")"
|
|
239
|
+
|
|
240
|
+
if [ -f "$config_file" ]; then
|
|
241
|
+
if grep -q "codex_hooks" "$config_file"; then
|
|
242
|
+
# Already has the flag — ensure it's true
|
|
243
|
+
sed -i.bak 's/codex_hooks *= *false/codex_hooks = true/' "$config_file"
|
|
244
|
+
rm -f "${config_file}.bak"
|
|
245
|
+
elif grep -q "\[features\]" "$config_file"; then
|
|
246
|
+
# Has [features] section but no codex_hooks — append under it
|
|
247
|
+
sed -i.bak '/\[features\]/a\
|
|
248
|
+
codex_hooks = true' "$config_file"
|
|
249
|
+
rm -f "${config_file}.bak"
|
|
250
|
+
else
|
|
251
|
+
# No [features] section — append it
|
|
252
|
+
printf '\n[features]\ncodex_hooks = true\n' >> "$config_file"
|
|
253
|
+
fi
|
|
254
|
+
else
|
|
255
|
+
printf '[features]\ncodex_hooks = true\n' > "$config_file"
|
|
256
|
+
fi
|
|
257
|
+
|
|
258
|
+
echo " [+] .codex/config.toml (hooks enabled)"
|
|
259
|
+
}
|
|
260
|
+
|
|
261
|
+
setup_codex() {
|
|
262
|
+
echo "--- Setting up Codex CLI ---"
|
|
263
|
+
|
|
264
|
+
# Check if Claude Code is also installed — if so, AGENTS.md just references CLAUDE.md
|
|
265
|
+
local has_claude=false
|
|
266
|
+
for a in "${AGENTS[@]}"; do
|
|
267
|
+
[ "$a" = "claude" ] && has_claude=true
|
|
268
|
+
done
|
|
269
|
+
|
|
270
|
+
if [ "$MODE" = "integrated" ]; then
|
|
271
|
+
# Integrated: merge hooks into project root .codex/hooks.json
|
|
272
|
+
mkdir -p "$CONFIG_DIR/.codex"
|
|
273
|
+
merge_hooks_json "$CONFIG_DIR/.codex/hooks.json" "$HOOKS_REL"
|
|
274
|
+
echo " [+] .codex/hooks.json (hooks merged at project root)"
|
|
275
|
+
|
|
276
|
+
if [ "$has_claude" = true ]; then
|
|
277
|
+
echo "@CLAUDE.md" > "$CONFIG_DIR/AGENTS.md"
|
|
278
|
+
echo " [+] AGENTS.md (references @CLAUDE.md)"
|
|
279
|
+
else
|
|
280
|
+
append_instructions "$CONFIG_DIR/AGENTS.md"
|
|
281
|
+
echo " [+] AGENTS.md (codex-vault section appended at project root)"
|
|
282
|
+
fi
|
|
283
|
+
|
|
284
|
+
# Enable hooks feature flag
|
|
285
|
+
enable_codex_hooks "$CONFIG_DIR"
|
|
286
|
+
|
|
287
|
+
# Install skills into project root .codex/skills/
|
|
288
|
+
install_skills "$CONFIG_DIR" ".codex"
|
|
289
|
+
else
|
|
290
|
+
# Standalone: write directly into vault/ (original behavior)
|
|
291
|
+
mkdir -p "$VAULT_DIR/.codex"
|
|
292
|
+
|
|
293
|
+
merge_hooks_json "$VAULT_DIR/.codex/hooks.json" "$HOOKS_REL"
|
|
294
|
+
echo " [+] .codex/hooks.json (3 hooks)"
|
|
295
|
+
|
|
296
|
+
# Enable hooks feature flag
|
|
297
|
+
enable_codex_hooks "$VAULT_DIR"
|
|
298
|
+
|
|
299
|
+
if [ "$has_claude" = true ]; then
|
|
300
|
+
echo "@CLAUDE.md" > "$VAULT_DIR/AGENTS.md"
|
|
301
|
+
echo " [+] AGENTS.md (references @CLAUDE.md)"
|
|
302
|
+
else
|
|
303
|
+
append_instructions "$VAULT_DIR/AGENTS.md"
|
|
304
|
+
echo " [+] AGENTS.md"
|
|
305
|
+
fi
|
|
306
|
+
|
|
307
|
+
# Install skills into vault/.codex/skills/
|
|
308
|
+
install_skills "$VAULT_DIR" ".codex"
|
|
309
|
+
fi
|
|
310
|
+
echo ""
|
|
311
|
+
}
|
|
312
|
+
|
|
313
|
+
# --- Run setup for each detected agent ---
|
|
314
|
+
|
|
315
|
+
for agent in "${AGENTS[@]}"; do
|
|
316
|
+
"setup_$agent"
|
|
317
|
+
done
|
|
318
|
+
|
|
319
|
+
# --- Done ---
|
|
320
|
+
|
|
321
|
+
echo "=== Done ==="
|
|
322
|
+
echo ""
|
|
323
|
+
|
|
324
|
+
if [ "$MODE" = "integrated" ]; then
|
|
325
|
+
echo "Vault created at: $VAULT_DIR"
|
|
326
|
+
echo "Hooks registered at: $CONFIG_DIR/"
|
|
327
|
+
echo ""
|
|
328
|
+
echo "Next steps:"
|
|
329
|
+
echo " cd $PROJECT_DIR"
|
|
330
|
+
for agent in "${AGENTS[@]}"; do
|
|
331
|
+
case $agent in
|
|
332
|
+
claude) echo " claude # hooks + vault work out of the box" ;;
|
|
333
|
+
codex) echo " codex # hooks + vault work out of the box" ;;
|
|
334
|
+
esac
|
|
335
|
+
done
|
|
336
|
+
else
|
|
337
|
+
echo "Your vault is ready at: $VAULT_DIR"
|
|
338
|
+
echo ""
|
|
339
|
+
echo "Next steps:"
|
|
340
|
+
echo " cd $VAULT_DIR"
|
|
341
|
+
for agent in "${AGENTS[@]}"; do
|
|
342
|
+
case $agent in
|
|
343
|
+
claude) echo " claude # start with Claude Code" ;;
|
|
344
|
+
codex) echo " codex # start with Codex CLI" ;;
|
|
345
|
+
esac
|
|
346
|
+
done
|
|
347
|
+
fi
|
|
348
|
+
|
|
349
|
+
echo ""
|
|
350
|
+
echo " Fill in brain/North Star.md with your goals, then start talking."
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
# Codex-Vault — Core Instructions
|
|
2
|
+
|
|
3
|
+
A structured knowledge vault maintained by an LLM agent. You write notes, maintain links, and keep indexes current. The human curates sources, directs analysis, and asks questions.
|
|
4
|
+
|
|
5
|
+
## Vault Structure
|
|
6
|
+
|
|
7
|
+
| Folder | Purpose |
|
|
8
|
+
|--------|---------|
|
|
9
|
+
| `Home.md` | Vault entry point — quick links, current focus |
|
|
10
|
+
| `brain/` | Persistent memory — goals, decisions, patterns |
|
|
11
|
+
| `work/` | Work notes index (`Index.md`) |
|
|
12
|
+
| `work/active/` | Current projects (move to archive when done) |
|
|
13
|
+
| `work/archive/` | Completed work |
|
|
14
|
+
| `templates/` | Note templates with YAML frontmatter |
|
|
15
|
+
| `sources/` | Raw source documents — immutable, LLM reads only |
|
|
16
|
+
| `thinking/` | Scratchpad — promote findings, then delete |
|
|
17
|
+
| `reference/` | Saved answers and analyses from query writeback |
|
|
18
|
+
|
|
19
|
+
## Session Lifecycle
|
|
20
|
+
|
|
21
|
+
### Start
|
|
22
|
+
|
|
23
|
+
The SessionStart hook injects: North Star goals, recent git changes, active work, vault file listing. You start with context, not a blank slate.
|
|
24
|
+
|
|
25
|
+
### Work
|
|
26
|
+
|
|
27
|
+
1. The classify hook detects intent and suggests skills — **do not auto-execute**. Suggest the skill to the user and let them decide.
|
|
28
|
+
2. Available skills: `/dump`, `/recall`, `/ingest`, `/wrap-up`
|
|
29
|
+
3. Search before creating — check if a related note exists (use `/recall <topic>` for targeted vault search)
|
|
30
|
+
4. Update `work/Index.md` if a new note was created
|
|
31
|
+
|
|
32
|
+
### End
|
|
33
|
+
|
|
34
|
+
When the user says "wrap up" or similar:
|
|
35
|
+
1. Verify new notes have frontmatter and wikilinks
|
|
36
|
+
2. Update `work/Index.md` with any new or completed notes
|
|
37
|
+
3. Archive completed projects: move from `work/active/` to `work/archive/`
|
|
38
|
+
4. Check if `brain/` notes need updating with new decisions or patterns
|
|
39
|
+
|
|
40
|
+
## Creating Notes
|
|
41
|
+
|
|
42
|
+
1. **Always use YAML frontmatter**: `date`, `description` (~150 chars), `tags`
|
|
43
|
+
2. **Use templates** from `templates/`
|
|
44
|
+
3. **Place files correctly**: active work in `work/active/`, completed in `work/archive/`, source summaries in `work/active/` (tag: `source-summary`), drafts in `thinking/`
|
|
45
|
+
4. **Name files descriptively** — use the note title as filename
|
|
46
|
+
|
|
47
|
+
## Linking — Critical
|
|
48
|
+
|
|
49
|
+
**Graph-first.** Folders group by purpose, links group by meaning. A note lives in one folder but links to many notes.
|
|
50
|
+
|
|
51
|
+
**A note without links is a bug.** Every new note must link to at least one existing note via `[[wikilinks]]`.
|
|
52
|
+
|
|
53
|
+
Link syntax:
|
|
54
|
+
- `[[Note Title]]` — standard wikilink
|
|
55
|
+
- `[[Note Title|display text]]` — aliased
|
|
56
|
+
- `[[Note Title#Heading]]` — deep link
|
|
57
|
+
|
|
58
|
+
### When to Link
|
|
59
|
+
|
|
60
|
+
- Work note ↔ Decision Record (bidirectional)
|
|
61
|
+
- Index → all work notes
|
|
62
|
+
- North Star → active projects
|
|
63
|
+
- Memories → source notes
|
|
64
|
+
|
|
65
|
+
## Memory System
|
|
66
|
+
|
|
67
|
+
All persistent memory lives in `brain/`:
|
|
68
|
+
|
|
69
|
+
| File | Stores |
|
|
70
|
+
|------|--------|
|
|
71
|
+
| `North Star.md` | Goals and focus areas — read every session |
|
|
72
|
+
| `Memories.md` | Index of memory topics |
|
|
73
|
+
| `Key Decisions.md` | Decisions worth recalling across sessions |
|
|
74
|
+
| `Patterns.md` | Recurring patterns discovered across work |
|
|
75
|
+
|
|
76
|
+
When asked to "remember" something: write to the appropriate `brain/` file with a wikilink to context.
|
|
77
|
+
|
|
78
|
+
## Sources & Ingest
|
|
79
|
+
|
|
80
|
+
`sources/` holds raw source documents (articles, papers, web clips). This is the immutable layer — the agent reads from it but never modifies source files.
|
|
81
|
+
|
|
82
|
+
- Drop raw files into `sources/` (markdown preferred) or use `/ingest` with a URL
|
|
83
|
+
- `/ingest` reads the source, discusses key takeaways, then creates a **Source Summary** in `work/active/` with tag `source-summary`
|
|
84
|
+
- The summary uses the Source Summary template: Key Takeaways, Summary, Connections, Quotes/Data Points
|
|
85
|
+
- Every ingest updates `work/Index.md` (Sources section) and checks for cross-links to existing notes
|
|
86
|
+
- If the source contains decisions or patterns, update the relevant `brain/` notes too
|
|
87
|
+
- Source summaries link back to the raw source via the `source` frontmatter field
|
|
88
|
+
|
|
89
|
+
## Operation Log
|
|
90
|
+
|
|
91
|
+
Append to `log.md` after significant operations: ingests, decisions, project archives, maintenance passes.
|
|
92
|
+
|
|
93
|
+
- Format: `## [YYYY-MM-DD] <type> | <title>` followed by bullet points
|
|
94
|
+
- Types: `ingest`, `session`, `query`, `maintenance`, `decision`, `archive`
|
|
95
|
+
- Don't log every small edit — only operations that change the vault's knowledge state
|
|
96
|
+
- Entries are append-only; never edit or delete previous entries
|
|
97
|
+
|
|
98
|
+
## Query Writeback
|
|
99
|
+
|
|
100
|
+
When answering a substantial question that synthesizes multiple vault notes:
|
|
101
|
+
|
|
102
|
+
1. Offer: "This answer could be useful later — want me to save it as a reference note?"
|
|
103
|
+
2. If yes, create a Reference Note in `reference/` using the template
|
|
104
|
+
3. Link the reference note from related work notes in `## Related`
|
|
105
|
+
4. Add the reference note to `work/Index.md` under `## Reference`
|
|
106
|
+
5. Don't prompt for trivial questions — only for answers that synthesize, compare, or analyze
|
|
107
|
+
|
|
108
|
+
## Vault Location
|
|
109
|
+
|
|
110
|
+
The vault may live at the project root or in a `vault/` subdirectory. Use the SessionStart context to determine the actual path. All folder references above (e.g. `brain/`, `work/active/`) are relative to the vault root.
|
|
111
|
+
|
|
112
|
+
## Rules
|
|
113
|
+
|
|
114
|
+
- Preserve existing frontmatter when editing notes
|
|
115
|
+
- Always check for and suggest connections between notes
|
|
116
|
+
- Every note must have a `description` field (~150 chars)
|
|
117
|
+
- When reorganizing, never delete without user confirmation
|
|
118
|
+
- Use `[[wikilinks]]` not markdown links
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: dump
|
|
3
|
+
description: "Freeform capture — dump anything (notes, ideas, decisions, links) and it gets classified and routed to the right vault location. Triggers: 'dump this', 'capture', 'save this thought', 'note this down', 'remember this', 'jot down'."
|
|
4
|
+
license: MIT
|
|
5
|
+
metadata:
|
|
6
|
+
author: sukbearai
|
|
7
|
+
version: "1.0.0"
|
|
8
|
+
homepage: "https://github.com/sukbearai/codex-vault"
|
|
9
|
+
---
|
|
10
|
+
|
|
11
|
+
Process the following freeform dump. For each distinct piece of information:
|
|
12
|
+
|
|
13
|
+
1. **Classify** it: decision, project update, win/achievement, or general work note.
|
|
14
|
+
2. **Search first**: Check if a related note already exists. Prefer updating over creating.
|
|
15
|
+
3. **Create or update** the appropriate note:
|
|
16
|
+
- Correct folder (work/active/, brain/, etc.)
|
|
17
|
+
- Full YAML frontmatter (date, description, tags)
|
|
18
|
+
- All relevant [[wikilinks]]
|
|
19
|
+
4. **Update indexes**: `work/Index.md`, `brain/` notes as needed.
|
|
20
|
+
5. **Cross-link**: Every new note links to at least one existing note.
|
|
21
|
+
|
|
22
|
+
After processing, summarize:
|
|
23
|
+
- What was captured and where
|
|
24
|
+
- New notes created (with paths)
|
|
25
|
+
- Existing notes updated
|
|
26
|
+
- Anything unclear (ask the user)
|
|
27
|
+
|
|
28
|
+
Content to process:
|
|
29
|
+
$ARGUMENTS
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: ingest
|
|
3
|
+
description: "Import external content (URLs, files, text) into the vault as structured source notes. Triggers: 'ingest', 'import this', 'save this article', 'add source', 'read and save'."
|
|
4
|
+
license: MIT
|
|
5
|
+
metadata:
|
|
6
|
+
author: sukbearai
|
|
7
|
+
version: "1.0.0"
|
|
8
|
+
homepage: "https://github.com/sukbearai/codex-vault"
|
|
9
|
+
---
|
|
10
|
+
|
|
11
|
+
Ingest a source into the vault. Follow these steps:
|
|
12
|
+
|
|
13
|
+
### 1. Locate the Source
|
|
14
|
+
|
|
15
|
+
The user provides either:
|
|
16
|
+
- A filename in `sources/` (e.g., `sources/karpathy-llm-wiki.md`)
|
|
17
|
+
- A URL to fetch (use `defuddle parse <url> --md` or `curl` to save to `sources/` first)
|
|
18
|
+
|
|
19
|
+
If a URL, save the raw content to `sources/` before proceeding — sources are the immutable record.
|
|
20
|
+
|
|
21
|
+
### 2. Read the Source
|
|
22
|
+
|
|
23
|
+
Read the full source document. Do not skim — ingestion depends on thorough reading.
|
|
24
|
+
|
|
25
|
+
### 3. Discuss Key Takeaways
|
|
26
|
+
|
|
27
|
+
Present the top 3-5 takeaways to the user. Ask:
|
|
28
|
+
- Which points are most relevant to current work?
|
|
29
|
+
- Any connections to existing vault notes?
|
|
30
|
+
- Anything to skip or emphasize?
|
|
31
|
+
|
|
32
|
+
Wait for user input before proceeding.
|
|
33
|
+
|
|
34
|
+
### 4. Create a Source Summary
|
|
35
|
+
|
|
36
|
+
Create a note in `work/active/` using the **Source Summary** template:
|
|
37
|
+
- Fill in all YAML frontmatter (date, description, source, tags)
|
|
38
|
+
- Write Key Takeaways, Summary, Connections (with [[wikilinks]]), Quotes/Data Points
|
|
39
|
+
- The `source` field should reference the file in `sources/` or the original URL
|
|
40
|
+
|
|
41
|
+
### 5. Update Indexes
|
|
42
|
+
|
|
43
|
+
- Add the summary to `work/Index.md` under a "Sources" section (create the section if it doesn't exist)
|
|
44
|
+
- Update relevant `brain/` notes if the source contains decisions (`Key Decisions.md`), patterns (`Patterns.md`), or context worth remembering (`Memories.md`)
|
|
45
|
+
|
|
46
|
+
### 6. Cross-Link
|
|
47
|
+
|
|
48
|
+
Check existing vault notes for connections:
|
|
49
|
+
- Do any active projects relate to this source?
|
|
50
|
+
- Does the source reinforce or challenge any existing decisions?
|
|
51
|
+
- Add [[wikilinks]] in both directions where relevant
|
|
52
|
+
|
|
53
|
+
### 7. Report
|
|
54
|
+
|
|
55
|
+
Summarize what was done:
|
|
56
|
+
- Source file location
|
|
57
|
+
- Summary note created (path)
|
|
58
|
+
- Indexes updated
|
|
59
|
+
- Cross-links added
|
|
60
|
+
- Brain notes updated (if any)
|
|
61
|
+
|
|
62
|
+
Source to process:
|
|
63
|
+
$ARGUMENTS
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: recall
|
|
3
|
+
description: "Search vault memory for a topic — finds relevant notes across brain, work, reference, and sources. Triggers: 'recall', 'what do I know about', 'search memory', 'find notes about', 'look up'."
|
|
4
|
+
license: MIT
|
|
5
|
+
metadata:
|
|
6
|
+
author: sukbearai
|
|
7
|
+
version: "1.0.0"
|
|
8
|
+
homepage: "https://github.com/sukbearai/codex-vault"
|
|
9
|
+
---
|
|
10
|
+
|
|
11
|
+
Search the vault for information about the given topic.
|
|
12
|
+
|
|
13
|
+
### 1. Parse the Query
|
|
14
|
+
|
|
15
|
+
Extract the key topic or question from the user's input.
|
|
16
|
+
|
|
17
|
+
### 2. Search the Vault
|
|
18
|
+
|
|
19
|
+
Two-pass search — semantic first, keyword fallback:
|
|
20
|
+
|
|
21
|
+
**Pass 1 — Frontmatter scan (semantic):**
|
|
22
|
+
Read the first 5 lines (YAML frontmatter) of every `.md` file in the vault. Use the `description` and `tags` fields to judge relevance semantically — match by meaning, not just keywords. For example, a query about "caching" should match a note with description "Redis selection for session storage".
|
|
23
|
+
|
|
24
|
+
Scan in priority order:
|
|
25
|
+
1. `brain/` — persistent memory
|
|
26
|
+
2. `work/active/` — current projects
|
|
27
|
+
3. `reference/` — saved analyses
|
|
28
|
+
4. `work/archive/` — completed work
|
|
29
|
+
5. `sources/` — raw source documents
|
|
30
|
+
|
|
31
|
+
**Pass 2 — Keyword grep (fallback):**
|
|
32
|
+
If Pass 1 finds fewer than 2 relevant files, supplement with a keyword grep across file contents.
|
|
33
|
+
|
|
34
|
+
### 3. Read Matches
|
|
35
|
+
|
|
36
|
+
Read the top 3-5 relevant files in full. Prioritize files where the topic appears in:
|
|
37
|
+
- The description or tags (strongest signal)
|
|
38
|
+
- Headings
|
|
39
|
+
- Multiple times in the body
|
|
40
|
+
|
|
41
|
+
### 4. Synthesize
|
|
42
|
+
|
|
43
|
+
Present what the vault knows about this topic:
|
|
44
|
+
- **Found in**: list the files (as [[wikilinks]])
|
|
45
|
+
- **Summary**: synthesize the relevant information across all matches
|
|
46
|
+
- **Connections**: note any links between the matched notes
|
|
47
|
+
- **Gaps**: flag if the vault has limited or no information on this topic
|
|
48
|
+
|
|
49
|
+
### 5. Offer Writeback
|
|
50
|
+
|
|
51
|
+
If the synthesis is substantial (combines 3+ sources), offer to save it as a reference note.
|
|
52
|
+
|
|
53
|
+
Topic to recall:
|
|
54
|
+
$ARGUMENTS
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: wrap-up
|
|
3
|
+
description: "End-of-session wrap-up — commits changes, updates indexes, captures decisions made. Triggers: 'wrap up', 'end session', 'save progress', 'commit and close', 'done for today'."
|
|
4
|
+
license: MIT
|
|
5
|
+
metadata:
|
|
6
|
+
author: sukbearai
|
|
7
|
+
version: "1.0.0"
|
|
8
|
+
homepage: "https://github.com/sukbearai/codex-vault"
|
|
9
|
+
---
|
|
10
|
+
|
|
11
|
+
Session wrap-up. Review what was done and leave the vault clean.
|
|
12
|
+
|
|
13
|
+
### 1. Review
|
|
14
|
+
Scan the conversation for notes created or modified. List them all.
|
|
15
|
+
|
|
16
|
+
### 2. Verify Quality
|
|
17
|
+
For each note: frontmatter complete? At least one [[wikilink]]? Correct folder?
|
|
18
|
+
|
|
19
|
+
### 3. Check Indexes
|
|
20
|
+
- `work/Index.md` — new notes linked? Completed projects moved?
|
|
21
|
+
- `brain/Memories.md` — Recent Context updated?
|
|
22
|
+
- `brain/Key Decisions.md` — new decisions captured?
|
|
23
|
+
- `brain/Patterns.md` — new patterns observed?
|
|
24
|
+
|
|
25
|
+
### 4. Check for Orphans
|
|
26
|
+
Any new notes not linked from at least one other note?
|
|
27
|
+
|
|
28
|
+
### 5. Archive Check
|
|
29
|
+
Notes in `work/active/` that should move to `work/archive/`?
|
|
30
|
+
|
|
31
|
+
### 6. Report
|
|
32
|
+
- **Done**: what was captured
|
|
33
|
+
- **Fixed**: issues resolved
|
|
34
|
+
- **Flagged**: needs user input
|
|
35
|
+
- **Suggested**: improvements for next time
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
{
|
|
2
|
+
"hooks": {
|
|
3
|
+
"SessionStart": [
|
|
4
|
+
{
|
|
5
|
+
"matcher": "startup|resume|compact",
|
|
6
|
+
"hooks": [
|
|
7
|
+
{
|
|
8
|
+
"type": "command",
|
|
9
|
+
"command": "bash .codex-vault/hooks/session-start.sh",
|
|
10
|
+
"timeout": 30
|
|
11
|
+
}
|
|
12
|
+
]
|
|
13
|
+
}
|
|
14
|
+
],
|
|
15
|
+
"UserPromptSubmit": [
|
|
16
|
+
{
|
|
17
|
+
"hooks": [
|
|
18
|
+
{
|
|
19
|
+
"type": "command",
|
|
20
|
+
"command": "python3 .codex-vault/hooks/classify-message.py",
|
|
21
|
+
"timeout": 15
|
|
22
|
+
}
|
|
23
|
+
]
|
|
24
|
+
}
|
|
25
|
+
],
|
|
26
|
+
"PostToolUse": [
|
|
27
|
+
{
|
|
28
|
+
"matcher": "Write|Edit",
|
|
29
|
+
"hooks": [
|
|
30
|
+
{
|
|
31
|
+
"type": "command",
|
|
32
|
+
"command": "python3 .codex-vault/hooks/validate-write.py",
|
|
33
|
+
"timeout": 15
|
|
34
|
+
}
|
|
35
|
+
]
|
|
36
|
+
}
|
|
37
|
+
]
|
|
38
|
+
}
|
|
39
|
+
}
|