@cyanheads/mcp-ts-core

v0.8.2 pre-1.0

Agent-native TypeScript framework for building MCP servers. Declarative definitions with auth, multi-backend storage, OpenTelemetry, and first-class support for Bun/Node/Cloudflare Workers.

public 12 tools 3 resources protocol 2025-11-25
@cyanheads/mcp-ts-core
{
  "mcpServers": {
    "mcp-ts-core": {
      "command": "bunx",
      "args": [
        "@cyanheads/mcp-ts-core@latest"
      ]
    }
  }
}
{
  "mcpServers": {
    "mcp-ts-core": {
      "type": "http",
      "url": "http://camerons-laptop.tail84327a.ts.net/mcp"
    }
  }
}
claude mcp add --transport http mcp-ts-core http://camerons-laptop.tail84327a.ts.net/mcp
curl -X POST http://camerons-laptop.tail84327a.ts.net/mcp \
  -H "Content-Type: application/json" \
  -H "MCP-Protocol-Version: 2025-11-25" \
  -d '{"jsonrpc":"2.0","id":1,"method":"initialize","params":{"protocolVersion":"2025-11-25","capabilities":{},"clientInfo":{"name":"curl","version":"1.0.0"}}}'

Tools

12

read 4

obsidian_get_note

read

Read a note from the vault. `format: "content"` returns just the raw markdown body. `format: "full"` returns a structured object with content, frontmatter, tags, and file metadata. `format: "document-map"` returns the catalog of headings, block references, and frontmatter fields. `format: "section"` returns a single heading/block/frontmatter section (requires `section`); heading sections include the full subtree under that heading, including nested headings. Works against any vault path, the active file, or a periodic note.

scope read
invocation
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "obsidian_get_note",
    "arguments": {
      "format": "<format>",
      "target": "<target>"
    }
  }
}
schema
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "format": {
      "type": "string",
      "enum": [
        "content",
        "full",
        "document-map",
        "section"
      ],
      "description": "Which projection of the note to return."
    },
    "target": {
      "oneOf": [
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "path",
              "description": "Address by vault-relative path."
            },
            "path": {
              "type": "string",
              "minLength": 1,
              "description": "Vault-relative path including extension, e.g. \"Projects/foo.md\"."
            }
          },
          "required": [
            "type",
            "path"
          ],
          "additionalProperties": false,
          "description": "Address a note by its vault-relative path."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "active",
              "description": "Address the file currently open in Obsidian."
            }
          },
          "required": [
            "type"
          ],
          "additionalProperties": false,
          "description": "Address whichever file is currently active in the Obsidian UI."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "periodic",
              "description": "Address a daily/weekly/monthly/etc. periodic note."
            },
            "period": {
              "type": "string",
              "enum": [
                "daily",
                "weekly",
                "monthly",
                "quarterly",
                "yearly"
              ],
              "description": "Periodic note granularity."
            },
            "date": {
              "description": "ISO date YYYY-MM-DD. Omit for the current period.",
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          "required": [
            "type",
            "period"
          ],
          "additionalProperties": false,
          "description": "Address a periodic note (current or dated)."
        }
      ],
      "description": "Where the note lives."
    },
    "section": {
      "description": "Required when `format` is `\"section\"`. Identifies the heading/block/frontmatter to extract.",
      "type": "object",
      "properties": {
        "type": {
          "type": "string",
          "enum": [
            "heading",
            "block",
            "frontmatter"
          ],
          "description": "Section locator kind."
        },
        "target": {
          "type": "string",
          "minLength": 1,
          "description": "Heading name (use \"::\" for nested headings), block reference (e.g. \"2d9b4a\"), or frontmatter field name."
        }
      },
      "required": [
        "type",
        "target"
      ],
      "additionalProperties": false
    }
  },
  "required": [
    "format",
    "target"
  ],
  "additionalProperties": false
}

obsidian_list_notes

read

List notes and subdirectories at a vault path. Defaults to vault root when `path` is omitted. Walks the directory tree up to `depth` levels (default 2 — top-level entries plus their immediate children, a structural overview; max 20). Pass `depth: 1` for a flat single-directory listing, or bump higher to walk deeper. Optional `extension` and `nameRegex` filters apply across the whole walk. Returns flat `entries[]` (each with `path`, `type`, optional `truncated`) plus a tree view in the rendered output. Capped at 1000 entries per call — when reached, walking stops and `excluded` is set; drill deeper by narrowing `path` to a subdirectory or applying filters.

scope read
invocation
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "obsidian_list_notes",
    "arguments": {}
  }
}
schema
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "path": {
      "description": "Vault-relative directory path. Omit for the vault root.",
      "type": "string"
    },
    "extension": {
      "description": "Only include files matching this extension, with or without leading dot. Applies to files only — directories are returned regardless.",
      "type": "string"
    },
    "nameRegex": {
      "description": "Optional ECMAScript regex (no flags) applied to entry names. Matches both files and directories; directories that fail the regex are skipped without recursing into them.",
      "type": "string"
    },
    "depth": {
      "description": "How many directory levels to walk. `1` = target directory only (no recursion); `2` (default) = target plus its immediate children — a structural overview; bump higher to drill in. Prefer narrowing `path` to a subdirectory over a high `depth` on the vault root.",
      "type": "integer",
      "minimum": 1,
      "maximum": 20
    }
  },
  "additionalProperties": false
}

obsidian_list_tags

read

List every tag found across the vault, with usage counts. Includes hierarchical parents — `work/tasks` contributes to both `work` and `work/tasks`.

scope read
invocation
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "obsidian_list_tags",
    "arguments": {}
  }
}
schema
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {},
  "additionalProperties": false
}

obsidian_search_notes

read

Search the vault. Modes: - `text`: substring match with context windows. Pass `query` as a string and optionally `pathPrefix` to filter the returned filenames. - `dataview`: a Dataview DQL query (`TABLE …`). Pass `query` as the DQL string. Use this for path/date/metadata filters; `file.mtime`, `file.path`, etc. are queryable. - `jsonlogic`: a JSONLogic tree evaluated over each note's NoteJson. Pass `logic` as a JSON object. Available `var` paths: `path` (string), `content` (string), `frontmatter.<key>` (any), `tags` (string[]), `stat.ctime` / `stat.mtime` / `stat.size` (number). Custom operators include `glob` and `regexp`. Results are capped at 100 hits; an `excluded` indicator reports the overflow. Text-mode hits are additionally clipped to `maxMatchesPerHit` matches per file (default 10); when clipped, the hit carries `truncated: true` and `totalMatches`.

scope read
invocation
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "obsidian_search_notes",
    "arguments": {
      "mode": "<mode>"
    }
  }
}
schema
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "mode": {
      "type": "string",
      "enum": [
        "text",
        "dataview",
        "jsonlogic"
      ],
      "description": "Search algorithm and request body shape."
    },
    "query": {
      "description": "For `text` mode: substring to match. For `dataview` mode: the DQL query string. Required for those modes.",
      "type": "string"
    },
    "logic": {
      "description": "JSONLogic tree. Required and only used when `mode` is `\"jsonlogic\"`.",
      "type": "object",
      "propertyNames": {
        "type": "string"
      },
      "additionalProperties": {}
    },
    "contextLength": {
      "description": "Characters of context on each side of the match (text mode only). Default 100.",
      "type": "integer",
      "exclusiveMinimum": 0,
      "maximum": 9007199254740991
    },
    "pathPrefix": {
      "description": "Filter returned filenames by prefix (text mode only, applied client-side).",
      "type": "string"
    },
    "maxMatchesPerHit": {
      "description": "Cap on match contexts returned per file in text mode. When clipped, the hit carries `truncated: true` and `totalMatches`. Default 10.",
      "type": "integer",
      "exclusiveMinimum": 0,
      "maximum": 9007199254740991
    }
  },
  "required": [
    "mode"
  ],
  "additionalProperties": false
}

write 1

obsidian_open_in_ui

writeopen-world

Open a file in the Obsidian app UI. By default fails when the path does not exist; the `failIfMissing` flag controls the open-or-create behavior.

scope write
invocation
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "obsidian_open_in_ui",
    "arguments": {
      "path": "<path>"
    }
  }
}
schema
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "path": {
      "type": "string",
      "minLength": 1,
      "description": "Vault-relative path of the file to open."
    },
    "failIfMissing": {
      "default": true,
      "description": "When true (default), fails if the file does not exist. When false, allows Obsidian to create the file on open.",
      "type": "boolean"
    },
    "newLeaf": {
      "default": false,
      "description": "Open in a new leaf (split pane) instead of the active one.",
      "type": "boolean"
    }
  },
  "required": [
    "path",
    "failIfMissing",
    "newLeaf"
  ],
  "additionalProperties": false
}

destructive 7

obsidian_write_note

destructive

Create or overwrite a note. With `section` provided, replaces just that heading/block/frontmatter section in place; otherwise writes the whole file. Whole-file writes refuse to clobber an existing note unless `overwrite: true` is set — read the note first and prefer `obsidian_patch_note` / `obsidian_append_to_note` / `obsidian_replace_in_note` for in-place edits. For heading sections, `content` is the new body; the heading line itself is preserved automatically and a leading duplicate heading is stripped.

scope write
invocation
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "obsidian_write_note",
    "arguments": {
      "target": "<target>",
      "content": "<content>"
    }
  }
}
schema
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "target": {
      "oneOf": [
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "path",
              "description": "Address by vault-relative path."
            },
            "path": {
              "type": "string",
              "minLength": 1,
              "description": "Vault-relative path including extension, e.g. \"Projects/foo.md\"."
            }
          },
          "required": [
            "type",
            "path"
          ],
          "additionalProperties": false,
          "description": "Address a note by its vault-relative path."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "active",
              "description": "Address the file currently open in Obsidian."
            }
          },
          "required": [
            "type"
          ],
          "additionalProperties": false,
          "description": "Address whichever file is currently active in the Obsidian UI."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "periodic",
              "description": "Address a daily/weekly/monthly/etc. periodic note."
            },
            "period": {
              "type": "string",
              "enum": [
                "daily",
                "weekly",
                "monthly",
                "quarterly",
                "yearly"
              ],
              "description": "Periodic note granularity."
            },
            "date": {
              "description": "ISO date YYYY-MM-DD. Omit for the current period.",
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          "required": [
            "type",
            "period"
          ],
          "additionalProperties": false,
          "description": "Address a periodic note (current or dated)."
        }
      ],
      "description": "Where the note lives."
    },
    "content": {
      "type": "string",
      "description": "Body to write. For heading sections, the new section body — do not repeat the heading line (it stays in place). Markdown unless `contentType` is `json`."
    },
    "section": {
      "description": "Optional sub-document target. When set, only this section is replaced; rest of the note is untouched.",
      "type": "object",
      "properties": {
        "type": {
          "type": "string",
          "enum": [
            "heading",
            "block",
            "frontmatter"
          ],
          "description": "Section locator kind."
        },
        "target": {
          "type": "string",
          "minLength": 1,
          "description": "Heading name (use \"::\" for nested headings), block reference (e.g. \"2d9b4a\"), or frontmatter field name."
        }
      },
      "required": [
        "type",
        "target"
      ],
      "additionalProperties": false
    },
    "contentType": {
      "default": "markdown",
      "description": "Content body format. Use \"json\" for typed frontmatter values or block-targeted table rows. JSON values must be valid JSON literals — strings need quoting (`\"\\\"draft\\\"\"`, not `\"draft\"`), and numbers/booleans/arrays/objects pass through as-is.",
      "type": "string",
      "enum": [
        "markdown",
        "json"
      ]
    },
    "overwrite": {
      "default": false,
      "description": "Whole-file mode only (ignored when `section` is set). When `false` (default), the call fails with `file_exists` if the target note already exists — read it first and use `obsidian_patch_note` / `obsidian_append_to_note` / `obsidian_replace_in_note` for in-place edits, or retry with `overwrite: true` for a deliberate full replacement.",
      "type": "boolean"
    }
  },
  "required": [
    "target",
    "content",
    "contentType",
    "overwrite"
  ],
  "additionalProperties": false
}

obsidian_append_to_note

destructive

Append content to a note. Without `section`, the body is appended to the end of the file. With `section`, the content is appended to the end of that heading/block/frontmatter. For block-reference targets, the upstream concatenates `content` adjacent to the block line without inserting a separator — include a leading newline in `content` if you want one. Set `createTargetIfMissing` to bring the target section into existence rather than failing when it does not exist.

scope write
invocation
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "obsidian_append_to_note",
    "arguments": {
      "target": "<target>",
      "content": "<content>"
    }
  }
}
schema
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "target": {
      "oneOf": [
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "path",
              "description": "Address by vault-relative path."
            },
            "path": {
              "type": "string",
              "minLength": 1,
              "description": "Vault-relative path including extension, e.g. \"Projects/foo.md\"."
            }
          },
          "required": [
            "type",
            "path"
          ],
          "additionalProperties": false,
          "description": "Address a note by its vault-relative path."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "active",
              "description": "Address the file currently open in Obsidian."
            }
          },
          "required": [
            "type"
          ],
          "additionalProperties": false,
          "description": "Address whichever file is currently active in the Obsidian UI."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "periodic",
              "description": "Address a daily/weekly/monthly/etc. periodic note."
            },
            "period": {
              "type": "string",
              "enum": [
                "daily",
                "weekly",
                "monthly",
                "quarterly",
                "yearly"
              ],
              "description": "Periodic note granularity."
            },
            "date": {
              "description": "ISO date YYYY-MM-DD. Omit for the current period.",
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          "required": [
            "type",
            "period"
          ],
          "additionalProperties": false,
          "description": "Address a periodic note (current or dated)."
        }
      ],
      "description": "Where the note lives."
    },
    "content": {
      "type": "string",
      "description": "Body to append. Markdown unless `contentType` is `json`."
    },
    "section": {
      "description": "Optional sub-document target. When set, content is appended to that section instead of the file.",
      "type": "object",
      "properties": {
        "type": {
          "type": "string",
          "enum": [
            "heading",
            "block",
            "frontmatter"
          ],
          "description": "Section locator kind."
        },
        "target": {
          "type": "string",
          "minLength": 1,
          "description": "Heading name (use \"::\" for nested headings), block reference (e.g. \"2d9b4a\"), or frontmatter field name."
        }
      },
      "required": [
        "type",
        "target"
      ],
      "additionalProperties": false
    },
    "contentType": {
      "default": "markdown",
      "description": "Content body format. Use \"json\" for typed frontmatter values or block-targeted table rows. JSON values must be valid JSON literals — strings need quoting (`\"\\\"draft\\\"\"`, not `\"draft\"`), and numbers/booleans/arrays/objects pass through as-is.",
      "type": "string",
      "enum": [
        "markdown",
        "json"
      ]
    },
    "createTargetIfMissing": {
      "default": false,
      "description": "When `section` is provided, create the section if it does not already exist (otherwise the call fails when the section is missing).",
      "type": "boolean"
    }
  },
  "required": [
    "target",
    "content",
    "contentType",
    "createTargetIfMissing"
  ],
  "additionalProperties": false
}

obsidian_patch_note

destructive

Surgical edit of a heading, block reference, or frontmatter field. Choose `operation: "append"` to add after the section, `"prepend"` to add before, or `"replace"` to swap it out. Use `obsidian_get_note` with `format: "document-map"` to discover available headings, blocks, and frontmatter fields. Nested headings need `Parent::Child` syntax.

scope write
invocation
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "obsidian_patch_note",
    "arguments": {
      "target": "<target>",
      "section": "<section>",
      "operation": "<operation>",
      "content": "<content>"
    }
  }
}
schema
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "target": {
      "oneOf": [
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "path",
              "description": "Address by vault-relative path."
            },
            "path": {
              "type": "string",
              "minLength": 1,
              "description": "Vault-relative path including extension, e.g. \"Projects/foo.md\"."
            }
          },
          "required": [
            "type",
            "path"
          ],
          "additionalProperties": false,
          "description": "Address a note by its vault-relative path."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "active",
              "description": "Address the file currently open in Obsidian."
            }
          },
          "required": [
            "type"
          ],
          "additionalProperties": false,
          "description": "Address whichever file is currently active in the Obsidian UI."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "periodic",
              "description": "Address a daily/weekly/monthly/etc. periodic note."
            },
            "period": {
              "type": "string",
              "enum": [
                "daily",
                "weekly",
                "monthly",
                "quarterly",
                "yearly"
              ],
              "description": "Periodic note granularity."
            },
            "date": {
              "description": "ISO date YYYY-MM-DD. Omit for the current period.",
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          "required": [
            "type",
            "period"
          ],
          "additionalProperties": false,
          "description": "Address a periodic note (current or dated)."
        }
      ],
      "description": "Where the note lives."
    },
    "section": {
      "type": "object",
      "properties": {
        "type": {
          "type": "string",
          "enum": [
            "heading",
            "block",
            "frontmatter"
          ],
          "description": "Section locator kind."
        },
        "target": {
          "type": "string",
          "minLength": 1,
          "description": "Heading name (use \"::\" for nested headings), block reference (e.g. \"2d9b4a\"), or frontmatter field name."
        }
      },
      "required": [
        "type",
        "target"
      ],
      "additionalProperties": false,
      "description": "Which heading/block/frontmatter field to edit."
    },
    "operation": {
      "type": "string",
      "enum": [
        "append",
        "prepend",
        "replace"
      ],
      "description": "How to apply the content relative to the section."
    },
    "content": {
      "type": "string",
      "description": "Body to insert/replace. Markdown unless `contentType` is `json`."
    },
    "contentType": {
      "default": "markdown",
      "description": "Content body format. Use \"json\" for typed frontmatter values or block-targeted table rows. JSON values must be valid JSON literals — strings need quoting (`\"\\\"draft\\\"\"`, not `\"draft\"`), and numbers/booleans/arrays/objects pass through as-is.",
      "type": "string",
      "enum": [
        "markdown",
        "json"
      ]
    },
    "patchOptions": {
      "description": "Optional flags: createTargetIfMissing, applyIfContentPreexists, trimTargetWhitespace.",
      "type": "object",
      "properties": {
        "createTargetIfMissing": {
          "default": false,
          "description": "Create the target heading/block/frontmatter field if it does not exist.",
          "type": "boolean"
        },
        "applyIfContentPreexists": {
          "default": false,
          "description": "Apply the patch even if matching content already exists in the target. Guards against double-applying.",
          "type": "boolean"
        },
        "trimTargetWhitespace": {
          "default": false,
          "description": "Trim whitespace from the target section before applying the operation.",
          "type": "boolean"
        }
      },
      "required": [
        "createTargetIfMissing",
        "applyIfContentPreexists",
        "trimTargetWhitespace"
      ],
      "additionalProperties": false
    }
  },
  "required": [
    "target",
    "section",
    "operation",
    "content",
    "contentType"
  ],
  "additionalProperties": false
}

obsidian_replace_in_note

destructive

String or regex search-replace inside a single note. The note is fetched, replacements are applied sequentially (each sees the previous one's output), and the result is written back. Use for edits that don't fit `obsidian_patch_note`'s structural targets — e.g., body-wide find-and-replace.

scope write
invocation
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "obsidian_replace_in_note",
    "arguments": {
      "target": "<target>",
      "replacements": "<replacements>"
    }
  }
}
schema
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "target": {
      "oneOf": [
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "path",
              "description": "Address by vault-relative path."
            },
            "path": {
              "type": "string",
              "minLength": 1,
              "description": "Vault-relative path including extension, e.g. \"Projects/foo.md\"."
            }
          },
          "required": [
            "type",
            "path"
          ],
          "additionalProperties": false,
          "description": "Address a note by its vault-relative path."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "active",
              "description": "Address the file currently open in Obsidian."
            }
          },
          "required": [
            "type"
          ],
          "additionalProperties": false,
          "description": "Address whichever file is currently active in the Obsidian UI."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "periodic",
              "description": "Address a daily/weekly/monthly/etc. periodic note."
            },
            "period": {
              "type": "string",
              "enum": [
                "daily",
                "weekly",
                "monthly",
                "quarterly",
                "yearly"
              ],
              "description": "Periodic note granularity."
            },
            "date": {
              "description": "ISO date YYYY-MM-DD. Omit for the current period.",
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          "required": [
            "type",
            "period"
          ],
          "additionalProperties": false,
          "description": "Address a periodic note (current or dated)."
        }
      ],
      "description": "Where the note lives."
    },
    "replacements": {
      "minItems": 1,
      "type": "array",
      "items": {
        "type": "object",
        "properties": {
          "search": {
            "type": "string",
            "minLength": 1,
            "description": "Substring or regex pattern to match."
          },
          "replace": {
            "type": "string",
            "description": "Replacement text. Empty string deletes matches."
          },
          "useRegex": {
            "default": false,
            "description": "Treat `search` as an ECMAScript regex pattern.",
            "type": "boolean"
          },
          "caseSensitive": {
            "default": true,
            "description": "When false, match case-insensitively.",
            "type": "boolean"
          },
          "wholeWord": {
            "default": false,
            "description": "Match only at word boundaries. Applies in both literal and regex modes — the search pattern is wrapped with `\\b…\\b`.",
            "type": "boolean"
          },
          "flexibleWhitespace": {
            "default": false,
            "description": "Treat any run of whitespace in `search` as matching any whitespace in the body. Literal mode only — has no effect when `useRegex: true` (express it directly with `\\s+`).",
            "type": "boolean"
          },
          "replaceAll": {
            "default": true,
            "description": "When false, only the first match is replaced.",
            "type": "boolean"
          }
        },
        "required": [
          "search",
          "replace",
          "useRegex",
          "caseSensitive",
          "wholeWord",
          "flexibleWhitespace",
          "replaceAll"
        ],
        "additionalProperties": false,
        "description": "A single search/replace operation."
      },
      "description": "Replacements to apply in array order over the evolving content."
    }
  },
  "required": [
    "target",
    "replacements"
  ],
  "additionalProperties": false
}

obsidian_manage_frontmatter

destructive

Atomic `get` / `set` / `delete` on a single frontmatter key. `set` requires `value` (any JSON-typed value: string, number, boolean, array, or object).

scope write
invocation
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "obsidian_manage_frontmatter",
    "arguments": {
      "operation": "<operation>",
      "target": "<target>",
      "key": "<key>"
    }
  }
}
schema
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "operation": {
      "type": "string",
      "enum": [
        "get",
        "set",
        "delete"
      ],
      "description": "Which mutation/read to perform on the key."
    },
    "target": {
      "oneOf": [
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "path",
              "description": "Address by vault-relative path."
            },
            "path": {
              "type": "string",
              "minLength": 1,
              "description": "Vault-relative path including extension, e.g. \"Projects/foo.md\"."
            }
          },
          "required": [
            "type",
            "path"
          ],
          "additionalProperties": false,
          "description": "Address a note by its vault-relative path."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "active",
              "description": "Address the file currently open in Obsidian."
            }
          },
          "required": [
            "type"
          ],
          "additionalProperties": false,
          "description": "Address whichever file is currently active in the Obsidian UI."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "periodic",
              "description": "Address a daily/weekly/monthly/etc. periodic note."
            },
            "period": {
              "type": "string",
              "enum": [
                "daily",
                "weekly",
                "monthly",
                "quarterly",
                "yearly"
              ],
              "description": "Periodic note granularity."
            },
            "date": {
              "description": "ISO date YYYY-MM-DD. Omit for the current period.",
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          "required": [
            "type",
            "period"
          ],
          "additionalProperties": false,
          "description": "Address a periodic note (current or dated)."
        }
      ],
      "description": "Where the note lives."
    },
    "key": {
      "type": "string",
      "minLength": 1,
      "description": "Frontmatter field name."
    },
    "value": {
      "description": "Required when `operation` is `\"set\"`. JSON-typed value to write — strings, numbers, booleans, arrays, and objects all accepted."
    }
  },
  "required": [
    "operation",
    "target",
    "key"
  ],
  "additionalProperties": false
}

obsidian_manage_tags

destructive

Add, remove, or list a note's tags. The server reconciles both representations — frontmatter `tags:` array and inline `#tag` syntax — so an `add` ensures the tag is present in the requested location(s), and a `remove` strips it. Inline `#tag` occurrences inside fenced code blocks are intentionally left alone. Inline-location additions append the new tag at the end of the file. `list` ignores the `tags` field.

scope write
invocation
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "obsidian_manage_tags",
    "arguments": {
      "target": "<target>",
      "operation": "<operation>"
    }
  }
}
schema
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "target": {
      "oneOf": [
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "path",
              "description": "Address by vault-relative path."
            },
            "path": {
              "type": "string",
              "minLength": 1,
              "description": "Vault-relative path including extension, e.g. \"Projects/foo.md\"."
            }
          },
          "required": [
            "type",
            "path"
          ],
          "additionalProperties": false,
          "description": "Address a note by its vault-relative path."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "active",
              "description": "Address the file currently open in Obsidian."
            }
          },
          "required": [
            "type"
          ],
          "additionalProperties": false,
          "description": "Address whichever file is currently active in the Obsidian UI."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "periodic",
              "description": "Address a daily/weekly/monthly/etc. periodic note."
            },
            "period": {
              "type": "string",
              "enum": [
                "daily",
                "weekly",
                "monthly",
                "quarterly",
                "yearly"
              ],
              "description": "Periodic note granularity."
            },
            "date": {
              "description": "ISO date YYYY-MM-DD. Omit for the current period.",
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          "required": [
            "type",
            "period"
          ],
          "additionalProperties": false,
          "description": "Address a periodic note (current or dated)."
        }
      ],
      "description": "Where the note lives."
    },
    "operation": {
      "type": "string",
      "enum": [
        "add",
        "remove",
        "list"
      ],
      "description": "`add` and `remove` mutate the note; `list` reads the current tag set."
    },
    "tags": {
      "description": "Tags to add or remove. Omit the leading `#`. Required for add/remove.",
      "type": "array",
      "items": {
        "type": "string",
        "minLength": 1
      }
    },
    "location": {
      "default": "both",
      "description": "Where to apply the change. Default `both` reconciles both representations.",
      "type": "string",
      "enum": [
        "frontmatter",
        "inline",
        "both"
      ]
    }
  },
  "required": [
    "target",
    "operation",
    "location"
  ],
  "additionalProperties": false
}

obsidian_delete_note

destructive

Permanently delete a note from the vault. Confirms with the user before deleting when the client supports interactive confirmation. Recovery requires the local trash in Obsidian — there is no API-level undo.

scope write
invocation
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "obsidian_delete_note",
    "arguments": {
      "target": "<target>"
    }
  }
}
schema
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "target": {
      "oneOf": [
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "path",
              "description": "Address by vault-relative path."
            },
            "path": {
              "type": "string",
              "minLength": 1,
              "description": "Vault-relative path including extension, e.g. \"Projects/foo.md\"."
            }
          },
          "required": [
            "type",
            "path"
          ],
          "additionalProperties": false,
          "description": "Address a note by its vault-relative path."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "active",
              "description": "Address the file currently open in Obsidian."
            }
          },
          "required": [
            "type"
          ],
          "additionalProperties": false,
          "description": "Address whichever file is currently active in the Obsidian UI."
        },
        {
          "type": "object",
          "properties": {
            "type": {
              "type": "string",
              "const": "periodic",
              "description": "Address a daily/weekly/monthly/etc. periodic note."
            },
            "period": {
              "type": "string",
              "enum": [
                "daily",
                "weekly",
                "monthly",
                "quarterly",
                "yearly"
              ],
              "description": "Periodic note granularity."
            },
            "date": {
              "description": "ISO date YYYY-MM-DD. Omit for the current period.",
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          "required": [
            "type",
            "period"
          ],
          "additionalProperties": false,
          "description": "Address a periodic note (current or dated)."
        }
      ],
      "description": "Which note to delete."
    }
  },
  "required": [
    "target"
  ],
  "additionalProperties": false
}

Resources

3

A note in the Obsidian vault. Returns the parsed NoteJson — content, frontmatter, tags, and stat — so clients can attach a specific note to a conversation.

uri obsidian://vault/{+path} mime application/json

All tags found in the Obsidian vault, with usage counts. Includes hierarchical parents (e.g. `work` for `work/tasks`).

uri obsidian://tags mime application/json

Server reachability, plugin version, and auth status of the Obsidian Local REST API. Reports the unauthenticated reachability info even when the API key is misconfigured; `authenticated` reflects whether the configured key is accepted by an authenticated probe.

uri obsidian://status mime application/json