mcp-data-agent 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.env.example +18 -0
- package/.idea/jsLibraryMappings.xml +6 -0
- package/.idea/mcp_engine.iml +8 -0
- package/.idea/modules.xml +8 -0
- package/.idea/php.xml +19 -0
- package/.idea/vcs.xml +6 -0
- package/README.md +587 -0
- package/examples/basic/package.json +26 -0
- package/examples/basic/src/index.ts +107 -0
- package/examples/basic/tsconfig.json +15 -0
- package/package.json +106 -0
- package/packages/core/README.md +7 -0
- package/packages/core/package.json +38 -0
- package/packages/core/src/agent.test.ts +213 -0
- package/packages/core/src/agent.ts +373 -0
- package/packages/core/src/errors.ts +73 -0
- package/packages/core/src/index.ts +78 -0
- package/packages/core/src/permissions.ts +71 -0
- package/packages/core/src/query-safety.ts +125 -0
- package/packages/core/src/schema-safety.ts +118 -0
- package/packages/core/src/tenant.ts +58 -0
- package/packages/core/src/tool-registry.ts +61 -0
- package/packages/core/src/types.ts +250 -0
- package/packages/core/tsconfig.json +10 -0
- package/packages/mcp/README.md +7 -0
- package/packages/mcp/package.json +46 -0
- package/packages/mcp/src/index.ts +15 -0
- package/packages/mcp/src/server.ts +170 -0
- package/packages/mcp/tsconfig.json +11 -0
- package/packages/postgres/README.md +7 -0
- package/packages/postgres/package.json +46 -0
- package/packages/postgres/src/adapter.ts +358 -0
- package/packages/postgres/src/index.ts +19 -0
- package/packages/postgres/tsconfig.json +11 -0
- package/tsconfig.base.json +22 -0
- package/tsconfig.json +8 -0
- package/vitest.config.ts +14 -0
package/.env.example
ADDED
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
# =============================================================================
|
|
2
|
+
# MCP Data Agent — example environment variables
|
|
3
|
+
# Created by Arslan Habib
|
|
4
|
+
#
|
|
5
|
+
# PURPOSE:
|
|
6
|
+
# Template for local/demo configuration. Copy to `.env` and fill in values.
|
|
7
|
+
# NEVER commit a real `.env` file or production secrets to git.
|
|
8
|
+
#
|
|
9
|
+
# USAGE:
|
|
10
|
+
# cp .env.example .env
|
|
11
|
+
# =============================================================================
|
|
12
|
+
|
|
13
|
+
# PostgreSQL connection string used by examples/basic and smoke tests
|
|
14
|
+
DATABASE_URL=postgres://localhost:5432/mcp_data_agent
|
|
15
|
+
|
|
16
|
+
# Demo identity for examples/basic (replace with real session auth in production)
|
|
17
|
+
DEMO_USER_ID=demo-user
|
|
18
|
+
DEMO_TENANT_ID=gym_001
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
<?xml version="1.0" encoding="UTF-8"?>
|
|
2
|
+
<module type="WEB_MODULE" version="4">
|
|
3
|
+
<component name="NewModuleRootManager">
|
|
4
|
+
<content url="file://$MODULE_DIR$" />
|
|
5
|
+
<orderEntry type="inheritedJdk" />
|
|
6
|
+
<orderEntry type="sourceFolder" forTests="false" />
|
|
7
|
+
</component>
|
|
8
|
+
</module>
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
<?xml version="1.0" encoding="UTF-8"?>
|
|
2
|
+
<project version="4">
|
|
3
|
+
<component name="ProjectModuleManager">
|
|
4
|
+
<modules>
|
|
5
|
+
<module fileurl="file://$PROJECT_DIR$/.idea/mcp_engine.iml" filepath="$PROJECT_DIR$/.idea/mcp_engine.iml" />
|
|
6
|
+
</modules>
|
|
7
|
+
</component>
|
|
8
|
+
</project>
|
package/.idea/php.xml
ADDED
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
<?xml version="1.0" encoding="UTF-8"?>
|
|
2
|
+
<project version="4">
|
|
3
|
+
<component name="MessDetectorOptionsConfiguration">
|
|
4
|
+
<option name="transferred" value="true" />
|
|
5
|
+
</component>
|
|
6
|
+
<component name="PHPCSFixerOptionsConfiguration">
|
|
7
|
+
<option name="transferred" value="true" />
|
|
8
|
+
</component>
|
|
9
|
+
<component name="PHPCodeSnifferOptionsConfiguration">
|
|
10
|
+
<option name="highlightLevel" value="WARNING" />
|
|
11
|
+
<option name="transferred" value="true" />
|
|
12
|
+
</component>
|
|
13
|
+
<component name="PhpStanOptionsConfiguration">
|
|
14
|
+
<option name="transferred" value="true" />
|
|
15
|
+
</component>
|
|
16
|
+
<component name="PsalmOptionsConfiguration">
|
|
17
|
+
<option name="transferred" value="true" />
|
|
18
|
+
</component>
|
|
19
|
+
</project>
|
package/.idea/vcs.xml
ADDED
package/README.md
ADDED
|
@@ -0,0 +1,587 @@
|
|
|
1
|
+
# MCP Data Agent
|
|
2
|
+
|
|
3
|
+
> Open-source MCP framework for securely connecting AI assistants to application databases.
|
|
4
|
+
|
|
5
|
+
## Created by
|
|
6
|
+
|
|
7
|
+
**Arslan Habib**
|
|
8
|
+
Creator, Founder & Lead Maintainer
|
|
9
|
+
|
|
10
|
+
> MCP Data Agent is an open-source project created and maintained by Arslan Habib, designed to connect AI assistants with application data through secure, permission-aware MCP tools.
|
|
11
|
+
|
|
12
|
+
---
|
|
13
|
+
|
|
14
|
+
## Project overview
|
|
15
|
+
|
|
16
|
+
**MCP Data Agent** lets developers connect an existing application database to AI assistants through the [Model Context Protocol (MCP)](https://modelcontextprotocol.io/). Authenticated users can ask natural-language questions about their business data while the framework enforces authentication, authorization, tenant isolation, and safe tool-based access.
|
|
17
|
+
|
|
18
|
+
Example:
|
|
19
|
+
|
|
20
|
+
> How many active gym members do we have?
|
|
21
|
+
|
|
22
|
+
The system understands application context, runs controlled tools (not unrestricted SQL), respects permissions and tenancy, and returns a useful answer.
|
|
23
|
+
|
|
24
|
+
This is a **reusable framework** — not a gym-specific app. Gym examples are illustrative only.
|
|
25
|
+
|
|
26
|
+
---
|
|
27
|
+
|
|
28
|
+
## Why MCP Data Agent
|
|
29
|
+
|
|
30
|
+
| Problem | Approach |
|
|
31
|
+
| --- | --- |
|
|
32
|
+
| LLMs with raw DB access are unsafe | Controlled MCP tools + permissions |
|
|
33
|
+
| SaaS data leakage across customers | Tenant context from the session only |
|
|
34
|
+
| Role confusion (receptionist vs finance) | RBAC on every tool |
|
|
35
|
+
| Sensitive columns exposed to models | Field protection + schema redaction |
|
|
36
|
+
| One-off glue code per app | Small, typed, extensible core |
|
|
37
|
+
|
|
38
|
+
---
|
|
39
|
+
|
|
40
|
+
## Architecture
|
|
41
|
+
|
|
42
|
+
```text
|
|
43
|
+
User
|
|
44
|
+
↓
|
|
45
|
+
AI Assistant / LLM
|
|
46
|
+
↓
|
|
47
|
+
MCP Client
|
|
48
|
+
↓
|
|
49
|
+
MCP Data Agent
|
|
50
|
+
↓
|
|
51
|
+
Authentication & Authorization
|
|
52
|
+
↓
|
|
53
|
+
Business Context
|
|
54
|
+
↓
|
|
55
|
+
Query / Tool Engine
|
|
56
|
+
↓
|
|
57
|
+
Database Adapter
|
|
58
|
+
↓
|
|
59
|
+
Database
|
|
60
|
+
↓
|
|
61
|
+
Structured Result
|
|
62
|
+
↓
|
|
63
|
+
AI Response
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
The AI never receives unrestricted direct database access.
|
|
67
|
+
|
|
68
|
+
---
|
|
69
|
+
|
|
70
|
+
## Features (Phase 1)
|
|
71
|
+
|
|
72
|
+
- TypeScript-first core (`@mcp-data-agent/core`)
|
|
73
|
+
- MCP server bridge (`@mcp-data-agent/mcp`)
|
|
74
|
+
- PostgreSQL adapter (`@mcp-data-agent/postgres`)
|
|
75
|
+
- Schema inspection with sensitive-field redaction
|
|
76
|
+
- Read-only query validation (SELECT / CTE only)
|
|
77
|
+
- Auth context + RBAC permission checks
|
|
78
|
+
- Multi-tenant context derived from the host session
|
|
79
|
+
- Custom tool registration (`agent.registerTool`)
|
|
80
|
+
- Business entity definitions (`agent.defineEntity`)
|
|
81
|
+
- Audit event hooks (no secrets logged)
|
|
82
|
+
- Secure defaults: read-only, mutations opt-in
|
|
83
|
+
|
|
84
|
+
---
|
|
85
|
+
|
|
86
|
+
## Security model
|
|
87
|
+
|
|
88
|
+
Every database operation is intended to pass through:
|
|
89
|
+
|
|
90
|
+
1. Authentication
|
|
91
|
+
2. Authorization (permissions)
|
|
92
|
+
3. Tenant isolation
|
|
93
|
+
4. Schema / field redaction
|
|
94
|
+
5. Query validation
|
|
95
|
+
6. Tool permissions
|
|
96
|
+
7. Database permissions (prefer read-only credentials)
|
|
97
|
+
8. Timeouts and result-size limits
|
|
98
|
+
|
|
99
|
+
**Defaults**
|
|
100
|
+
|
|
101
|
+
- AI database access is **read-only**
|
|
102
|
+
- Destructive SQL is blocked
|
|
103
|
+
- `tenantId` from tool/AI parameters is **rejected**
|
|
104
|
+
- Sensitive columns (e.g. `password_hash`, `api_key`) are withheld
|
|
105
|
+
- Write tools require `allowMutations: true` and explicit permissions
|
|
106
|
+
|
|
107
|
+
---
|
|
108
|
+
|
|
109
|
+
## Multi-tenancy
|
|
110
|
+
|
|
111
|
+
Tenant identity must come from the authenticated application session:
|
|
112
|
+
|
|
113
|
+
```ts
|
|
114
|
+
tenant: { tenantId: "gym_001" } // from session — never from the LLM
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
A user from Tenant A must never retrieve Tenant B data. The Postgres adapter sets session GUCs (`app.tenant_id`, `app.user_id`) suitable for Row Level Security policies.
|
|
118
|
+
|
|
119
|
+
---
|
|
120
|
+
|
|
121
|
+
## Installation
|
|
122
|
+
|
|
123
|
+
**MCP Data Agent — Created by Arslan Habib**
|
|
124
|
+
|
|
125
|
+
This section covers everything you need to install and wire the library into a Node.js / TypeScript app.
|
|
126
|
+
|
|
127
|
+
### Requirements
|
|
128
|
+
|
|
129
|
+
| Requirement | Version |
|
|
130
|
+
| --- | --- |
|
|
131
|
+
| Node.js | **20+** (recommended: current LTS) |
|
|
132
|
+
| Package manager | npm, pnpm, or yarn |
|
|
133
|
+
| TypeScript (recommended) | 5.x |
|
|
134
|
+
| PostgreSQL (for the Postgres adapter) | 13+ |
|
|
135
|
+
|
|
136
|
+
Confirm Node:
|
|
137
|
+
|
|
138
|
+
```bash
|
|
139
|
+
node -v # should print v20.x or higher
|
|
140
|
+
npm -v
|
|
141
|
+
```
|
|
142
|
+
|
|
143
|
+
### Packages
|
|
144
|
+
|
|
145
|
+
Install only what you need:
|
|
146
|
+
|
|
147
|
+
| Package | Purpose |
|
|
148
|
+
| --- | --- |
|
|
149
|
+
| `@mcp-data-agent/core` | **Required** — agent, auth context, RBAC, tools, query safety |
|
|
150
|
+
| `@mcp-data-agent/postgres` | PostgreSQL database adapter |
|
|
151
|
+
| `@mcp-data-agent/mcp` | MCP server bridge for AI assistants |
|
|
152
|
+
|
|
153
|
+
### Option A — Install in your application (recommended)
|
|
154
|
+
|
|
155
|
+
From your app directory:
|
|
156
|
+
|
|
157
|
+
```bash
|
|
158
|
+
npm install @mcp-data-agent/core @mcp-data-agent/postgres @mcp-data-agent/mcp
|
|
159
|
+
```
|
|
160
|
+
|
|
161
|
+
Install **peer dependencies** (required at runtime):
|
|
162
|
+
|
|
163
|
+
```bash
|
|
164
|
+
npm install pg @modelcontextprotocol/server zod
|
|
165
|
+
```
|
|
166
|
+
|
|
167
|
+
For TypeScript projects, also install types for `pg`:
|
|
168
|
+
|
|
169
|
+
```bash
|
|
170
|
+
npm install -D @types/pg typescript
|
|
171
|
+
```
|
|
172
|
+
|
|
173
|
+
**pnpm**
|
|
174
|
+
|
|
175
|
+
```bash
|
|
176
|
+
pnpm add @mcp-data-agent/core @mcp-data-agent/postgres @mcp-data-agent/mcp
|
|
177
|
+
pnpm add pg @modelcontextprotocol/server zod
|
|
178
|
+
pnpm add -D @types/pg typescript
|
|
179
|
+
```
|
|
180
|
+
|
|
181
|
+
**yarn**
|
|
182
|
+
|
|
183
|
+
```bash
|
|
184
|
+
yarn add @mcp-data-agent/core @mcp-data-agent/postgres @mcp-data-agent/mcp
|
|
185
|
+
yarn add pg @modelcontextprotocol/server zod
|
|
186
|
+
yarn add -D @types/pg typescript
|
|
187
|
+
```
|
|
188
|
+
|
|
189
|
+
> **Note:** Until packages are published to the npm registry, use **Option B** (install from this repository) or link local workspaces.
|
|
190
|
+
|
|
191
|
+
### Option B — Install from this repository (local development)
|
|
192
|
+
|
|
193
|
+
Clone and build the monorepo:
|
|
194
|
+
|
|
195
|
+
```bash
|
|
196
|
+
git clone <your-repo-url> mcp_engine
|
|
197
|
+
cd mcp_engine
|
|
198
|
+
npm install
|
|
199
|
+
npm run build
|
|
200
|
+
npm test
|
|
201
|
+
```
|
|
202
|
+
|
|
203
|
+
#### Use the packages from another project on your machine
|
|
204
|
+
|
|
205
|
+
**npm link**
|
|
206
|
+
|
|
207
|
+
```bash
|
|
208
|
+
# In this repo, after build:
|
|
209
|
+
cd packages/core && npm link
|
|
210
|
+
cd ../postgres && npm link
|
|
211
|
+
cd ../mcp && npm link
|
|
212
|
+
|
|
213
|
+
# In your application:
|
|
214
|
+
npm link @mcp-data-agent/core @mcp-data-agent/postgres @mcp-data-agent/mcp
|
|
215
|
+
npm install pg @modelcontextprotocol/server zod
|
|
216
|
+
```
|
|
217
|
+
|
|
218
|
+
**Or point `package.json` at local paths**
|
|
219
|
+
|
|
220
|
+
```json
|
|
221
|
+
{
|
|
222
|
+
"dependencies": {
|
|
223
|
+
"@mcp-data-agent/core": "file:../mcp_engine/packages/core",
|
|
224
|
+
"@mcp-data-agent/postgres": "file:../mcp_engine/packages/postgres",
|
|
225
|
+
"@mcp-data-agent/mcp": "file:../mcp_engine/packages/mcp",
|
|
226
|
+
"pg": "^8.14.0",
|
|
227
|
+
"@modelcontextprotocol/server": "^2.0.0",
|
|
228
|
+
"zod": "^4.0.0"
|
|
229
|
+
}
|
|
230
|
+
}
|
|
231
|
+
```
|
|
232
|
+
|
|
233
|
+
Then in your app:
|
|
234
|
+
|
|
235
|
+
```bash
|
|
236
|
+
npm install
|
|
237
|
+
```
|
|
238
|
+
|
|
239
|
+
### Peer dependencies explained
|
|
240
|
+
|
|
241
|
+
| Peer | Used by | Why |
|
|
242
|
+
| --- | --- | --- |
|
|
243
|
+
| `pg` | `@mcp-data-agent/postgres` | PostgreSQL driver |
|
|
244
|
+
| `@modelcontextprotocol/server` | `@mcp-data-agent/mcp` | Official MCP TypeScript SDK (v2) |
|
|
245
|
+
| `zod` | `@mcp-data-agent/mcp` | Tool input schemas for MCP |
|
|
246
|
+
|
|
247
|
+
These are peers so your app controls versions and avoids duplicate drivers.
|
|
248
|
+
|
|
249
|
+
### Environment configuration
|
|
250
|
+
|
|
251
|
+
Copy the example env file when working from this repo:
|
|
252
|
+
|
|
253
|
+
```bash
|
|
254
|
+
cp .env.example .env
|
|
255
|
+
```
|
|
256
|
+
|
|
257
|
+
Set at least:
|
|
258
|
+
|
|
259
|
+
```bash
|
|
260
|
+
DATABASE_URL=postgres://USER:PASSWORD@localhost:5432/YOUR_DATABASE
|
|
261
|
+
```
|
|
262
|
+
|
|
263
|
+
Prefer a **read-only** database user for AI/analytical access. Never commit real credentials or `.env` files.
|
|
264
|
+
|
|
265
|
+
### TypeScript setup
|
|
266
|
+
|
|
267
|
+
Use ESM-friendly settings (packages ship as `"type": "module"`):
|
|
268
|
+
|
|
269
|
+
```json
|
|
270
|
+
{
|
|
271
|
+
"compilerOptions": {
|
|
272
|
+
"target": "ES2022",
|
|
273
|
+
"module": "NodeNext",
|
|
274
|
+
"moduleResolution": "NodeNext",
|
|
275
|
+
"strict": true,
|
|
276
|
+
"esModuleInterop": true,
|
|
277
|
+
"types": ["node"]
|
|
278
|
+
}
|
|
279
|
+
}
|
|
280
|
+
```
|
|
281
|
+
|
|
282
|
+
### Verify the installation
|
|
283
|
+
|
|
284
|
+
Create a small smoke file (e.g. `smoke.mjs` or `smoke.ts`):
|
|
285
|
+
|
|
286
|
+
```ts
|
|
287
|
+
import { createMCPDataAgent, Permissions } from "@mcp-data-agent/core";
|
|
288
|
+
import { createPostgresAdapter } from "@mcp-data-agent/postgres";
|
|
289
|
+
|
|
290
|
+
const database = createPostgresAdapter({
|
|
291
|
+
connectionString: process.env.DATABASE_URL!,
|
|
292
|
+
});
|
|
293
|
+
|
|
294
|
+
const agent = createMCPDataAgent({
|
|
295
|
+
database,
|
|
296
|
+
resolveContext: () => ({
|
|
297
|
+
auth: {
|
|
298
|
+
userId: "install-check",
|
|
299
|
+
permissions: [Permissions.DATABASE_SCHEMA],
|
|
300
|
+
},
|
|
301
|
+
tenant: { tenantId: "gym_001" },
|
|
302
|
+
}),
|
|
303
|
+
});
|
|
304
|
+
|
|
305
|
+
const schema = await agent.invokeTool("database.schema");
|
|
306
|
+
console.log("Installed OK — tables:", schema.schema.tables.length);
|
|
307
|
+
await database.close?.();
|
|
308
|
+
```
|
|
309
|
+
|
|
310
|
+
Run it (with `DATABASE_URL` set):
|
|
311
|
+
|
|
312
|
+
```bash
|
|
313
|
+
npx tsx smoke.ts
|
|
314
|
+
# or, after compiling: node dist/smoke.js
|
|
315
|
+
```
|
|
316
|
+
|
|
317
|
+
### Run the included example
|
|
318
|
+
|
|
319
|
+
From the monorepo root:
|
|
320
|
+
|
|
321
|
+
```bash
|
|
322
|
+
npm install
|
|
323
|
+
npm run build
|
|
324
|
+
cp .env.example .env # edit DATABASE_URL
|
|
325
|
+
npm start -w @mcp-data-agent/example-basic
|
|
326
|
+
```
|
|
327
|
+
|
|
328
|
+
The example starts an MCP server over stdio. Point your MCP client (e.g. Cursor) at that command.
|
|
329
|
+
|
|
330
|
+
### Troubleshooting
|
|
331
|
+
|
|
332
|
+
| Problem | Fix |
|
|
333
|
+
| --- | --- |
|
|
334
|
+
| `Cannot find module '@mcp-data-agent/...'` | Run `npm run build` in the monorepo, or use `file:` / `npm link` correctly |
|
|
335
|
+
| Peer dependency warnings | Install `pg`, `@modelcontextprotocol/server`, and `zod` in your app |
|
|
336
|
+
| `ECONNREFUSED` on Postgres | Check `DATABASE_URL`, that Postgres is running, and network/firewall |
|
|
337
|
+
| Node version errors | Upgrade to Node.js 20+ |
|
|
338
|
+
| ESM / `require` errors | Use `"type": "module"` or import from ESM entry points |
|
|
339
|
+
|
|
340
|
+
### Minimal install (core only)
|
|
341
|
+
|
|
342
|
+
If you only need the agent API and will supply your own adapter:
|
|
343
|
+
|
|
344
|
+
```bash
|
|
345
|
+
npm install @mcp-data-agent/core
|
|
346
|
+
```
|
|
347
|
+
|
|
348
|
+
You must implement `DatabaseAdapter` yourself (see [Database adapters](#database-adapters)).
|
|
349
|
+
|
|
350
|
+
---
|
|
351
|
+
|
|
352
|
+
## Quick start
|
|
353
|
+
|
|
354
|
+
```ts
|
|
355
|
+
import { createMCPDataAgent, Permissions } from "@mcp-data-agent/core";
|
|
356
|
+
import { createPostgresAdapter } from "@mcp-data-agent/postgres";
|
|
357
|
+
import { createMcpDataAgentServer } from "@mcp-data-agent/mcp";
|
|
358
|
+
import { StdioServerTransport } from "@modelcontextprotocol/server/stdio";
|
|
359
|
+
|
|
360
|
+
const database = createPostgresAdapter({
|
|
361
|
+
connectionString: process.env.DATABASE_URL!,
|
|
362
|
+
});
|
|
363
|
+
|
|
364
|
+
const agent = createMCPDataAgent({
|
|
365
|
+
database,
|
|
366
|
+
resolveContext: async () => ({
|
|
367
|
+
// Wire this to your real auth/session middleware
|
|
368
|
+
auth: {
|
|
369
|
+
userId: "user_123",
|
|
370
|
+
permissions: [
|
|
371
|
+
Permissions.DATABASE_SCHEMA,
|
|
372
|
+
Permissions.DATABASE_QUERY,
|
|
373
|
+
"members.read",
|
|
374
|
+
],
|
|
375
|
+
},
|
|
376
|
+
tenant: { tenantId: "gym_001" },
|
|
377
|
+
}),
|
|
378
|
+
audit: (event) => console.error("[audit]", event),
|
|
379
|
+
});
|
|
380
|
+
|
|
381
|
+
agent
|
|
382
|
+
.defineEntity({
|
|
383
|
+
name: "Member",
|
|
384
|
+
table: "members",
|
|
385
|
+
description: "A person registered at the gym",
|
|
386
|
+
})
|
|
387
|
+
.protectField({ table: "members", column: "password_hash" });
|
|
388
|
+
|
|
389
|
+
const server = createMcpDataAgentServer({ agent });
|
|
390
|
+
await server.connect(new StdioServerTransport());
|
|
391
|
+
```
|
|
392
|
+
|
|
393
|
+
See `examples/basic` for a runnable sketch.
|
|
394
|
+
|
|
395
|
+
---
|
|
396
|
+
|
|
397
|
+
## Configuration
|
|
398
|
+
|
|
399
|
+
| Option | Description |
|
|
400
|
+
| --- | --- |
|
|
401
|
+
| `database` | `DatabaseAdapter` implementation |
|
|
402
|
+
| `resolveContext` | Returns `auth` + `tenant` per request |
|
|
403
|
+
| `defaultLimit` | Max rows (default `100`) |
|
|
404
|
+
| `defaultTimeoutMs` | Query timeout (default `10000`) |
|
|
405
|
+
| `protectedFields` | Extra columns to redact |
|
|
406
|
+
| `audit` | Audit logger callback |
|
|
407
|
+
| `allowMutations` | Enable explicit write tools (default `false`) |
|
|
408
|
+
|
|
409
|
+
Use environment variables for secrets. Never commit credentials.
|
|
410
|
+
|
|
411
|
+
---
|
|
412
|
+
|
|
413
|
+
## MCP integration
|
|
414
|
+
|
|
415
|
+
Built-in MCP tools:
|
|
416
|
+
|
|
417
|
+
| MCP tool | Agent tool | Permission |
|
|
418
|
+
| --- | --- | --- |
|
|
419
|
+
| `database_schema` | `database.schema` | `database.schema` |
|
|
420
|
+
| `database_query` | `database.query` | `database.query` |
|
|
421
|
+
|
|
422
|
+
Custom tools registered on the agent are exposed with dots replaced by underscores (e.g. `members.statistics` → `members_statistics`).
|
|
423
|
+
|
|
424
|
+
---
|
|
425
|
+
|
|
426
|
+
## Database adapters
|
|
427
|
+
|
|
428
|
+
| Package | Status |
|
|
429
|
+
| --- | --- |
|
|
430
|
+
| `@mcp-data-agent/postgres` | Phase 1 |
|
|
431
|
+
| `@mcp-data-agent/mysql` | Planned |
|
|
432
|
+
| `@mcp-data-agent/mongodb` | Planned |
|
|
433
|
+
|
|
434
|
+
Adapter contract:
|
|
435
|
+
|
|
436
|
+
```ts
|
|
437
|
+
interface DatabaseAdapter {
|
|
438
|
+
getSchema(): Promise<DatabaseSchema>;
|
|
439
|
+
query(request: QueryRequest, context: RequestContext): Promise<QueryResult>;
|
|
440
|
+
}
|
|
441
|
+
```
|
|
442
|
+
|
|
443
|
+
---
|
|
444
|
+
|
|
445
|
+
## Authentication
|
|
446
|
+
|
|
447
|
+
The host application authenticates users. MCP Data Agent receives an `AuthContext`:
|
|
448
|
+
|
|
449
|
+
```ts
|
|
450
|
+
{
|
|
451
|
+
userId: string;
|
|
452
|
+
permissions: string[];
|
|
453
|
+
roles?: string[];
|
|
454
|
+
sessionId?: string;
|
|
455
|
+
}
|
|
456
|
+
```
|
|
457
|
+
|
|
458
|
+
The framework does not replace your identity provider — it consumes the session you already trust.
|
|
459
|
+
|
|
460
|
+
---
|
|
461
|
+
|
|
462
|
+
## Authorization
|
|
463
|
+
|
|
464
|
+
Example permissions:
|
|
465
|
+
|
|
466
|
+
```text
|
|
467
|
+
members.read
|
|
468
|
+
members.write
|
|
469
|
+
attendance.read
|
|
470
|
+
employees.read
|
|
471
|
+
revenue.read
|
|
472
|
+
expenses.read
|
|
473
|
+
reports.read
|
|
474
|
+
database.schema
|
|
475
|
+
database.query
|
|
476
|
+
```
|
|
477
|
+
|
|
478
|
+
Tools declare a required permission. A receptionist with `members.read` + `attendance.read` does not automatically receive `revenue.read`.
|
|
479
|
+
|
|
480
|
+
---
|
|
481
|
+
|
|
482
|
+
## Examples
|
|
483
|
+
|
|
484
|
+
- `examples/basic` — Postgres + MCP stdio server sketch
|
|
485
|
+
- Domain tools such as `members.statistics` show how to prefer constrained tools over free-form SQL
|
|
486
|
+
|
|
487
|
+
---
|
|
488
|
+
|
|
489
|
+
## AI contexts (roadmap)
|
|
490
|
+
|
|
491
|
+
| Context | Purpose | Example shape |
|
|
492
|
+
| --- | --- | --- |
|
|
493
|
+
| Decision | “What needs my attention?” | Actionable cards |
|
|
494
|
+
| Report | “Customer aging” | `{ type: "table", columns, rows }` |
|
|
495
|
+
| Graph | “Revenue vs expenses” | `{ type: "chart", chart: "line", series }` |
|
|
496
|
+
|
|
497
|
+
Phase 1 focuses on secure schema + query tools. Structured decision/report/graph contexts land in Phase 2.
|
|
498
|
+
|
|
499
|
+
---
|
|
500
|
+
|
|
501
|
+
## Custom tools
|
|
502
|
+
|
|
503
|
+
```ts
|
|
504
|
+
agent.registerTool({
|
|
505
|
+
name: "payments.overdue",
|
|
506
|
+
description: "List overdue payments for the current tenant",
|
|
507
|
+
permission: "payments.read",
|
|
508
|
+
handler: async (_input, context) => {
|
|
509
|
+
// Use context.tenant.tenantId from the session
|
|
510
|
+
return { items: [] };
|
|
511
|
+
},
|
|
512
|
+
});
|
|
513
|
+
```
|
|
514
|
+
|
|
515
|
+
---
|
|
516
|
+
|
|
517
|
+
## Development
|
|
518
|
+
|
|
519
|
+
```bash
|
|
520
|
+
npm install
|
|
521
|
+
npm run build
|
|
522
|
+
npm run typecheck
|
|
523
|
+
npm test
|
|
524
|
+
```
|
|
525
|
+
|
|
526
|
+
Packages:
|
|
527
|
+
|
|
528
|
+
```text
|
|
529
|
+
packages/core @mcp-data-agent/core
|
|
530
|
+
packages/mcp @mcp-data-agent/mcp
|
|
531
|
+
packages/postgres @mcp-data-agent/postgres
|
|
532
|
+
```
|
|
533
|
+
|
|
534
|
+
---
|
|
535
|
+
|
|
536
|
+
## Testing
|
|
537
|
+
|
|
538
|
+
Unit tests live next to source (`*.test.ts`) and run with Vitest:
|
|
539
|
+
|
|
540
|
+
```bash
|
|
541
|
+
npm test
|
|
542
|
+
```
|
|
543
|
+
|
|
544
|
+
---
|
|
545
|
+
|
|
546
|
+
## Roadmap
|
|
547
|
+
|
|
548
|
+
**Phase 1 (current)** — Core, MCP server, PostgreSQL, schema inspection, read-only queries, auth context, RBAC, tenant isolation
|
|
549
|
+
|
|
550
|
+
**Phase 2** — MySQL, MongoDB, richer business entities, report/graph/decision contexts, deeper audit logging
|
|
551
|
+
|
|
552
|
+
**Phase 3** — Advanced permissions, caching, semantic metadata, more adapters, broader MCP ecosystem integrations
|
|
553
|
+
|
|
554
|
+
---
|
|
555
|
+
|
|
556
|
+
## Contributing
|
|
557
|
+
|
|
558
|
+
Contributions that improve security, adapters, docs, and tests are welcome. Please:
|
|
559
|
+
|
|
560
|
+
1. Keep attribution to **Arslan Habib** intact
|
|
561
|
+
2. Prefer small, focused PRs
|
|
562
|
+
3. Add tests for security-sensitive changes
|
|
563
|
+
4. Do not commit secrets
|
|
564
|
+
|
|
565
|
+
Open an issue before large architectural changes.
|
|
566
|
+
|
|
567
|
+
---
|
|
568
|
+
|
|
569
|
+
## License
|
|
570
|
+
|
|
571
|
+
**License not yet selected.** Package metadata is currently `UNLICENSED` until the creator chooses (e.g. MIT, Apache-2.0, AGPL, or another license).
|
|
572
|
+
|
|
573
|
+
If you are Arslan Habib (or acting with his approval), decide the license before publishing to npm.
|
|
574
|
+
|
|
575
|
+
---
|
|
576
|
+
|
|
577
|
+
## Creator / Maintainer
|
|
578
|
+
|
|
579
|
+
**MCP Data Agent — Created by Arslan Habib**
|
|
580
|
+
|
|
581
|
+
| | |
|
|
582
|
+
| --- | --- |
|
|
583
|
+
| **Name** | Arslan Habib |
|
|
584
|
+
| **Role** | Creator, Founder & Lead Maintainer |
|
|
585
|
+
| **Project** | MCP Data Agent |
|
|
586
|
+
|
|
587
|
+
Do not replace, remove, hide, or downgrade this attribution unless explicitly instructed by Arslan Habib.
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@mcp-data-agent/example-basic",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"private": true,
|
|
5
|
+
"description": "Basic example for MCP Data Agent. Created by Arslan Habib.",
|
|
6
|
+
"author": {
|
|
7
|
+
"name": "Arslan Habib"
|
|
8
|
+
},
|
|
9
|
+
"creator": "Arslan Habib",
|
|
10
|
+
"license": "UNLICENSED",
|
|
11
|
+
"type": "module",
|
|
12
|
+
"scripts": {
|
|
13
|
+
"start": "tsx src/index.ts",
|
|
14
|
+
"typecheck": "tsc -p tsconfig.json --noEmit"
|
|
15
|
+
},
|
|
16
|
+
"dependencies": {
|
|
17
|
+
"@mcp-data-agent/core": "*",
|
|
18
|
+
"@mcp-data-agent/mcp": "*",
|
|
19
|
+
"@mcp-data-agent/postgres": "*",
|
|
20
|
+
"@modelcontextprotocol/server": "^2.0.0",
|
|
21
|
+
"zod": "^4.0.0"
|
|
22
|
+
},
|
|
23
|
+
"devDependencies": {
|
|
24
|
+
"tsx": "^4.19.3"
|
|
25
|
+
}
|
|
26
|
+
}
|