Skip to main content
Glama
igorilic

Obsidian MCP Server

by igorilic
README.md
# Obsidian MCP Server

An MCP (Model Context Protocol) server for integrating AI assistants with your Obsidian vault. Supports both stdio and HTTP/SSE transports for maximum compatibility.

## Features

- **Session Reports**: Automatically save coding session summaries with metadata
- **Note Management**: Create, read, append, and search notes
- **Daily Notes Integration**: Append to daily notes automatically
- **TODO Tracking**: Create and manage TODOs with priorities and due dates
- **Backlink Discovery**: Find notes that link to a specific note
- **Smart Linking**: Get suggestions for related notes based on keywords
- **Dual Transport**: Supports both stdio (direct) and HTTP/SSE (networked) modes

## Quick Start with Docker (Recommended)

The easiest way to run the server is with Docker Compose:

```bash
# Clone the repository
git clone https://github.com/igorilic/obsidian-mcp.git
cd obsidian-mcp

# Create your environment file
cp .env.example .env

# Edit .env and set your vault path
# OBSIDIAN_VAULT_HOST_PATH=/path/to/your/obsidian/vault

# Start the server
docker compose up -d

# Verify it's running
curl http://localhost:9111/health
```

The server will be available at `http://localhost:9111/mcp`.

## Installation (Local)

### Prerequisites

- Node.js 18+
- npm or pnpm

### Steps

```bash
git clone https://github.com/igorilic/obsidian-mcp.git
cd obsidian-mcp
npm install
npm run build
```

---

## Client Setup

### Claude Code (CLI)

Claude Code supports HTTP transport natively. Add to your global config at `~/.claude.json`:

```json
{
  "mcpServers": {
    "obsidian": {
      "type": "http",
      "url": "http://localhost:9111/mcp"
    }
  }
}
```

Or for stdio transport (direct, no Docker):

```json
{
  "mcpServers": {
    "obsidian": {
      "type": "stdio",
      "command": "node",
      "args": ["/path/to/obsidian-mcp/dist/index.js"],
      "env": {
        "OBSIDIAN_VAULT_PATH": "/path/to/your/obsidian/vault"
      }
    }
  }
}
```

After adding, restart Claude Code or run `/mcp` to reconnect.

---

### Claude Desktop

Claude Desktop only supports stdio transport, so use `mcp-remote` as a bridge for HTTP servers.

**Config location:**
- macOS: `~/Library/Application Support/Claude/claude_desktop_config.json`
- Windows: `%APPDATA%\Claude\claude_desktop_config.json`

**For HTTP transport (with Docker):**

```json
{
  "mcpServers": {
    "obsidian": {
      "command": "npx",
      "args": ["-y", "mcp-remote", "http://localhost:9111/mcp"]
    }
  }
}
```

**For stdio transport (direct, no Docker):**

```json
{
  "mcpServers": {
    "obsidian": {
      "command": "node",
      "args": ["/path/to/obsidian-mcp/dist/index.js"],
      "env": {
        "OBSIDIAN_VAULT_PATH": "/path/to/your/obsidian/vault"
      }
    }
  }
}
```

Restart Claude Desktop after changes.

---

### Cursor

Cursor supports MCP servers with stdio, SSE, and HTTP transports.

**Config location:**
- Global: `~/.cursor/mcp.json`
- Project: `.cursor/mcp.json`

**For stdio transport:**

```json
{
  "mcpServers": {
    "obsidian": {
      "command": "node",
      "args": ["/path/to/obsidian-mcp/dist/index.js"],
      "env": {
        "OBSIDIAN_VAULT_PATH": "/path/to/your/obsidian/vault"
      }
    }
  }
}
```

**For HTTP transport:**

```json
{
  "mcpServers": {
    "obsidian": {
      "url": "http://localhost:9111/mcp",
      "transport": "sse"
    }
  }
}
```

Or configure via UI: **File → Preferences → Cursor Settings → MCP**

Documentation: [Cursor MCP Docs](https://docs.cursor.com/context/model-context-protocol)

---

### Windsurf

Windsurf uses the same config format as Claude Desktop.

**Config location:** `~/.codeium/windsurf/mcp_config.json`

```json
{
  "mcpServers": {
    "obsidian": {
      "command": "node",
      "args": ["/path/to/obsidian-mcp/dist/index.js"],
      "env": {
        "OBSIDIAN_VAULT_PATH": "/path/to/your/obsidian/vault"
      }
    }
  }
}
```

Or configure via UI: **Windsurf Settings → Cascade → Plugins**

Documentation: [Windsurf MCP Docs](https://docs.windsurf.com/windsurf/cascade/mcp)

---

### Zed

Zed has built-in MCP support but currently only supports stdio transport (not HTTP).

**Config location:** `~/.config/zed/settings.json`

```json
{
  "context_servers": {
    "obsidian": {
      "command": {
        "path": "node",
        "args": ["/path/to/obsidian-mcp/dist/index.js"],
        "env": {
          "OBSIDIAN_VAULT_PATH": "/path/to/your/obsidian/vault"
        }
      }
    }
  }
}
```

To verify: Check the Agent Panel settings - a green indicator means the server is active.

Documentation: [Zed MCP Docs](https://zed.dev/docs/ai/mcp)

---

### VS Code with Continue

[Continue](https://continue.dev/) supports MCP servers via YAML configuration files.

**Config location:** Create `.continue/mcpServers/obsidian.yaml` in your workspace or home directory:

**For stdio transport:**

```yaml
name: Obsidian MCP Server
version: 1.0.0
schema: v1
mcpServers:
  - name: obsidian
    command: node
    args:
      - /path/to/obsidian-mcp/dist/index.js
    env:
      OBSIDIAN_VAULT_PATH: /path/to/your/obsidian/vault
```

**For HTTP transport:**

```yaml
name: Obsidian MCP Server
version: 1.0.0
schema: v1
mcpServers:
  - name: obsidian
    type: streamable-http
    url: http://localhost:9111/mcp
```

Documentation: [Continue MCP Docs](https://docs.continue.dev/customize/deep-dives/mcp)

---

### VS Code with Cline

[Cline](https://github.com/cline/cline) supports both stdio and SSE transports.

Click the **MCP Servers** icon in Cline's top navigation → **Configure** → **Advanced MCP Settings**

**For stdio transport:**

```json
{
  "mcpServers": {
    "obsidian": {
      "command": "node",
      "args": ["/path/to/obsidian-mcp/dist/index.js"],
      "env": {
        "OBSIDIAN_VAULT_PATH": "/path/to/your/obsidian/vault"
      }
    }
  }
}
```

**For SSE/HTTP transport:**

```json
{
  "mcpServers": {
    "obsidian": {
      "url": "http://localhost:9111/mcp",
      "transport": "sse"
    }
  }
}
```

Documentation: [Cline MCP Docs](https://docs.cline.bot/mcp/configuring-mcp-servers)

---

### JetBrains IDEs (IntelliJ, WebStorm, PyCharm, etc.)

JetBrains AI Assistant supports MCP servers starting from version 2025.1.

**Setup via UI:**
1. Go to **Settings → Tools → AI Assistant → Model Context Protocol (MCP)**
2. Click **+** to add a new server
3. Configure the server

**For stdio transport:**

```json
{
  "command": "node",
  "args": ["/path/to/obsidian-mcp/dist/index.js"],
  "env": {
    "OBSIDIAN_VAULT_PATH": "/path/to/your/obsidian/vault"
  }
}
```

> **Note:** MCP tools only work with "Codebase" mode enabled in the chat window.

Documentation: [JetBrains MCP Docs](https://www.jetbrains.com/help/ai-assistant/mcp.html)

---

### Generic HTTP Client

For any client supporting HTTP/SSE MCP transport:

- **Endpoint**: `http://localhost:9111/mcp`
- **Health check**: `http://localhost:9111/health`
- **Protocol**: MCP over Streamable HTTP (SSE responses)
- **Required headers**: `Accept: application/json, text/event-stream`

Example initialization request:

```bash
curl -X POST http://localhost:9111/mcp \
  -H "Content-Type: application/json" \
  -H "Accept: application/json, text/event-stream" \
  -d '{
    "jsonrpc": "2.0",
    "id": 1,
    "method": "initialize",
    "params": {
      "protocolVersion": "2024-11-05",
      "capabilities": {},
      "clientInfo": {"name": "my-client", "version": "1.0.0"}
    }
  }'
```

---

## Transport Modes

### HTTP/SSE Transport (Default for Docker)

Best for:
- Multiple clients connecting simultaneously
- Networked/remote access
- Containerized deployments

```bash
# Using Docker
docker compose up -d

# Or manually
MCP_TRANSPORT=http MCP_HTTP_PORT=3000 node dist/index.js
```

### Stdio Transport (Default for local)

Best for:
- Direct integration with IDEs
- Single client usage
- Lower latency

```bash
OBSIDIAN_VAULT_PATH=/path/to/vault node dist/index.js
```

---

## Available Tools

| Tool | Description |
|------|-------------|
| `write_session_report` | Save coding session summaries with metadata |
| `write_note` | Create or overwrite a note |
| `append_to_note` | Append content to an existing note |
| `append_to_daily_note` | Append to today's daily note |
| `search_notes` | Search notes by content, tags, or folder |
| `read_note` | Read a note's content and frontmatter |
| `list_recent_notes` | List recently modified notes |
| `find_backlinks` | Find notes linking to a specific note |
| `create_todo` | Create a TODO item |
| `link_notes` | Get suggestions for related notes |

### Tool Details

<details>
<summary><code>write_session_report</code></summary>

```typescript
{
  title: string;           // Short title (required)
  summary: string;         // Brief summary (required)
  details?: string;        // Detailed description
  files_changed?: string[]; // List of modified files
  next_steps?: string[];   // Follow-up TODOs
  tags?: string[];         // Tags for categorization
  project?: string;        // Project name
  folder?: string;         // Subfolder in Claude-Sessions
}
```
</details>

<details>
<summary><code>write_note</code></summary>

```typescript
{
  path: string;            // Relative path (required)
  content: string;         // Markdown content (required)
  title?: string;          // Note title
  tags?: string[];         // Tags
  frontmatter?: object;    // Additional frontmatter
}
```
</details>

<details>
<summary><code>search_notes</code></summary>

```typescript
{
  query: string;           // Search query (required)
  tags?: string[];         // Filter by tags
  folder?: string;         // Limit to folder
  limit?: number;          // Max results (default: 20)
}
```
</details>

<details>
<summary><code>create_todo</code></summary>

```typescript
{
  task: string;            // Task description (required)
  project?: string;        // Project tag
  priority?: string;       // "high" | "medium" | "low"
  due_date?: string;       // YYYY-MM-DD format
  context?: string;        // Additional context
  todo_file?: string;      // Target file (default: "TODOs.md")
}
```
</details>

---

## Environment Variables

| Variable | Description | Default |
|----------|-------------|---------|
| `OBSIDIAN_VAULT_PATH` | Path to Obsidian vault | Required |
| `MCP_TRANSPORT` | Transport mode: `stdio` or `http` | `stdio` |
| `MCP_HTTP_PORT` | HTTP server port (when using http transport) | `3000` |

---

## Vault Structure

The server creates/uses this structure:

```
Your Vault/
├── Claude-Sessions/           # Session reports
│   ├── project-name/         # Per-project folders
│   │   └── 2024-01-15-1430-feature-complete.md
│   └── 2024-01-15-1200-quick-fix.md
├── Daily Notes/              # Daily notes (configurable)
│   └── 2024-01-15.md
└── TODOs.md                  # TODO items
```

---

## Development

```bash
# Watch mode
npm run dev

# Build
npm run build

# Run with stdio
OBSIDIAN_VAULT_PATH=/path/to/vault npm start

# Run with HTTP
MCP_TRANSPORT=http npm start

# Docker build
docker compose build

# Docker logs
docker compose logs -f
```

---

## Troubleshooting

### "Server not initialized" error

The MCP client has a stale session. Solutions:
- **Claude Code**: Run `/mcp` to reconnect
- **Claude Desktop**: Restart the app
- **Docker**: Run `docker compose restart`

### Connection refused

Ensure the server is running:
```bash
curl http://localhost:9111/health
```

### Permission denied writing notes

If using Docker, ensure the vault is mounted with write access (`:rw` not `:ro`) in your `.env` file.

### MCP tools not appearing

1. Check server logs: `docker compose logs`
2. Verify configuration path is correct
3. Restart your IDE/client
4. For JetBrains: Ensure "Codebase" mode is enabled

### Zed shows "Server not active"

Zed doesn't support HTTP transport yet. Use stdio configuration instead.

---

## License

MIT

TDQS

A3.5/5.0

Scored across 10 tools

Disambiguation4/5

Most tools have distinct purposes, but there is some overlap between 'append_to_daily_note' and 'append_to_note' that could cause confusion, as both handle appending content. Additionally, 'create_todo' and 'write_note' might be ambiguous for creating new notes, though their specific focuses help differentiate them.

Naming Consistency4/5

The naming follows a consistent verb_noun pattern throughout, such as 'append_to_daily_note', 'read_note', and 'search_notes'. Minor deviations like 'find_backlinks' (which could be 'list_backlinks') and 'link_notes' (which suggests linking but is for suggestions) slightly break the pattern, but overall it's highly readable and predictable.

Tool Count5/5

With 10 tools, this server is well-scoped for managing an Obsidian vault, covering key operations like reading, writing, appending, searching, and listing notes. Each tool serves a clear purpose, and the count aligns well with typical MCP server ranges, avoiding bloat or thinness.

Completeness4/5

The toolset provides strong coverage for core Obsidian workflows, including CRUD operations (create, read, write, append) and utilities like search and backlinks. Minor gaps exist, such as the lack of update or delete operations for notes, which might require workarounds, but agents can handle most tasks effectively with the available tools.

Maintenance

ActivityInactive
ResponsivenessNo issues