Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
93 changes: 93 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -416,6 +416,99 @@ Congratulations! You have successfully run OpenViking 🎉

---

### 5. MCP Server (V1)

OpenViking provides an embedded MCP server for local agent integration.

Install MCP dependency:

```bash
pip install "openviking[mcp]"
```

Start MCP server (stdio transport, readonly by default):

```bash
openviking mcp --path ./data
```

Enable access level explicitly when needed:

```bash
openviking mcp --path ./data --access-level mutate
```

Current V1 scope:
- Transport: `stdio` only
- Runtime mode: embedded local path (`--path`)
- Access levels: `readonly`, `ingest`, `mutate`, `admin`
- Compatibility: `--enable-write` maps to `--access-level mutate`
- Readonly tools: `openviking_find`, `openviking_search`, `openviking_read`, `openviking_ls`, `openviking_abstract`, `openviking_overview`, `openviking_wait_processed`, `openviking_stat`, `openviking_tree`, `openviking_grep`, `openviking_glob`, `openviking_status`, `openviking_health`, `openviking_session_list`, `openviking_session_get`, `openviking_relation_list`
- Ingest tools: `openviking_session_create`, `openviking_session_add_message`, `openviking_session_commit`, `openviking_resource_add`, `openviking_resource_add_skill`
- Mutate tools: `openviking_relation_link`, `openviking_relation_unlink`, `openviking_fs_mkdir`, `openviking_fs_mv`
- Admin tools: `openviking_session_delete`, `openviking_fs_rm`, `openviking_pack_export`, `openviking_pack_import`
- Compatibility alias: `openviking_add_resource` is accepted as alias of `openviking_resource_add`

OpenCode example configuration:

```json
{
"mcp": {
"openviking": {
"command": "openviking",
"args": ["mcp", "--path", "./data"]
}
}
}
```

OpenCode writable configuration:

```json
{
"mcp": {
"openviking": {
"command": "openviking",
"args": ["mcp", "--path", "./data", "--access-level", "mutate"]
}
}
}
```

Codex example configuration:

```json
{
"mcpServers": {
"openviking": {
"command": "openviking",
"args": ["mcp", "--path", "./data"]
}
}
}
```

Codex writable configuration:

```json
{
"mcpServers": {
"openviking": {
"command": "openviking",
"args": ["mcp", "--path", "./data", "--access-level", "mutate"]
}
}
}
```

Production recommendation:
- Prefer readonly MCP instances by default.
- Use `ingest` for content ingestion workflows.
- Use `mutate` only when relation or filesystem mutation is required.
- Restrict `admin` to trusted environments and operators only.

---

## Server Deployment

For production environments, we recommend running OpenViking as a standalone HTTP service to provide persistent, high-performance context support for your AI Agents.
Expand Down
93 changes: 93 additions & 0 deletions README_CN.md
Original file line number Diff line number Diff line change
Expand Up @@ -292,6 +292,99 @@ Search results:

---

### 5. MCP Server(V1)

OpenViking 提供了可嵌入的 MCP Server,便于本地 Agent 工具接入。

安装 MCP 依赖:

```bash
pip install "openviking[mcp]"
```

启动 MCP Server(stdio 传输,默认只读):

```bash
openviking mcp --path ./data
```

需要写入能力时,显式开启写模式:

```bash
openviking mcp --path ./data --access-level mutate
```

当前 V1 范围:
- 传输协议:仅 `stdio`
- 运行模式:仅本地嵌入 `--path`
- 访问级别:`readonly`、`ingest`、`mutate`、`admin`
- 兼容开关:`--enable-write` 等价于 `--access-level mutate`
- 只读工具:`openviking_find`、`openviking_search`、`openviking_read`、`openviking_ls`、`openviking_abstract`、`openviking_overview`、`openviking_wait_processed`、`openviking_stat`、`openviking_tree`、`openviking_grep`、`openviking_glob`、`openviking_status`、`openviking_health`、`openviking_session_list`、`openviking_session_get`、`openviking_relation_list`
- ingest 工具:`openviking_session_create`、`openviking_session_add_message`、`openviking_session_commit`、`openviking_resource_add`、`openviking_resource_add_skill`
- mutate 工具:`openviking_relation_link`、`openviking_relation_unlink`、`openviking_fs_mkdir`、`openviking_fs_mv`
- admin 工具:`openviking_session_delete`、`openviking_fs_rm`、`openviking_pack_export`、`openviking_pack_import`
- 兼容别名:`openviking_add_resource` 可作为 `openviking_resource_add` 的别名继续调用

OpenCode 配置示例:

```json
{
"mcp": {
"openviking": {
"command": "openviking",
"args": ["mcp", "--path", "./data"]
}
}
}
```

OpenCode 可写配置示例:

```json
{
"mcp": {
"openviking": {
"command": "openviking",
"args": ["mcp", "--path", "./data", "--access-level", "mutate"]
}
}
}
```

Codex 配置示例:

```json
{
"mcpServers": {
"openviking": {
"command": "openviking",
"args": ["mcp", "--path", "./data"]
}
}
}
```

Codex 可写配置示例:

```json
{
"mcpServers": {
"openviking": {
"command": "openviking",
"args": ["mcp", "--path", "./data", "--access-level", "mutate"]
}
}
}
```

生产环境建议:
- 默认使用只读 MCP 实例。
- 内容导入场景建议使用 `ingest` 级别。
- 需要关系/文件结构变更时再使用 `mutate`。
- `admin` 仅建议在受信任环境中使用。

---

## 服务端部署

在生产环境中,我们推荐将 OpenViking 作为独立 HTTP 服务运行,以便为您的 AI Agent 提供持久化、高性能的上下文支持。
Expand Down
26 changes: 26 additions & 0 deletions openviking/mcp/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
# Copyright (c) 2026 Beijing Volcano Engine Technology Co., Ltd.
# SPDX-License-Identifier: Apache-2.0
"""MCP integration for OpenViking."""

from openviking.mcp.server import OpenVikingMCPAdapter, run_stdio_server
from openviking.mcp.permissions import (
ACCESS_LEVEL_ORDER,
MCPAccessLevel,
access_level_name,
can_access,
parse_access_level,
)
from openviking.mcp.tools import TOOL_DEFINITIONS, dispatch_tool, get_tool_definitions

__all__ = [
"TOOL_DEFINITIONS",
"get_tool_definitions",
"dispatch_tool",
"MCPAccessLevel",
"ACCESS_LEVEL_ORDER",
"parse_access_level",
"access_level_name",
"can_access",
"OpenVikingMCPAdapter",
"run_stdio_server",
]
55 changes: 55 additions & 0 deletions openviking/mcp/permissions.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
# Copyright (c) 2026 Beijing Volcano Engine Technology Co., Ltd.
# SPDX-License-Identifier: Apache-2.0
"""Access-level helpers for OpenViking MCP tools."""

from __future__ import annotations

from enum import IntEnum


class MCPAccessLevel(IntEnum):
"""Ordered access levels for MCP tool authorization."""

READONLY = 0
INGEST = 1
MUTATE = 2
ADMIN = 3


ACCESS_LEVEL_ORDER = ("readonly", "ingest", "mutate", "admin")

_ACCESS_LEVEL_BY_NAME = {
"readonly": MCPAccessLevel.READONLY,
"ingest": MCPAccessLevel.INGEST,
"mutate": MCPAccessLevel.MUTATE,
"admin": MCPAccessLevel.ADMIN,
}


def parse_access_level(value: MCPAccessLevel | str) -> MCPAccessLevel:
"""Parse access-level input into MCPAccessLevel."""
if isinstance(value, MCPAccessLevel):
return value
if isinstance(value, str):
normalized = value.strip().lower()
if normalized in _ACCESS_LEVEL_BY_NAME:
return _ACCESS_LEVEL_BY_NAME[normalized]
allowed = ", ".join(ACCESS_LEVEL_ORDER)
raise ValueError(f"Invalid access level '{value}'. Expected one of: {allowed}")


def access_level_name(value: MCPAccessLevel | str) -> str:
"""Return canonical lowercase name of an access level."""
level = parse_access_level(value)
for name, enum_value in _ACCESS_LEVEL_BY_NAME.items():
if enum_value == level:
return name
return "readonly"


def can_access(
current: MCPAccessLevel | str,
required: MCPAccessLevel | str,
) -> bool:
"""Return whether current level can access required level."""
return parse_access_level(current) >= parse_access_level(required)
Loading