Oracle Read-Only MCP Server
A read-only MCP server for Oracle databases that enables SQL queries, schema inspection, and data sampling without requiring OCI client libraries. It supports both TNS alias and direct connection modes with robust security guardrails.
README
Oracle Read-Only MCP Server
Local Python MCP server for Oracle database access using python-oracledb in thin mode only.
This server is designed to:
- run locally on demand through an MCP client
- connect to Oracle without OCI / Oracle Instant Client
- support read-only SQL queries and schema inspection
- support both
tnsnames.oraalias mode and direct host/port/service-name mode
Features
run_query(sql)- execute a single read-only
SELECTorWITH ... SELECTquery - returns columns, rows, row count, and truncation status
- execute a single read-only
preview_query(sql)- validates SQL with the same read-only guard as
run_query - returns normalized SQL without executing it
- validates SQL with the same read-only guard as
list_tables(schema?, name_pattern?)- list accessible tables
list_views(schema?, name_pattern?)- list accessible views
search_objects(name_pattern, schema?, object_types?)- search tables, views, synonyms, or other allowed object types by SQL
LIKEpattern
- search tables, views, synonyms, or other allowed object types by SQL
describe_table(table_name, schema?)- full table/view structure including type, precision/scale, defaults, and comments when available
list_columns(table_name, schema?)- lightweight column listing for quick schema inspection
get_primary_key(table_name, schema?)- list primary key columns and position order
list_foreign_keys(table_name, schema?)- list outbound foreign key relationships and referenced columns
get_table_sample(table_name, schema?, limit?)- return a capped sample of rows from a table or view
list_schemas()- list visible Oracle schemas/users
Security Model
This server rejects non-read-only SQL in application code, but the real security boundary should be the Oracle account itself.
Use a database user that only has read access.
The SQL guard allows only a single statement starting with SELECT or WITH and rejects DML, DDL, PL/SQL, and multi-statement input.
Application-level protection:
- only read-oriented MCP tools are exposed
run_query()andpreview_query()validate SQL before execution- multi-statement input is rejected
- common write and DDL keywords are rejected outside string literals
Database-level protection:
- the Oracle user should only have
CREATE SESSIONandSELECTprivileges as needed - do not use
SYSTEM,SYS, or any account with write privileges in normal use
The MCP server reduces risk, but a read-only Oracle account is what actually guarantees that writes cannot happen.
Requirements
- Python 3.10+
- Oracle database reachable over the network
- No OCI / Oracle Instant Client required
Install
python -m venv .venv
. .venv/bin/activate
pip install -e .[dev]
Configuration
Copy .env.example and set environment variables before starting the server.
TNS Alias Mode
ORACLE_CONNECTION_MODE=tns
ORACLE_TNSNAMES_PATH=/path/to/tnsnames.ora
ORACLE_DSN_ALIAS=MYDB
ORACLE_USERNAME=readonly_user
ORACLE_PASSWORD=secret
ORACLE_FETCH_MAX_ROWS=500
ORACLE_TNSNAMES_PATH points to the file itself. The server uses the file's parent directory as the Oracle Net config directory for thin-mode alias resolution.
Direct Mode
ORACLE_CONNECTION_MODE=direct
ORACLE_HOST=dbhost.example.com
ORACLE_PORT=1521
ORACLE_SERVICE_NAME=orclpdb1
ORACLE_USERNAME=readonly_user
ORACLE_PASSWORD=secret
ORACLE_FETCH_MAX_ROWS=500
Run
oracle-mcp-server
Or during development:
python -m oracle_mcp_server.server
Or use the included Makefile helpers:
make install
make test
make test-integration
make run-server
Makefile Commands
make install- create
.venv - install the project and dev dependencies
- create
make test- run the default test suite
- integration tests remain skipped
make test-integration- run the live Oracle integration tests
- requires a suitable Oracle test environment
make run-server- start the MCP server from the project virtualenv
OpenCode MCP Configuration
OpenCode uses local MCP server definitions under the mcp key in opencode.json or opencode.jsonc.
Example OpenCode config:
{
"$schema": "https://opencode.ai/config.json",
"mcp": {
"oracle_readonly": {
"type": "local",
"command": ["/absolute/path/to/oracle-mcp/.venv/bin/oracle-mcp-server"],
"cwd": "/absolute/path/to/oracle-mcp",
"enabled": true,
"environment": {
"ORACLE_CONNECTION_MODE": "tns",
"ORACLE_TNSNAMES_PATH": "/path/to/tnsnames.ora",
"ORACLE_DSN_ALIAS": "MYDB",
"ORACLE_USERNAME": "readonly_user",
"ORACLE_PASSWORD": "secret",
"ORACLE_FETCH_MAX_ROWS": "500"
}
}
}
}
Direct mode OpenCode example:
{
"$schema": "https://opencode.ai/config.json",
"mcp": {
"oracle_readonly": {
"type": "local",
"command": ["/absolute/path/to/oracle-mcp/.venv/bin/oracle-mcp-server"],
"cwd": "/absolute/path/to/oracle-mcp",
"enabled": true,
"environment": {
"ORACLE_CONNECTION_MODE": "direct",
"ORACLE_HOST": "dbhost.example.com",
"ORACLE_PORT": "1521",
"ORACLE_SERVICE_NAME": "orclpdb1",
"ORACLE_USERNAME": "readonly_user",
"ORACLE_PASSWORD": "secret",
"ORACLE_FETCH_MAX_ROWS": "500"
}
}
}
}
Once configured in OpenCode, the MCP tools are available under the oracle_readonly server namespace.
Generic MCP Client Configuration
Example for a generic client that launches a local stdio server:
{
"mcpServers": {
"oracle-readonly": {
"command": "/absolute/path/to/.venv/bin/oracle-mcp-server",
"env": {
"ORACLE_CONNECTION_MODE": "tns",
"ORACLE_TNSNAMES_PATH": "/path/to/tnsnames.ora",
"ORACLE_DSN_ALIAS": "MYDB",
"ORACLE_USERNAME": "readonly_user",
"ORACLE_PASSWORD": "secret"
}
}
}
}
Tests
pytest
Or with make:
make test
make test-integration
Default test runs exclude live Oracle integration tests.
Run the live integration suite only when you have a suitable Oracle environment available:
pytest --run-integration -m integration
Integration tests use these environment variables, with Docker-friendly defaults matching the sample Oracle XE setup:
ORACLE_TEST_HOST=127.0.0.1
ORACLE_TEST_PORT=1521
ORACLE_TEST_SERVICE_NAME=XE
ORACLE_TEST_USERNAME=system
ORACLE_TEST_PASSWORD=oracle
ORACLE_TEST_DEFAULT_SCHEMA=SYS
ORACLE_TEST_DSN_ALIAS=XETEST
ORACLE_TEST_CONNECT_TIMEOUT=15
ORACLE_TEST_PROTOCOL=tcp
This lets you keep the tests in the repo but skip them in normal development or CI unless explicitly requested.
Test coverage currently includes:
- config validation for direct and TNS modes
- SQL guard behavior for read-only validation
- connection kwargs for direct mode
tnsnames.oraparent-directory resolution, ensuring the server passes the containing directory asconfig_dir- opt-in live integration tests for direct-mode queries, metadata tools, sampling, and TNS alias resolution
There is also a live smoke-tested tests/fixtures/tnsnames.ora example used during development to validate real TNS alias resolution against Oracle XE.
推荐服务器
Baidu Map
百度地图核心API现已全面兼容MCP协议,是国内首家兼容MCP协议的地图服务商。
Playwright MCP Server
一个模型上下文协议服务器,它使大型语言模型能够通过结构化的可访问性快照与网页进行交互,而无需视觉模型或屏幕截图。
Magic Component Platform (MCP)
一个由人工智能驱动的工具,可以从自然语言描述生成现代化的用户界面组件,并与流行的集成开发环境(IDE)集成,从而简化用户界面开发流程。
Audiense Insights MCP Server
通过模型上下文协议启用与 Audiense Insights 账户的交互,从而促进营销洞察和受众数据的提取和分析,包括人口统计信息、行为和影响者互动。
VeyraX
一个单一的 MCP 工具,连接你所有喜爱的工具:Gmail、日历以及其他 40 多个工具。
graphlit-mcp-server
模型上下文协议 (MCP) 服务器实现了 MCP 客户端与 Graphlit 服务之间的集成。 除了网络爬取之外,还可以将任何内容(从 Slack 到 Gmail 再到播客订阅源)导入到 Graphlit 项目中,然后从 MCP 客户端检索相关内容。
Kagi MCP Server
一个 MCP 服务器,集成了 Kagi 搜索功能和 Claude AI,使 Claude 能够在回答需要最新信息的问题时执行实时网络搜索。
e2b-mcp-server
使用 MCP 通过 e2b 运行代码。
Neon MCP Server
用于与 Neon 管理 API 和数据库交互的 MCP 服务器
Exa MCP Server
模型上下文协议(MCP)服务器允许像 Claude 这样的 AI 助手使用 Exa AI 搜索 API 进行网络搜索。这种设置允许 AI 模型以安全和受控的方式获取实时的网络信息。