Problem
Developers working on multiple projects simultaneously lose significant time context-switching. Each project has its own conventions, architecture decisions, and accumulated AI memories. When you jump from project A to project B, your AI agent starts fresh with no knowledge of project B's patterns. Maintaining a single shared memory leads to cross-contamination where advice for one project leaks into another. You need isolated contexts that activate automatically when you switch workspaces.
Solution
Step 1: Create a separate Obsidian vault per project
~/vaults/
project-alpha/
00-context/
architecture.md
conventions.md
decisions/
01-memories/
patterns.md
pitfalls.md
02-tasks/
backlog.md
current-sprint.md
CLAUDE.md
project-beta/
00-context/
01-memories/
02-tasks/
CLAUDE.md
relay.md # The routing layer
Step 2: Define the relay routing layer
The relay.md file maps workspace directories to their corresponding vault.
# Relay Routing Table
| Workspace Path | Vault | Active |
|---------------------------|--------------------------|--------|
| ~/code/alpha-app | ~/vaults/project-alpha | yes |
| ~/code/beta-api | ~/vaults/project-beta | yes |
| ~/code/shared-libs | ~/vaults/project-alpha | yes |
Step 3: Auto-load context with Claude hooks
#!/bin/bash
# .claude/hooks/session-start.sh
# Reads relay.md and loads the correct vault context
RELAY_FILE="$HOME/vaults/relay.md"
CURRENT_DIR=$(pwd)
# Find the matching vault for the current workspace
VAULT_PATH=$(awk -F'|' -v dir="$CURRENT_DIR" '
NR > 2 && $4 ~ /yes/ {
gsub(/^[ \t]+|[ \t]+$/, "", $2)
gsub(/^[ \t]+|[ \t]+$/, "", $3)
gsub("~", ENVIRON["HOME"], $2)
if (dir ~ $2) { gsub("~", ENVIRON["HOME"], $3); print $3; exit }
}
' "$RELAY_FILE")
if [ -n "$VAULT_PATH" ]; then
echo "## Project Context"
echo ""
cat "$VAULT_PATH/CLAUDE.md" 2>/dev/null
echo ""
echo "## Recent Memories"
cat "$VAULT_PATH/01-memories/patterns.md" 2>/dev/null
fi
Step 4: Update memories on session end
#!/bin/bash
# .claude/hooks/session-end.sh
# Prompt the agent to summarize learnings before exit
VAULT_PATH=$(get_vault_for_cwd) # same lookup as above
if [ -n "$VAULT_PATH" ]; then
MEMORY_FILE="$VAULT_PATH/01-memories/patterns.md"
TIMESTAMP=$(date +"%Y-%m-%d %H:%M")
echo "" >> "$MEMORY_FILE"
echo "### Session: $TIMESTAMP" >> "$MEMORY_FILE"
echo "- [Agent writes summary here via pre-exit prompt]" >> "$MEMORY_FILE"
fi
Step 5: Cross-project search via QMD
When you need to find a pattern used in another project, search across all vaults:
# QMD (Quick Markdown Search) indexes all vaults
qmd search "authentication middleware pattern" --path ~/vaults/
Why It Works
Each vault acts as an isolated memory bank so project-specific patterns, decisions, and pitfalls never leak across boundaries. The relay layer automates vault selection based on your working directory, eliminating the manual step of loading context. Claude hooks inject the right context at session start and capture learnings at session end, creating a feedback loop where the vault grows more useful over time. Cross-project search via QMD means isolation does not prevent knowledge reuse when you explicitly need it.
Context
- This pattern was inspired by developers using Clawdbot with purpose-built Obsidian vaults organized by project
- QMD by Tobias Lutke combines BM25 full-text and vector semantic search, running entirely locally
- Each vault's CLAUDE.md should describe the project's architecture, stack, and coding conventions
- For teams, the vault can live in a shared git repo so all team members' agents share the same context
- The relay.md format is deliberately simple markdown so it is human-readable and AI-parseable
- Consider adding vault-level CLAUDE.md files per subfolder for fine-grained context scoping