CVE-2026-19331 Overview
CVE-2026-19331 is a path traversal vulnerability in bazylhorsey obsidian-mcp-server version 1.0.0. The flaw resides in the readCanvas and writeCanvas functions within src/services/CanvasService.ts. An authenticated local attacker can manipulate file path input to read or write files outside the intended canvas directory. The issue is tracked as [CWE-22] Improper Limitation of a Pathname to a Restricted Directory. The project maintainer was informed through a public GitHub issue but has not responded at the time of disclosure. No patched release is currently available.
Critical Impact
A local attacker with low privileges can read or write arbitrary files reachable by the Model Context Protocol (MCP) server process, potentially exposing notes, credentials, or configuration data outside the Obsidian vault directory.
Affected Products
- bazylhorsey/obsidian-mcp-server version 1.0.0
- Function readCanvas in src/services/CanvasService.ts
- Function writeCanvas in src/services/CanvasService.ts
Discovery Timeline
- 2026-08-09 - CVE-2026-19331 published to NVD
- 2026-08-12 - Last updated in NVD database
Technical Details for CVE-2026-19331
Vulnerability Analysis
The obsidian-mcp-server project exposes an MCP server that allows AI clients to interact with an Obsidian vault. The CanvasService module implements two file operations: readCanvas retrieves canvas file contents and writeCanvas persists canvas data to disk. Both functions accept a canvas identifier or filename from the caller and join it with a base directory without normalizing the resulting path or validating that it remains inside the vault root.
Because the input is passed directly to filesystem APIs, path traversal sequences such as ../ traverse outside the intended directory. A caller can therefore reference arbitrary locations reachable by the server process. The vulnerability requires local access and low privileges, which limits its blast radius but does not eliminate the risk in shared or multi-user environments.
Root Cause
The root cause is missing canonicalization and boundary enforcement on user-supplied file names before they are concatenated with the canvas storage directory. Neither readCanvas nor writeCanvas resolves the path and verifies that the resolved location remains a descendant of the configured vault path.
Attack Vector
An attacker with local access to the MCP server sends a canvas read or write request whose identifier contains traversal segments. readCanvas returns the contents of the targeted file, while writeCanvas overwrites or creates a file at the traversed path with attacker-controlled content. See the GitHub Issue Discussion for a working proof of concept and the VulDB CVE-2026-19331 record for additional technical detail.
Detection Methods for CVE-2026-19331
Indicators of Compromise
- Canvas request payloads or MCP tool invocations containing ../, ..\\, URL-encoded %2e%2e%2f, or absolute paths in the canvas name argument.
- Files created or modified by the obsidian-mcp-server process outside the configured Obsidian vault directory.
- Unexpected reads of sensitive files such as ~/.ssh/, .env, or shell history from the account running the MCP server.
Detection Strategies
- Enable verbose logging on the MCP server and alert on any canvas identifier that contains path separators or traversal sequences.
- Monitor process-level file access from the Node.js process hosting obsidian-mcp-server and flag reads or writes outside the vault root.
- Correlate MCP tool call logs with filesystem audit events to identify traversal attempts followed by suspicious file access.
Monitoring Recommendations
- Ship filesystem audit events and MCP server logs to a central analytics platform for retention and correlation across sessions.
- Baseline the normal working set of files touched by the MCP server and alert on deviations, especially writes to dotfiles or system directories.
- Review the GitHub PoC Repository for indicators drawn from the vulnerable code paths.
How to Mitigate CVE-2026-19331
Immediate Actions Required
- Stop the obsidian-mcp-server process on multi-user systems until a fix is available, since no patch has been released.
- Restrict the operating system account running the server to the minimum filesystem scope required for the vault.
- Remove sensitive files such as SSH keys and credentials from directories reachable by the server account.
Patch Information
No vendor patch is currently available. The maintainer was notified via GitHub Issue #3 but has not responded. Track the GitHub PoC Repository for release updates and apply any fix that adds canonical path resolution and vault-root containment checks in CanvasService.ts.
Workarounds
- Run the MCP server inside a sandbox or container with a bind mount limited to the Obsidian vault directory.
- Apply a local patch that resolves the incoming canvas name with path.resolve and rejects results that do not start with the configured vault root.
- Add an allowlist of permitted canvas filenames and reject any input containing /, \\, or .. sequences before invoking filesystem APIs.
# Configuration example: run obsidian-mcp-server in a restricted container
docker run --rm \
--read-only \
--tmpfs /tmp \
-v "$HOME/ObsidianVault:/vault:rw" \
-e VAULT_PATH=/vault \
--user 1000:1000 \
--cap-drop=ALL \
obsidian-mcp-server:1.0.0
Disclaimer: This content was generated using AI. While we strive for accuracy, please verify critical information with official sources.

