Skip to main content
Glama
Mergoth

second-brain-mcp

by Mergoth

second-brain-mcp

An MCP server that exposes an Obsidian vault to Claude — read, search, and write notes, capture voice thoughts into the right folder with the right frontmatter, and manage Tasks.md.

Built so the vault's filing rules live in code rather than in a prompt that can be forgotten.

Status

Phase

State

1. Local, stdio, five primitives

Done, 119 tests

2. HTTP transport + bearer auth

Done, verified locally

2b. Container image

Written but never built — no Docker daemon on the dev machine

3. Expose via DDNS + reverse proxy

Not started — needs NAS access, see Deployment

4. Semantic tools

Done

Related MCP server: Vault MCP Server

Quick start

Requires uv. Python comes from uv; the system python3 is too old.

uv sync

# Point at a COPY of your vault first. Never the real one until you trust it.
rsync -a ~/Library/CloudStorage/SynologyDrive-Mergoth/Notes/PersonalObsidian/ /tmp/vault-copy/

VAULT_PATH=/tmp/vault-copy uv run python -m second_brain_mcp

That starts the stdio server. It will refuse to start without VAULT_PATH — there is no default, deliberately, because a default is how a test run reaches the real vault.

Connect it to Claude Desktop

{
  "mcpServers": {
    "second-brain": {
      "command": "uv",
      "args": ["run", "--directory", "/Users/vladislav/work/second-brain-mcp",
               "python", "-m", "second_brain_mcp"],
      "env": { "VAULT_PATH": "/Users/vladislav/work/vault-sandbox/PersonalObsidian" }
    }
  }
}

HTTP transport

VAULT_PATH=/tmp/vault-copy MCP_AUTH_TOKEN=$(openssl rand -hex 32) \
  uv run python -m second_brain_mcp --transport http

Serves on 127.0.0.1:8000, MCP endpoint at /mcp. Every request needs Authorization: Bearer <token>; unauthenticated requests get a 401 with a WWW-Authenticate header pointing at /.well-known/oauth-protected-resource (RFC 9728).

Configuration

All configuration is environment variables. None have defaults.

Variable

Required for

Notes

VAULT_PATH

always

Absolute path to the vault root. Resolved and frozen at startup; never re-read.

MCP_AUTH_TOKEN

--transport http

Static bearer token. Compared with hmac.compare_digest.

Tools

Primitives — no vault knowledge

Tool

Signature

list_notes

(glob="**/*.md", since=None) — paths and mtimes, no bodies. Excludes dotfiles.

read_note

(path)

write_note

(path, content, mode) — mode is create | overwrite | append

search_vault

(query, scope=None) — ripgrep. Requires rg on PATH.

move_note

(from_path, to_path) — the only removal verb. There is no delete.

Semantic — encodes the vault's rules

Tool

Signature

capture_thought

(text, source, domain=None) — writes raw/thoughts/YYYY-MM-DD-HHMM-slug.md with correct frontmatter. The voice-while-driving path.

list_task_sections

() — the ## headers currently in Tasks.md, read live

add_task

(text, section, priority=None, due=None, link=None)

get_tasks

(filter=None) — structured tasks, flags overdue

append_log

(line) — appends to meta/log.md verbatim

add_task requires an explicit section and raises listing the available ones if it doesn't match. It does not guess and has no default section. This is deliberate: the vault's own CLAUDE.md says "Sections are a view, not a taxonomy. Re-sort when reality moves", so any hardcoded section table would silently misfile tasks the next time you reorganise. Call list_task_sections() first.

add_task never invents a date or priority, and reports back any marker it added that you did not state.

capture_thought rejects a domain outside the closed list (work finance legal health trips home plants smart-home projects learning) rather than inventing one.

Security model

The server is a plain local-filesystem server. Its one real control is path confinement.

  • Every caller-supplied path becomes a real path in exactly one function, vault/paths.py::resolve(). Nothing else in the package opens a file by a caller-supplied path.

  • The vault root is resolved once at startup and frozen. It is not a tool argument and cannot be changed at runtime.

  • resolve() takes one parameter. There is no bypass flag, no per-call root, no trusted-path list, no follow-symlinks toggle.

  • Containment is checked by path ancestry, never string prefix — with root /vault, the sibling /vault-evil must not pass.

  • Rejected: .., absolute paths, null bytes, empty paths, and symlinks that resolve outside the root even when the link itself lives inside the vault.

  • Glob patterns and search scopes are validated too, and the search query goes to rg after -e so it can never be parsed as a flag.

That last point is not theoretical. An early build appended the caller's query to rg as a bare positional argument, so a query of --pre=<script> executed arbitrary commands — with a model-controlled argument, which is exactly the prompt-injection threat the design exists to stop. See factory/adr/0002-single-path-resolution-chokepoint.md.

No hard delete anywhere. Archiving is move_note into raw/archive/.

Every mutation appends a line to meta/audit.log (machine-readable, append-only). That is deliberately a different file from meta/log.md, which stays human-curated so an unexplained line in it is still a usable tripwire.

Development

uv run --frozen pytest -q     # 119 tests
uv run ruff check .

Tests run against a synthetic fixture vault copied into tmp_path. An autouse guard fails the session if the resolved vault root is not under tmp_path, so the suite cannot reach a real vault.

Design documents:

  • factory/briefs/vault-mcp-server.md — why it is built this way, and what was rejected

  • factory/adr/ — binding architecture decisions

  • specs/ — what each increment builds

  • docs/initial_spec.md — the original design record

Deployment

Phase 3 is not done. What remains is NAS and browser work, not code:

  1. Fix the advertised metadata URLs first — this is a blocker, not a nicety. __main__.py calls build_auth_settings() with no arguments, so it advertises the defaults resource_url="http://127.0.0.1:8000" and issuer_url="https://auth.example.com". Behind a reverse proxy those are wrong: a remote client is told the resource lives on loopback. Make both read from the environment (e.g. MCP_RESOURCE_URL, MCP_ISSUER_URL) before exposing anything.

  2. Build the container. deploy/Dockerfile and deploy/compose.yaml are written — non-root user, read-only rootfs, ripgrep installed, port bound to 127.0.0.1 — but have never been built or run.

  3. Resolve container UID vs. vault file ownership. Tasks.md and meta/log.md are mode 600 on the real vault, so a non-root container with a mismatched UID gets EACCES on exactly the two highest-value writes while reads of raw/ keep working — a partial failure that looks like a tool bug.

  4. DSM reverse proxy, Let's Encrypt cert, rate limit, auto-block on failed auth. Never publish the container port directly.

  5. Register as a custom connector and test from Android.

On auth

docs/initial_spec.md assumed custom connectors require OAuth 2.1 with dynamic client registration. That is out of date: DCR is deprecated in the current MCP spec (Client ID Metadata Documents replace it), and static bearer tokens are first-class on Anthropic's MCP client surfaces. So this ships a static bearer.

The honest caveat: that is evidence about Anthropic's API surfaces. Whether the claude.ai custom connector UI accepts a static bearer is a product question that needs a live test. If it turns out to demand OAuth, auth.py is the only module that changes — transport and auth are confined to the entrypoint by factory/adr/0003.

Known limitations

  • The container image is unbuilt and unverified.

  • RFC 9728 metadata URLs are hardcoded defaults (see Deployment step 1).

  • list_notes(since) filters on filesystem mtime, which on a Synology-synced folder is sync time, not edit time. The vault's CLAUDE.md says created: in frontmatter is the real recency anchor.

  • No end-to-end test drives a JSON-RPC tool call over HTTP; tools are covered over stdio and via direct calls.

  • propose_wiki_page from the original spec is deliberately not built — its arguments were never specified and it serves deep work at the desk, where nothing is blocked.

  • Synology sync conflicts are not handled. Writes are atomic (temp file + os.replace), but there is no merge logic. The original spec cited conflict files as evidence this was urgent; there are none in PersonalObsidian/, so the risk is real but unproven and was not paid for.

Available Tools

10 tools
add_taskC

Add a task under an existing section in Tasks.md. section is matched case-insensitively against live headers.

ParametersJSON Schema
NameRequiredDescriptionDefault
dueNo
linkNo
textYes
sectionYes
priorityNo

Output Schema

ParametersJSON Schema
NameRequiredDescription
resultYes

TDQS

C2.8/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With no annotations, the description carries the full behavioral burden. It does disclose one real trait — section matching is case-insensitive against live headers — but says nothing about what happens if the section does not exist, where the task is inserted within the section, or whether the write is additive/reversible.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two short sentences, no filler, with the matching rule front-loaded immediately after the core action. Every sentence earns its place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness2/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

An output schema exists so return values need not be described, but for a 5-parameter mutation tool with zero annotation coverage and 0% schema coverage, the description leaves failure modes, insertion position, and four parameters entirely undocumented.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters2/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 0% across 5 parameters, and the description only touches 'section' (case-insensitive matching). The required 'text' and the optional due, link, and priority fields get no explanation of format or expected values anywhere.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb and resource ('Add a task') and names the target file and container ('under an existing section in Tasks.md'). It is clear enough to distinguish from get_tasks and list_task_sections, but it does not explicitly position itself against sibling write tools like append_log or capture_thought.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies usage by requiring an existing section, but never states when to reach for add_task versus append_log, capture_thought, or write_note. No prerequisites or exclusions are given.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

append_logC

Append an entry to human meta/log.md.

ParametersJSON Schema
NameRequiredDescriptionDefault
lineYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
resultYes

TDQS

C2.8/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With no annotations, the description carries the full disclosure burden. 'Append' implies a mutation, but it says nothing about whether the log file is created if absent, whether entries are timestamped, or what permissions are needed.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

A single front-loaded sentence with no waste. It is efficiently sized, though its brevity borders on under-specification given the disclosure burden.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

An output schema exists, so return values need not be explained. For a one-parameter append tool the description is minimally adequate, but with no annotations it should say more about file creation and entry format.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters2/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The single 'line' parameter has 0% schema description coverage, so the description must compensate but does not. It implies the argument is the log entry text, but gives no format, length, or content guidance.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb (append) and target resource (an entry in human meta/log.md), so an agent can tell what it does. It does not, however, distinguish itself from the sibling write_note, which could also add content.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

There is no when-to-use guidance, no prerequisites, and no mention of alternatives such as write_note. The agent must infer that this is for logging rather than note authoring.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

capture_thoughtC

Capture a raw thought into raw/thoughts/ with frontmatter and tags.

ParametersJSON Schema
NameRequiredDescriptionDefault
textYes
domainNo
sourceYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
resultYes

TDQS

C2.9/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations are provided, so the description carries the full burden. It does disclose useful behavior: content lands in raw/thoughts/ and is wrapped with frontmatter and tags. However, it says nothing about overwrite/duplicate handling, whether a new file is always created, or what source/domain affect.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

A single tight sentence with the key destination front-loaded and no filler. It is efficient, though the brevity contributes to the coverage gaps noted elsewhere.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness2/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

An output schema exists, so return values need not be explained, but with zero schema coverage and no annotations the description should clarify the required source and optional domain parameters. It leaves an agent guessing about the most important invocation details.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters2/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 0%, and the description names none of the three parameters (text, source, domain). 'frontmatter and tags' alludes to metadata handling but does not explain what source or domain mean or how tags are derived, so it fails to compensate for the undocumented schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb (capture) and resource (raw thought) plus the destination path raw/thoughts/, which implicitly separates it from write_note's general note writing. It does not explicitly name a sibling or contrast with write_note, so it stops short of a 5.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

There is no guidance on when to use this versus write_note, which is the obvious alternative for persisting text in the vault. The destination folder hints at a 'quick capture' workflow but no condition, prerequisite, or exclusion is stated.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

get_tasksC

Get structured tasks parsed from Tasks.md with overdue flags.

ParametersJSON Schema
NameRequiredDescriptionDefault
filterNo

Output Schema

ParametersJSON Schema
NameRequiredDescription
resultYes

TDQS

C2.8/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations exist, so the description carries the full behavioral burden. It does add useful context (data is parsed from Tasks.md, results carry overdue flags), but never states that this is a read-only operation, how parsing failures are surfaced, or how the optional filter affects behavior.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

A single front-loaded sentence with no filler; the source and the overdue-flag behavior come first. Efficient, though the terseness is partly what leaves the filter unexplained.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

An output schema exists, so return values need not be described, and for a simple one-param read tool the description is close to adequate. It falls short because the only parameter is undocumented and the parsing/read semantics of the Tasks.md source are unstated.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters2/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

One parameter ('filter') with 0% schema description coverage and no mention anywhere in the description. The agent cannot tell whether filter accepts a status, a date, a section name, or free text, which is a real gap for a tool whose sole knob is this filter.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb (Get) and resource (structured tasks) plus the source (Tasks.md) and a derived field (overdue flags). It distinguishes itself from add_task, list_task_sections, and the note-oriented siblings. Not a 5 only because 'structured tasks' is slightly vague about output shape, though the output schema covers that.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No when-to-use guidance and no alternatives named. It does not say how this differs from list_task_sections or when a caller should prefer this over that sibling, leaving the agent to infer routing from names alone.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

list_notesB

List notes matching a glob pattern. Returns paths and mtimes only, no bodies. Excludes dotfiles and dotdirs.

ParametersJSON Schema
NameRequiredDescriptionDefault
globNo**/*.md
sinceNo

Output Schema

ParametersJSON Schema
NameRequiredDescription
resultYes

TDQS

B3.1/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With no annotations, the description must carry the behavioral burden, and it does add real value: it discloses the return shape ('paths and mtimes only, no bodies') and a filtering rule (excludes dotfiles/dotdirs). It says nothing about ordering, limits, or pagination, so it's useful but incomplete for an unannotated tool.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two short sentences, zero waste, front-loading the operation and immediately qualifying the return contents and the exclusion rule.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

An output schema exists, so return-value documentation is arguably redundant, yet 'since' is left wholly undescribed in both schema and description. Adequate for a simple read-only listing but with a real gap in filter semantics.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters2/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 0%, so the description must compensate, but it only implicitly covers 'glob' and never explains 'since' (presumably an mtime cutoff) despite it being a nullable number with a default of null. Half the parameters remain uninterpretable from the description alone.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb and resource ('List notes') plus the matching mechanism ('glob pattern'), which is enough to distinguish it from read_note/write_note/move_note. It doesn't explicitly name an alternative such as search_vault, so it falls short of a 5.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

There is no when-to-use guidance, no exclusion of overlapping siblings (search_vault could plausibly return notes too), and no indication of when the 'since' filter should be used. The glob mention implies usage but says nothing about context or alternatives.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

list_task_sectionsB

List current section headers (##) in Tasks.md live from the file.

ParametersJSON Schema
NameRequiredDescriptionDefault

No parameters

Output Schema

ParametersJSON Schema
NameRequiredDescription
resultYes

TDQS

B3.3/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With no annotations, the description carries the full burden, but 'live from the file' usefully signals it reads the current on-disk state rather than a cache. It does not mention behavior when Tasks.md is missing, is empty, or has no ## sections.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

One tight sentence with the scope and source front-loaded and no filler. It is perhaps a touch terse, but nothing is wasted.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

An output schema exists so return structure is covered, and there are no parameters to explain. However, edge cases like a missing or unreadable Tasks.md file, and whether headers are returned with or without the '##' prefix, are unaddressed.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Zero parameters, so there is nothing to document and the baseline is 4. The description correctly implies no inputs are needed.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb (List) and resource (section headers in Tasks.md), so an agent knows it retrieves section headings rather than notes. It is distinguishable from note-oriented siblings, though it does not explicitly name an alternative tool.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No guidance on when to use this versus get_tasks, list_notes, or read_note. The agent must infer the use case from the resource name alone.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

move_noteC

Move a note from one path to another. Both paths are relative to vault root.

ParametersJSON Schema
NameRequiredDescriptionDefault
to_pathYes
from_pathYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
resultYes

TDQS

C2.9/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With no annotations, the description carries the full behavioral burden. It usefully discloses that paths resolve against the vault root, but is silent on the critical mutation questions: what happens if to_path already exists (overwrite, error, or merge), whether intermediate folders are created, and whether the source is deleted or copied.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two sentences, zero filler, with the core action front-loaded and the path-resolution caveat immediately after. Nothing redundant.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness2/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

An output schema exists so return values need no explanation, but this is a destructive-style mutation tool with no annotations and no description of collision or failure behavior. For a move/overwrite-capable operation, that is a significant omission an agent could get wrong.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 0%, so the description must compensate, and it does partially by establishing that both paths are vault-relative rather than absolute. However, it adds nothing about path format (extensions, folder separators), or validity constraints for either path, leaving meaningful gaps for both parameters.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb and resource ('Move a note') and names both endpoints of the operation, so it is clearly distinguishable from read_note, write_note, and list_notes in the sibling set. It stops short of explicitly contrasting itself with those siblings, but the verb 'move' carries the meaning on its own.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

There is no guidance on when to choose this tool over write_note (e.g., rename vs. content change) or any precondition such as the source note needing to exist. The agent is left to infer the use case entirely from the verb.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

read_noteB

Read the full content of a note at the given relative path.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
resultYes

TDQS

B3.1/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With no annotations provided, the description carries the full behavioral burden. It says only that the note content is read in full; it does not disclose whether this is read-only, whether any permissions are needed, whether missing paths error, or any other behavioral trait. The verb 'Read' implies no mutation, but no explicit context is added.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

A single sentence with zero filler. The essential operation and its scope are front-loaded and immediately clear.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The tool is simple (one parameter) and has an output schema, so return values need not be explained. However, the lack of usage guidance and the thin parameter semantics leave gaps for an agent choosing between this and sibling retrieval tools. The description is minimally adequate but not rich.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 0%, so the description must compensate. It adds that the path is relative and points to a note, which is useful beyond the schema's bare 'Path' title. It does not give format examples or clarify path syntax, but the added meaning is enough for a minimal 3.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb and resource: 'Read the full content of a note.' It clearly implies a single-note retrieval operation, distinguishing it from list_notes and search_vault. However, it does not explicitly name any sibling tool or state when this is preferred over alternatives.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description offers no when-to-use guidance, no prerequisites, and no alternatives. An agent must infer from the verb 'Read' that this is for retrieving a known note, but nothing routes it between read_note, list_notes, or search_vault.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

search_vaultB

Search the vault using ripgrep. Returns matching lines with file paths.

ParametersJSON Schema
NameRequiredDescriptionDefault
queryYes
scopeNo

Output Schema

ParametersJSON Schema
NameRequiredDescription
resultYes

TDQS

B3.1/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations are provided, so the description carries the full burden. Disclosing 'using ripgrep' implies regex/case-sensitive line-based matching and 'returns matching lines with file paths' describes output shape, but it omits auth requirements, result limits, and whether the search is read-only in practice.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two sentences, zero filler, with the core action front-loaded and the return format trailing it. Every clause earns its place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

An output schema exists, so return values need no elaboration, and the ripgrep mention covers the search mechanic. However, the fully undocumented 'scope' parameter and absent usage routing leave gaps for a tool with a sibling that also lists notes.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters2/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 0% and the description explains neither parameter. 'query' is self-evident from its name, but 'scope' is an undocumented optional string with a null default, leaving the agent unable to tell what values it accepts or what it constrains.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb and resource ('Search the vault') plus the underlying mechanism (ripgrep) and the return shape. This clearly separates it from read/list/move siblings, though it never names an alternative directly.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No guidance on when this tool is preferred over list_notes or read_note, nor any exclusions or prerequisites. The agent must infer that this is for pattern matching rather than enumerating or fetching files.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

write_noteC

Write content to a note. mode: 'create' | 'overwrite' | 'append'.

ParametersJSON Schema
NameRequiredDescriptionDefault
modeYes
pathYes
contentYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
resultYes

TDQS

C2.7/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations are provided, so the description carries the full burden. It does not disclose that 'overwrite' destroys existing content, that 'create' may fail on an existing path, or whether any permissions are required — the most safety-relevant facts for a write tool are absent.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two terse sentences with the core action front-loaded and the mode list appended. Efficient, though the mode list is under-explained rather than over-long.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness2/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

An output schema exists, so return values need not be described, but for a three-parameter write tool with no annotations the description omits the semantics of the destructive modes and the meaning of path/content. Not enough for an agent to call this safely.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters2/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 0%, so the description must compensate. It adds the three legal mode values (genuinely useful, since the schema has no enum), but says nothing about 'path' or 'content' format, and the mode values are listed without explaining their behavior.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb ('write') and resource ('a note'), and the mode enumeration signals the write variants. It is distinguishable from read_note/list_notes/move_note by the verb alone, but it never explicitly contrasts itself with siblings that also mutate notes.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No guidance on when to choose create vs overwrite vs append, or what happens if the target already exists or does not exist. The agent must guess which mode is appropriate for its situation.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Tool Schema Changelog

Recent tool additions, removals, and schema changes observed during successful MCP inspections.

  1. 10 tool updatesv0.1.0
    • First observedadd_task
    • First observedappend_log
    • First observedcapture_thought
    • First observedget_tasks
    • First observedlist_notes
    • First observedlist_task_sections
    • First observedmove_note
    • First observedread_note
    • First observedsearch_vault
    • First observedwrite_note

TDQS

B3.3/5.0

Scored across 10 tools

Disambiguation4/5

Tools are largely distinct: note operations (list/read/write/move), search, task management, and logging each have clear purposes. However, write_note overlaps with capture_thought and append_log (all write operations), and list_notes vs search_vault both retrieve note information, requiring careful reading to choose correctly.

Naming Consistency5/5

All tool names follow a consistent verb_noun snake_case pattern (list_notes, read_note, write_note, search_vault, move_note, capture_thought, list_task_sections, add_task, get_tasks, append_log). Minor singular/plural variation (note vs notes) exists but the pattern is predictable and readable.

Tool Count5/5

10 tools is well-scoped for a personal knowledge management server. Each tool covers a distinct function within note handling, search, task management, or logging, with no redundant tools and sufficient breadth for the domain.

Completeness3/5

Missing delete_note and update_note (write_note can overwrite but no delete), and task management lacks complete/update/delete task operations. No way to create a new task section either. These gaps will force agents to fall back to generic write_note for editing Tasks.md, which is error-prone.

Maintenance

ActivitySlowing
ResponsivenessNo issues

Related MCP Connectors

Related MCP Servers

  • F
    license
    Not graded
    quality
    C
    maintenance
    Built on Obsidian Vault, this MCP server integrates with Claude Code to provide personal knowledge management including note saving, full-text search, code graph extraction, and context resumption.
    1
    -
  • A
    license
    Not graded
    quality
    D
    maintenance
    An MCP server that gives Claude AI direct access to your Obsidian vault, enabling natural language search, note creation, file management, and automated workflows.
    3,893 npm
    10
    MIT