@eamonboyle/mssql-mcp 1.0.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/LICENSE +21 -0
- package/README.md +195 -0
- package/dist/db.d.ts +25 -0
- package/dist/db.d.ts.map +1 -0
- package/dist/db.js +90 -0
- package/dist/db.js.map +1 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +106 -0
- package/dist/index.js.map +1 -0
- package/dist/tools/CreateIndexTool.d.ts +24 -0
- package/dist/tools/CreateIndexTool.d.ts.map +1 -0
- package/dist/tools/CreateIndexTool.js +72 -0
- package/dist/tools/CreateIndexTool.js.map +1 -0
- package/dist/tools/CreateTableTool.d.ts +12 -0
- package/dist/tools/CreateTableTool.d.ts.map +1 -0
- package/dist/tools/CreateTableTool.js +57 -0
- package/dist/tools/CreateTableTool.js.map +1 -0
- package/dist/tools/DescribeTableTool.d.ts +21 -0
- package/dist/tools/DescribeTableTool.d.ts.map +1 -0
- package/dist/tools/DescribeTableTool.js +42 -0
- package/dist/tools/DescribeTableTool.js.map +1 -0
- package/dist/tools/DropTableTool.d.ts +12 -0
- package/dist/tools/DropTableTool.d.ts.map +1 -0
- package/dist/tools/DropTableTool.js +45 -0
- package/dist/tools/DropTableTool.js.map +1 -0
- package/dist/tools/InsertDataTool.d.ts +17 -0
- package/dist/tools/InsertDataTool.d.ts.map +1 -0
- package/dist/tools/InsertDataTool.js +151 -0
- package/dist/tools/InsertDataTool.js.map +1 -0
- package/dist/tools/ListTableTool.d.ts +17 -0
- package/dist/tools/ListTableTool.d.ts.map +1 -0
- package/dist/tools/ListTableTool.js +50 -0
- package/dist/tools/ListTableTool.js.map +1 -0
- package/dist/tools/ReadDataTool.d.ts +42 -0
- package/dist/tools/ReadDataTool.d.ts.map +1 -0
- package/dist/tools/ReadDataTool.js +229 -0
- package/dist/tools/ReadDataTool.js.map +1 -0
- package/dist/tools/UpdateDataTool.d.ts +17 -0
- package/dist/tools/UpdateDataTool.d.ts.map +1 -0
- package/dist/tools/UpdateDataTool.js +66 -0
- package/dist/tools/UpdateDataTool.js.map +1 -0
- package/package.json +52 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) Microsoft Corporation.
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE
|
package/README.md
ADDED
|
@@ -0,0 +1,195 @@
|
|
|
1
|
+
# MSSQL MCP Server
|
|
2
|
+
|
|
3
|
+
[](https://opensource.org/licenses/MIT)
|
|
4
|
+
[](https://nodejs.org/)
|
|
5
|
+
|
|
6
|
+
[](cursor://anysphere.cursor-deeplink/mcp/install?name=MSSQL&config=eyJjb21tYW5kIjoibnB4IiwiYXJncyI6WyIteSIsIkBlYW1vbmJveWxlL21zc3FsLW1jcCJdLCJlbnYiOnsiU0VSVkVSX05BTUUiOiJsb2NhbGhvc3QiLCJEQVRBQkFTRV9OQU1FIjoiWW91ckRhdGFiYXNlIiwiREJfVVNFUiI6IiIsIkRCX1BBU1NXT1JEIjoiIiwiUkVBRE9OTFkiOiJmYWxzZSJ9fQ==)
|
|
7
|
+
[](vscode://mcp/install?%7B%22name%22%3A%22mssql%22%2C%22type%22%3A%22stdio%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40eamonboyle%2Fmssql-mcp%22%5D%2C%22env%22%3A%7B%22SERVER_NAME%22%3A%22localhost%22%2C%22DATABASE_NAME%22%3A%22YourDatabase%22%2C%22DB_USER%22%3A%22%22%2C%22DB_PASSWORD%22%3A%22%22%2C%22READONLY%22%3A%22false%22%7D%7D)
|
|
8
|
+
|
|
9
|
+
> ⚠️ **EXPERIMENTAL USE ONLY** — This MCP Server is provided for educational and experimental purposes. It is NOT intended for production use. Use appropriate security measures and test thoroughly before any deployment.
|
|
10
|
+
|
|
11
|
+
## What is this? 🤔
|
|
12
|
+
|
|
13
|
+
An [MCP (Model Context Protocol)](https://modelcontextprotocol.io/) server that lets AI assistants like Claude, Cursor, and other LLM-powered tools query and manage your Microsoft SQL Server database using natural language.
|
|
14
|
+
|
|
15
|
+
### Quick Example
|
|
16
|
+
|
|
17
|
+
```
|
|
18
|
+
You: "Show me all customers from New York"
|
|
19
|
+
AI: *queries your MSSQL database and returns the results in plain English*
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
## Features 📊
|
|
23
|
+
|
|
24
|
+
- **Natural language to SQL** — Ask questions in plain English
|
|
25
|
+
- **CRUD operations** — Create, read, update, and delete data
|
|
26
|
+
- **Schema management** — Create tables, indexes; describe and drop tables
|
|
27
|
+
- **Multi-database support** — Connect to multiple databases on the same server
|
|
28
|
+
- **Read-only mode** — Restrict to SELECT-only for safer environments
|
|
29
|
+
- **Secure by default** — WHERE clauses required for reads/updates; SQL injection safeguards
|
|
30
|
+
|
|
31
|
+
## Supported AI Clients
|
|
32
|
+
|
|
33
|
+
- [Claude Desktop](https://claude.ai/)
|
|
34
|
+
- [Cursor](https://cursor.com/) (VS Code with AI)
|
|
35
|
+
- [VS Code Agent](https://marketplace.visualstudio.com/items?itemName=Anthropic.anthropic-vscode) extension
|
|
36
|
+
- Any MCP-compatible client
|
|
37
|
+
|
|
38
|
+
## Quick Start 🚀
|
|
39
|
+
|
|
40
|
+
### One-Click Install (Cursor / VS Code)
|
|
41
|
+
|
|
42
|
+
Click **Add to Cursor** or **Install in VS Code** above to add the MCP server. Edit the config to add your database credentials (`DB_USER`, `DB_PASSWORD`, etc.). No cloning required—runs via `npx`.
|
|
43
|
+
|
|
44
|
+
### Prerequisites
|
|
45
|
+
|
|
46
|
+
- **Node.js 18** or higher
|
|
47
|
+
- SQL Server (local, Azure SQL, or remote)
|
|
48
|
+
- An MCP-compatible AI client (Claude Desktop, Cursor, etc.)
|
|
49
|
+
|
|
50
|
+
### Installation
|
|
51
|
+
|
|
52
|
+
**From npm** (recommended):
|
|
53
|
+
|
|
54
|
+
```bash
|
|
55
|
+
npx -y @eamonboyle/mssql-mcp
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
Or install globally: `npm install -g @eamonboyle/mssql-mcp`
|
|
59
|
+
|
|
60
|
+
**From source** (for development):
|
|
61
|
+
|
|
62
|
+
```bash
|
|
63
|
+
git clone https://github.com/eamonboyle/mssql-mcp.git
|
|
64
|
+
cd mssql-mcp
|
|
65
|
+
npm install
|
|
66
|
+
npm run build
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
## Configuration
|
|
70
|
+
|
|
71
|
+
### Environment Variables
|
|
72
|
+
|
|
73
|
+
| Variable | Required | Description |
|
|
74
|
+
|----------|----------|-------------|
|
|
75
|
+
| `SERVER_NAME` | Yes | SQL Server host (e.g., `localhost`, `my-server.database.windows.net`) |
|
|
76
|
+
| `DATABASE_NAME` | Yes | Default database name |
|
|
77
|
+
| `DB_USER` | Yes* | SQL Server username (for SQL authentication) |
|
|
78
|
+
| `DB_PASSWORD` | Yes* | SQL Server password (for SQL authentication) |
|
|
79
|
+
| `READONLY` | No | `"true"` for read-only mode, `"false"` for full access (default: `"false"`) |
|
|
80
|
+
| `DATABASES` | No | Comma-separated list for multi-database access (e.g., `ProdDB,StagingDB`) |
|
|
81
|
+
| `CONNECTION_TIMEOUT` | No | Timeout in seconds (default: `30`) |
|
|
82
|
+
| `TRUST_SERVER_CERTIFICATE` | No | `"true"` for self-signed certs (e.g., local dev) (default: `"false"`) |
|
|
83
|
+
|
|
84
|
+
\* Required for SQL authentication. For Windows/Integrated authentication, consult the [mssql](https://www.npmjs.com/package/mssql) package documentation.
|
|
85
|
+
|
|
86
|
+
### Option 1: Cursor / VS Code Setup
|
|
87
|
+
|
|
88
|
+
1. Create or edit `.vscode/mcp.json` in your workspace:
|
|
89
|
+
|
|
90
|
+
```json
|
|
91
|
+
{
|
|
92
|
+
"mcpServers": {
|
|
93
|
+
"mssql": {
|
|
94
|
+
"command": "npx",
|
|
95
|
+
"args": ["-y", "@eamonboyle/mssql-mcp"],
|
|
96
|
+
"env": {
|
|
97
|
+
"SERVER_NAME": "localhost",
|
|
98
|
+
"DATABASE_NAME": "YourDatabase",
|
|
99
|
+
"DB_USER": "your_username",
|
|
100
|
+
"DB_PASSWORD": "your_password",
|
|
101
|
+
"READONLY": "false"
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
```
|
|
107
|
+
|
|
108
|
+
2. Restart Cursor/VS Code.
|
|
109
|
+
|
|
110
|
+
### Option 2: Claude Desktop Setup
|
|
111
|
+
|
|
112
|
+
1. Open **File → Settings → Developer → Edit Config**
|
|
113
|
+
2. Add the MCP server configuration:
|
|
114
|
+
|
|
115
|
+
```json
|
|
116
|
+
{
|
|
117
|
+
"mcpServers": {
|
|
118
|
+
"mssql": {
|
|
119
|
+
"command": "npx",
|
|
120
|
+
"args": ["-y", "@eamonboyle/mssql-mcp"],
|
|
121
|
+
"env": {
|
|
122
|
+
"SERVER_NAME": "localhost",
|
|
123
|
+
"DATABASE_NAME": "YourDatabase",
|
|
124
|
+
"DB_USER": "your_username",
|
|
125
|
+
"DB_PASSWORD": "your_password",
|
|
126
|
+
"READONLY": "false"
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
```
|
|
132
|
+
|
|
133
|
+
3. Restart Claude Desktop.
|
|
134
|
+
|
|
135
|
+
### Multi-Database Support
|
|
136
|
+
|
|
137
|
+
To allow queries across multiple databases:
|
|
138
|
+
|
|
139
|
+
```json
|
|
140
|
+
"env": {
|
|
141
|
+
"SERVER_NAME": "your-server.database.windows.net",
|
|
142
|
+
"DATABASE_NAME": "ProdDB",
|
|
143
|
+
"DATABASES": "ProdDB,StagingDB,AnalyticsDB",
|
|
144
|
+
"DB_USER": "your_username",
|
|
145
|
+
"DB_PASSWORD": "your_password",
|
|
146
|
+
"READONLY": "false"
|
|
147
|
+
}
|
|
148
|
+
```
|
|
149
|
+
|
|
150
|
+
All tools accept an optional `databaseName` parameter. When omitted, `DATABASE_NAME` is used.
|
|
151
|
+
|
|
152
|
+
## Sample Configurations
|
|
153
|
+
|
|
154
|
+
See `src/samples/` for example configs:
|
|
155
|
+
|
|
156
|
+
- `claude_desktop_config.json` — Claude Desktop
|
|
157
|
+
- `vscode_agent_config.json` — VS Code Agent
|
|
158
|
+
|
|
159
|
+
## Usage Examples
|
|
160
|
+
|
|
161
|
+
Once configured, you can ask things like:
|
|
162
|
+
|
|
163
|
+
- "Show me all users from New York"
|
|
164
|
+
- "Create a new table called products with columns for id, name, and price"
|
|
165
|
+
- "Update all pending orders to completed status"
|
|
166
|
+
- "List all tables in the database"
|
|
167
|
+
- "Describe the schema of the customers table"
|
|
168
|
+
|
|
169
|
+
## Available Tools
|
|
170
|
+
|
|
171
|
+
| Tool | Read-only | Description |
|
|
172
|
+
|------|-----------|-------------|
|
|
173
|
+
| `read_data` | ✓ | Execute SELECT queries |
|
|
174
|
+
| `list_table` | ✓ | List tables in a database |
|
|
175
|
+
| `describe_table` | ✓ | Get table schema |
|
|
176
|
+
| `insert_data` | | Insert rows |
|
|
177
|
+
| `update_data` | | Update rows (requires WHERE) |
|
|
178
|
+
| `create_table` | | Create tables |
|
|
179
|
+
| `create_index` | | Create indexes |
|
|
180
|
+
| `drop_table` | | Drop tables |
|
|
181
|
+
|
|
182
|
+
## Security Notes
|
|
183
|
+
|
|
184
|
+
- **Credentials** — Never commit `DB_USER`/`DB_PASSWORD` or config files with secrets. Use environment variables or a secrets manager.
|
|
185
|
+
- **Read-only mode** — Set `READONLY: "true"` when you only need queries.
|
|
186
|
+
- **WHERE clauses** — Read and update operations require explicit WHERE clauses to reduce accidental full-table operations.
|
|
187
|
+
- **SQL injection** — The server validates and restricts dangerous SQL patterns.
|
|
188
|
+
|
|
189
|
+
## Contributing
|
|
190
|
+
|
|
191
|
+
Contributions are welcome! Please read [CONTRIBUTING.md](CONTRIBUTING.md) for guidelines.
|
|
192
|
+
|
|
193
|
+
## License
|
|
194
|
+
|
|
195
|
+
MIT License — see [LICENSE](LICENSE) for details.
|
package/dist/db.d.ts
ADDED
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import sql from "mssql";
|
|
2
|
+
/**
|
|
3
|
+
* Returns the list of allowed database names.
|
|
4
|
+
* If DATABASES is set, returns those; otherwise returns only DATABASE_NAME.
|
|
5
|
+
*/
|
|
6
|
+
export declare function getAllowedDatabases(): string[];
|
|
7
|
+
/**
|
|
8
|
+
* Resolves the database name to use (param or default).
|
|
9
|
+
* Returns null if invalid.
|
|
10
|
+
*/
|
|
11
|
+
export declare function resolveDatabaseName(databaseName?: string): string | null;
|
|
12
|
+
/**
|
|
13
|
+
* Ensures a connection pool exists for the given database.
|
|
14
|
+
*/
|
|
15
|
+
export declare function ensureSqlConnection(databaseName: string): Promise<sql.ConnectionPool>;
|
|
16
|
+
/**
|
|
17
|
+
* Returns a sql.Request for the given database.
|
|
18
|
+
* Resolves database name (param or default), validates against allowed list,
|
|
19
|
+
* ensures connection, and returns pool.request().
|
|
20
|
+
*/
|
|
21
|
+
export declare function getSqlRequest(databaseName?: string): Promise<{
|
|
22
|
+
request: sql.Request;
|
|
23
|
+
error?: string;
|
|
24
|
+
}>;
|
|
25
|
+
//# sourceMappingURL=db.d.ts.map
|
package/dist/db.d.ts.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"db.d.ts","sourceRoot":"","sources":["../src/db.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,OAAO,CAAC;AAKxB;;;GAGG;AACH,wBAAgB,mBAAmB,IAAI,MAAM,EAAE,CAO9C;AAED;;;GAGG;AACH,wBAAgB,mBAAmB,CAAC,YAAY,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAQxE;AAwBD;;GAEG;AACH,wBAAsB,mBAAmB,CACvC,YAAY,EAAE,MAAM,GACnB,OAAO,CAAC,GAAG,CAAC,cAAc,CAAC,CAoB7B;AAED;;;;GAIG;AACH,wBAAsB,aAAa,CACjC,YAAY,CAAC,EAAE,MAAM,GACpB,OAAO,CAAC;IAAE,OAAO,EAAE,GAAG,CAAC,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,CAYnD"}
|
package/dist/db.js
ADDED
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import sql from "mssql";
|
|
2
|
+
// Connection pools keyed by database name
|
|
3
|
+
const sqlPools = new Map();
|
|
4
|
+
/**
|
|
5
|
+
* Returns the list of allowed database names.
|
|
6
|
+
* If DATABASES is set, returns those; otherwise returns only DATABASE_NAME.
|
|
7
|
+
*/
|
|
8
|
+
export function getAllowedDatabases() {
|
|
9
|
+
const databasesEnv = process.env.DATABASES;
|
|
10
|
+
if (databasesEnv && databasesEnv.trim()) {
|
|
11
|
+
return databasesEnv.split(",").map((db) => db.trim()).filter(Boolean);
|
|
12
|
+
}
|
|
13
|
+
const defaultDb = process.env.DATABASE_NAME;
|
|
14
|
+
return defaultDb ? [defaultDb] : [];
|
|
15
|
+
}
|
|
16
|
+
/**
|
|
17
|
+
* Resolves the database name to use (param or default).
|
|
18
|
+
* Returns null if invalid.
|
|
19
|
+
*/
|
|
20
|
+
export function resolveDatabaseName(databaseName) {
|
|
21
|
+
const resolved = databaseName?.trim() || process.env.DATABASE_NAME?.trim();
|
|
22
|
+
if (!resolved)
|
|
23
|
+
return null;
|
|
24
|
+
const allowed = getAllowedDatabases();
|
|
25
|
+
if (allowed.length === 0)
|
|
26
|
+
return resolved; // No validation if nothing configured
|
|
27
|
+
if (allowed.includes(resolved))
|
|
28
|
+
return resolved;
|
|
29
|
+
return null;
|
|
30
|
+
}
|
|
31
|
+
function createSqlConfigForDatabase(databaseName) {
|
|
32
|
+
const trustServerCertificate = process.env.TRUST_SERVER_CERTIFICATE?.toLowerCase() === "true";
|
|
33
|
+
const connectionTimeout = process.env.CONNECTION_TIMEOUT
|
|
34
|
+
? parseInt(process.env.CONNECTION_TIMEOUT, 10)
|
|
35
|
+
: 30;
|
|
36
|
+
return {
|
|
37
|
+
server: process.env.SERVER_NAME || "localhost",
|
|
38
|
+
database: databaseName,
|
|
39
|
+
user: process.env.DB_USER,
|
|
40
|
+
password: process.env.DB_PASSWORD,
|
|
41
|
+
options: {
|
|
42
|
+
encrypt: false,
|
|
43
|
+
trustServerCertificate: trustServerCertificate || true,
|
|
44
|
+
enableArithAbort: true,
|
|
45
|
+
useUTC: false,
|
|
46
|
+
},
|
|
47
|
+
connectionTimeout: connectionTimeout * 1000,
|
|
48
|
+
};
|
|
49
|
+
}
|
|
50
|
+
/**
|
|
51
|
+
* Ensures a connection pool exists for the given database.
|
|
52
|
+
*/
|
|
53
|
+
export async function ensureSqlConnection(databaseName) {
|
|
54
|
+
const existing = sqlPools.get(databaseName);
|
|
55
|
+
if (existing && existing.connected) {
|
|
56
|
+
return existing;
|
|
57
|
+
}
|
|
58
|
+
if (existing) {
|
|
59
|
+
try {
|
|
60
|
+
await existing.close();
|
|
61
|
+
}
|
|
62
|
+
catch {
|
|
63
|
+
// Ignore close errors
|
|
64
|
+
}
|
|
65
|
+
sqlPools.delete(databaseName);
|
|
66
|
+
}
|
|
67
|
+
const config = createSqlConfigForDatabase(databaseName);
|
|
68
|
+
const pool = new sql.ConnectionPool(config);
|
|
69
|
+
await pool.connect();
|
|
70
|
+
sqlPools.set(databaseName, pool);
|
|
71
|
+
return pool;
|
|
72
|
+
}
|
|
73
|
+
/**
|
|
74
|
+
* Returns a sql.Request for the given database.
|
|
75
|
+
* Resolves database name (param or default), validates against allowed list,
|
|
76
|
+
* ensures connection, and returns pool.request().
|
|
77
|
+
*/
|
|
78
|
+
export async function getSqlRequest(databaseName) {
|
|
79
|
+
const resolved = resolveDatabaseName(databaseName);
|
|
80
|
+
if (!resolved) {
|
|
81
|
+
const allowed = getAllowedDatabases();
|
|
82
|
+
return {
|
|
83
|
+
request: null,
|
|
84
|
+
error: `Invalid or disallowed database. Allowed: ${allowed.join(", ") || "DATABASE_NAME"}. Use databaseName parameter to target a specific database.`,
|
|
85
|
+
};
|
|
86
|
+
}
|
|
87
|
+
const pool = await ensureSqlConnection(resolved);
|
|
88
|
+
return { request: pool.request() };
|
|
89
|
+
}
|
|
90
|
+
//# sourceMappingURL=db.js.map
|
package/dist/db.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"db.js","sourceRoot":"","sources":["../src/db.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":""}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import { Server } from '@modelcontextprotocol/sdk/server/index.js';
|
|
3
|
+
import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
|
|
4
|
+
import { CallToolRequestSchema, ListToolsRequestSchema } from '@modelcontextprotocol/sdk/types.js';
|
|
5
|
+
// Internal imports
|
|
6
|
+
import { UpdateDataTool } from './tools/UpdateDataTool.js';
|
|
7
|
+
import { InsertDataTool } from './tools/InsertDataTool.js';
|
|
8
|
+
import { ReadDataTool } from './tools/ReadDataTool.js';
|
|
9
|
+
import { CreateTableTool } from './tools/CreateTableTool.js';
|
|
10
|
+
import { CreateIndexTool } from './tools/CreateIndexTool.js';
|
|
11
|
+
import { ListTableTool } from './tools/ListTableTool.js';
|
|
12
|
+
import { DropTableTool } from './tools/DropTableTool.js';
|
|
13
|
+
import { DescribeTableTool } from './tools/DescribeTableTool.js';
|
|
14
|
+
const updateDataTool = new UpdateDataTool();
|
|
15
|
+
const insertDataTool = new InsertDataTool();
|
|
16
|
+
const readDataTool = new ReadDataTool();
|
|
17
|
+
const createTableTool = new CreateTableTool();
|
|
18
|
+
const createIndexTool = new CreateIndexTool();
|
|
19
|
+
const listTableTool = new ListTableTool();
|
|
20
|
+
const dropTableTool = new DropTableTool();
|
|
21
|
+
const describeTableTool = new DescribeTableTool();
|
|
22
|
+
const server = new Server({
|
|
23
|
+
name: 'mssql-mcp-server',
|
|
24
|
+
version: '0.1.0',
|
|
25
|
+
}, {
|
|
26
|
+
capabilities: {
|
|
27
|
+
tools: {},
|
|
28
|
+
},
|
|
29
|
+
});
|
|
30
|
+
// Read READONLY env variable
|
|
31
|
+
const isReadOnly = process.env.READONLY === 'true';
|
|
32
|
+
// Request handlers
|
|
33
|
+
server.setRequestHandler(ListToolsRequestSchema, async () => ({
|
|
34
|
+
tools: isReadOnly
|
|
35
|
+
? [listTableTool, readDataTool, describeTableTool] // todo: add searchDataTool to the list of tools available in readonly mode once implemented
|
|
36
|
+
: [insertDataTool, readDataTool, describeTableTool, updateDataTool, createTableTool, createIndexTool, dropTableTool, listTableTool], // add all new tools here
|
|
37
|
+
}));
|
|
38
|
+
server.setRequestHandler(CallToolRequestSchema, async (request) => {
|
|
39
|
+
const { name, arguments: args } = request.params;
|
|
40
|
+
try {
|
|
41
|
+
let result;
|
|
42
|
+
switch (name) {
|
|
43
|
+
case insertDataTool.name:
|
|
44
|
+
result = await insertDataTool.run(args);
|
|
45
|
+
break;
|
|
46
|
+
case readDataTool.name:
|
|
47
|
+
result = await readDataTool.run(args);
|
|
48
|
+
break;
|
|
49
|
+
case updateDataTool.name:
|
|
50
|
+
result = await updateDataTool.run(args);
|
|
51
|
+
break;
|
|
52
|
+
case createTableTool.name:
|
|
53
|
+
result = await createTableTool.run(args);
|
|
54
|
+
break;
|
|
55
|
+
case createIndexTool.name:
|
|
56
|
+
result = await createIndexTool.run(args);
|
|
57
|
+
break;
|
|
58
|
+
case listTableTool.name:
|
|
59
|
+
result = await listTableTool.run(args);
|
|
60
|
+
break;
|
|
61
|
+
case dropTableTool.name:
|
|
62
|
+
result = await dropTableTool.run(args);
|
|
63
|
+
break;
|
|
64
|
+
case describeTableTool.name:
|
|
65
|
+
if (!args || typeof args.tableName !== 'string') {
|
|
66
|
+
return {
|
|
67
|
+
content: [{ type: 'text', text: `Missing or invalid 'tableName' argument for describe_table tool.` }],
|
|
68
|
+
isError: true,
|
|
69
|
+
};
|
|
70
|
+
}
|
|
71
|
+
result = await describeTableTool.run(args);
|
|
72
|
+
break;
|
|
73
|
+
default:
|
|
74
|
+
return {
|
|
75
|
+
content: [{ type: 'text', text: `Unknown tool: ${name}` }],
|
|
76
|
+
isError: true,
|
|
77
|
+
};
|
|
78
|
+
}
|
|
79
|
+
return {
|
|
80
|
+
content: [{ type: 'text', text: JSON.stringify(result, null, 2) }],
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
catch (error) {
|
|
84
|
+
return {
|
|
85
|
+
content: [{ type: 'text', text: `Error occurred: ${error}` }],
|
|
86
|
+
isError: true,
|
|
87
|
+
};
|
|
88
|
+
}
|
|
89
|
+
});
|
|
90
|
+
// Server startup
|
|
91
|
+
async function runServer() {
|
|
92
|
+
try {
|
|
93
|
+
const transport = new StdioServerTransport();
|
|
94
|
+
await server.connect(transport);
|
|
95
|
+
}
|
|
96
|
+
catch (error) {
|
|
97
|
+
console.error('Fatal error running server:', error);
|
|
98
|
+
process.exit(1);
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
runServer().catch((error) => {
|
|
102
|
+
console.error('Fatal error running server:', error);
|
|
103
|
+
process.exit(1);
|
|
104
|
+
});
|
|
105
|
+
// Tools call getSqlRequest(databaseName) internally - no wrapping needed
|
|
106
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { Tool } from "@modelcontextprotocol/sdk/types.js";
|
|
2
|
+
export declare class CreateIndexTool implements Tool {
|
|
3
|
+
[key: string]: any;
|
|
4
|
+
name: string;
|
|
5
|
+
description: string;
|
|
6
|
+
inputSchema: any;
|
|
7
|
+
run(params: any): Promise<{
|
|
8
|
+
success: boolean;
|
|
9
|
+
message: string;
|
|
10
|
+
details?: undefined;
|
|
11
|
+
} | {
|
|
12
|
+
success: boolean;
|
|
13
|
+
message: string;
|
|
14
|
+
details: {
|
|
15
|
+
schemaName: any;
|
|
16
|
+
tableName: any;
|
|
17
|
+
indexName: any;
|
|
18
|
+
columnNames: any;
|
|
19
|
+
isUnique: any;
|
|
20
|
+
isClustered: any;
|
|
21
|
+
};
|
|
22
|
+
}>;
|
|
23
|
+
}
|
|
24
|
+
//# sourceMappingURL=CreateIndexTool.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"CreateIndexTool.d.ts","sourceRoot":"","sources":["../../src/tools/CreateIndexTool.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,oCAAoC,CAAC;AAG1D,qBAAa,eAAgB,YAAW,IAAI;IAC1C,CAAC,GAAG,EAAE,MAAM,GAAG,GAAG,CAAC;IACnB,IAAI,SAAkB;IACtB,WAAW,SAAkF;IAC7F,WAAW,MA2BF;IAEH,GAAG,CAAC,MAAM,EAAE,GAAG;;;;;;;;;;;;;;;;CAsCtB"}
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
import { getSqlRequest } from "../db.js";
|
|
2
|
+
export class CreateIndexTool {
|
|
3
|
+
constructor() {
|
|
4
|
+
this.name = "create_index";
|
|
5
|
+
this.description = "Creates an index on a specified column or columns in an MSSQL Database table";
|
|
6
|
+
this.inputSchema = {
|
|
7
|
+
type: "object",
|
|
8
|
+
properties: {
|
|
9
|
+
schemaName: { type: "string", description: "Name of the schema containing the table" },
|
|
10
|
+
tableName: { type: "string", description: "Name of the table to create index on" },
|
|
11
|
+
indexName: { type: "string", description: "Name for the new index" },
|
|
12
|
+
columns: {
|
|
13
|
+
type: "array",
|
|
14
|
+
items: { type: "string" },
|
|
15
|
+
description: "Array of column names to include in the index"
|
|
16
|
+
},
|
|
17
|
+
isUnique: {
|
|
18
|
+
type: "boolean",
|
|
19
|
+
description: "Whether the index should enforce uniqueness (default: false)",
|
|
20
|
+
default: false
|
|
21
|
+
},
|
|
22
|
+
isClustered: {
|
|
23
|
+
type: "boolean",
|
|
24
|
+
description: "Whether the index should be clustered (default: false)",
|
|
25
|
+
default: false
|
|
26
|
+
},
|
|
27
|
+
databaseName: {
|
|
28
|
+
type: "string",
|
|
29
|
+
description: "Name of the database to use (optional). Omit to use the default database."
|
|
30
|
+
},
|
|
31
|
+
},
|
|
32
|
+
required: ["tableName", "indexName", "columns"],
|
|
33
|
+
};
|
|
34
|
+
}
|
|
35
|
+
async run(params) {
|
|
36
|
+
try {
|
|
37
|
+
const { schemaName, tableName, indexName, columns, databaseName, isUnique = false, isClustered = false } = params;
|
|
38
|
+
const { request, error } = await getSqlRequest(databaseName);
|
|
39
|
+
if (error) {
|
|
40
|
+
return { success: false, message: error };
|
|
41
|
+
}
|
|
42
|
+
let indexType = isClustered ? "CLUSTERED" : "NONCLUSTERED";
|
|
43
|
+
if (isUnique) {
|
|
44
|
+
indexType = `UNIQUE ${indexType}`;
|
|
45
|
+
}
|
|
46
|
+
const columnNames = columns.join(", ");
|
|
47
|
+
const tableRef = schemaName ? `${schemaName}.${tableName}` : tableName;
|
|
48
|
+
const query = `CREATE ${indexType} INDEX ${indexName} ON ${tableRef} (${columnNames})`;
|
|
49
|
+
await request.query(query);
|
|
50
|
+
return {
|
|
51
|
+
success: true,
|
|
52
|
+
message: `Index [${indexName}] created successfully on table [${tableRef}]`,
|
|
53
|
+
details: {
|
|
54
|
+
schemaName: schemaName || undefined,
|
|
55
|
+
tableName,
|
|
56
|
+
indexName,
|
|
57
|
+
columnNames,
|
|
58
|
+
isUnique,
|
|
59
|
+
isClustered
|
|
60
|
+
}
|
|
61
|
+
};
|
|
62
|
+
}
|
|
63
|
+
catch (error) {
|
|
64
|
+
console.error("Error creating index:", error);
|
|
65
|
+
return {
|
|
66
|
+
success: false,
|
|
67
|
+
message: `Failed to create index: ${error}`,
|
|
68
|
+
};
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
//# sourceMappingURL=CreateIndexTool.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"CreateIndexTool.js","sourceRoot":"","sources":["../../src/tools/CreateIndexTool.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAEzC,MAAM,OAAO,eAAe;IAA5B;QAEE,SAAI,GAAG,cAAc,CAAC;QACtB,gBAAW,GAAG,8EAA8E,CAAC;QAC7F,gBAAW,GAAG;YACZ,IAAI,EAAE,QAAQ;YACd,UAAU,EAAE;gBACV,UAAU,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,yCAAyC,EAAE;gBACtF,SAAS,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,sCAAsC,EAAE;gBAClF,SAAS,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,wBAAwB,EAAE;gBACpE,OAAO,EAAE;oBACP,IAAI,EAAE,OAAO;oBACb,KAAK,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;oBACzB,WAAW,EAAE,+CAA+C;iBAC7D;gBACD,QAAQ,EAAE;oBACR,IAAI,EAAE,SAAS;oBACf,WAAW,EAAE,8DAA8D;oBAC3E,OAAO,EAAE,KAAK;iBACf;gBACD,WAAW,EAAE;oBACX,IAAI,EAAE,SAAS;oBACf,WAAW,EAAE,wDAAwD;oBACrE,OAAO,EAAE,KAAK;iBACf;gBACD,YAAY,EAAE;oBACZ,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,2EAA2E;iBACzF;aACF;YACD,QAAQ,EAAE,CAAC,WAAW,EAAE,WAAW,EAAE,SAAS,CAAC;SACzC,CAAC;IAwCX,CAAC;IAtCC,KAAK,CAAC,GAAG,CAAC,MAAW;QACnB,IAAI;YACF,MAAM,EAAE,UAAU,EAAE,SAAS,EAAE,SAAS,EAAE,OAAO,EAAE,YAAY,EAAE,QAAQ,GAAG,KAAK,EAAE,WAAW,GAAG,KAAK,EAAE,GAAG,MAAM,CAAC;YAElH,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,GAAG,MAAM,aAAa,CAAC,YAAY,CAAC,CAAC;YAC7D,IAAI,KAAK,EAAE;gBACT,OAAO,EAAE,OAAO,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC;aAC3C;YAED,IAAI,SAAS,GAAG,WAAW,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC,CAAC,cAAc,CAAC;YAC3D,IAAI,QAAQ,EAAE;gBACZ,SAAS,GAAG,UAAU,SAAS,EAAE,CAAC;aACnC;YACD,MAAM,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACvC,MAAM,QAAQ,GAAG,UAAU,CAAC,CAAC,CAAC,GAAG,UAAU,IAAI,SAAS,EAAE,CAAC,CAAC,CAAC,SAAS,CAAC;YACvE,MAAM,KAAK,GAAG,UAAU,SAAS,UAAU,SAAS,OAAO,QAAQ,KAAK,WAAW,GAAG,CAAC;YACvF,MAAM,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;YAE3B,OAAO;gBACL,OAAO,EAAE,IAAI;gBACb,OAAO,EAAE,UAAU,SAAS,oCAAoC,QAAQ,GAAG;gBAC3E,OAAO,EAAE;oBACP,UAAU,EAAE,UAAU,IAAI,SAAS;oBACnC,SAAS;oBACT,SAAS;oBACT,WAAW;oBACX,QAAQ;oBACR,WAAW;iBACZ;aACF,CAAC;SACH;QAAC,OAAO,KAAK,EAAE;YACd,OAAO,CAAC,KAAK,CAAC,uBAAuB,EAAE,KAAK,CAAC,CAAC;YAC9C,OAAO;gBACL,OAAO,EAAE,KAAK;gBACd,OAAO,EAAE,2BAA2B,KAAK,EAAE;aAC5C,CAAC;SACH;IACH,CAAC;CACF"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { Tool } from "@modelcontextprotocol/sdk/types.js";
|
|
2
|
+
export declare class CreateTableTool implements Tool {
|
|
3
|
+
[key: string]: any;
|
|
4
|
+
name: string;
|
|
5
|
+
description: string;
|
|
6
|
+
inputSchema: any;
|
|
7
|
+
run(params: any): Promise<{
|
|
8
|
+
success: boolean;
|
|
9
|
+
message: string;
|
|
10
|
+
}>;
|
|
11
|
+
}
|
|
12
|
+
//# sourceMappingURL=CreateTableTool.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"CreateTableTool.d.ts","sourceRoot":"","sources":["../../src/tools/CreateTableTool.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,oCAAoC,CAAC;AAG1D,qBAAa,eAAgB,YAAW,IAAI;IAC1C,CAAC,GAAG,EAAE,MAAM,GAAG,GAAG,CAAC;IACnB,IAAI,SAAkB;IACtB,WAAW,SAA2E;IACtF,WAAW,MAsBF;IAEH,GAAG,CAAC,MAAM,EAAE,GAAG;;;;CA2BtB"}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
import { getSqlRequest } from "../db.js";
|
|
2
|
+
export class CreateTableTool {
|
|
3
|
+
constructor() {
|
|
4
|
+
this.name = "create_table";
|
|
5
|
+
this.description = "Creates a new table in the MSSQL Database with the specified columns.";
|
|
6
|
+
this.inputSchema = {
|
|
7
|
+
type: "object",
|
|
8
|
+
properties: {
|
|
9
|
+
tableName: { type: "string", description: "Name of the table to create" },
|
|
10
|
+
columns: {
|
|
11
|
+
type: "array",
|
|
12
|
+
description: "Array of column definitions (e.g., [{ name: 'id', type: 'INT PRIMARY KEY' }, ...])",
|
|
13
|
+
items: {
|
|
14
|
+
type: "object",
|
|
15
|
+
properties: {
|
|
16
|
+
name: { type: "string", description: "Column name" },
|
|
17
|
+
type: { type: "string", description: "SQL type and constraints (e.g., 'INT PRIMARY KEY', 'NVARCHAR(255) NOT NULL')" }
|
|
18
|
+
},
|
|
19
|
+
required: ["name", "type"]
|
|
20
|
+
}
|
|
21
|
+
},
|
|
22
|
+
databaseName: {
|
|
23
|
+
type: "string",
|
|
24
|
+
description: "Name of the database to use (optional). Omit to use the default database."
|
|
25
|
+
},
|
|
26
|
+
},
|
|
27
|
+
required: ["tableName", "columns"],
|
|
28
|
+
};
|
|
29
|
+
}
|
|
30
|
+
async run(params) {
|
|
31
|
+
try {
|
|
32
|
+
const { tableName, columns, databaseName } = params;
|
|
33
|
+
const { request, error } = await getSqlRequest(databaseName);
|
|
34
|
+
if (error) {
|
|
35
|
+
return { success: false, message: error };
|
|
36
|
+
}
|
|
37
|
+
if (!Array.isArray(columns) || columns.length === 0) {
|
|
38
|
+
throw new Error("'columns' must be a non-empty array");
|
|
39
|
+
}
|
|
40
|
+
const columnDefs = columns.map((col) => `[${col.name}] ${col.type}`).join(", ");
|
|
41
|
+
const query = `CREATE TABLE [${tableName}] (${columnDefs})`;
|
|
42
|
+
await request.query(query);
|
|
43
|
+
return {
|
|
44
|
+
success: true,
|
|
45
|
+
message: `Table '${tableName}' created successfully.`
|
|
46
|
+
};
|
|
47
|
+
}
|
|
48
|
+
catch (error) {
|
|
49
|
+
console.error("Error creating table:", error);
|
|
50
|
+
return {
|
|
51
|
+
success: false,
|
|
52
|
+
message: `Failed to create table: ${error}`
|
|
53
|
+
};
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
//# sourceMappingURL=CreateTableTool.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"CreateTableTool.js","sourceRoot":"","sources":["../../src/tools/CreateTableTool.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAEzC,MAAM,OAAO,eAAe;IAA5B;QAEE,SAAI,GAAG,cAAc,CAAC;QACtB,gBAAW,GAAG,uEAAuE,CAAC;QACtF,gBAAW,GAAG;YACZ,IAAI,EAAE,QAAQ;YACd,UAAU,EAAE;gBACV,SAAS,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,6BAA6B,EAAE;gBACzE,OAAO,EAAE;oBACP,IAAI,EAAE,OAAO;oBACb,WAAW,EAAE,oFAAoF;oBACjG,KAAK,EAAE;wBACL,IAAI,EAAE,QAAQ;wBACd,UAAU,EAAE;4BACV,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,aAAa,EAAE;4BACpD,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,8EAA8E,EAAE;yBACtH;wBACD,QAAQ,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC;qBAC3B;iBACF;gBACD,YAAY,EAAE;oBACZ,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,2EAA2E;iBACzF;aACF;YACD,QAAQ,EAAE,CAAC,WAAW,EAAE,SAAS,CAAC;SAC5B,CAAC;IA6BX,CAAC;IA3BC,KAAK,CAAC,GAAG,CAAC,MAAW;QACnB,IAAI;YACF,MAAM,EAAE,SAAS,EAAE,OAAO,EAAE,YAAY,EAAE,GAAG,MAAM,CAAC;YAEpD,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,GAAG,MAAM,aAAa,CAAC,YAAY,CAAC,CAAC;YAC7D,IAAI,KAAK,EAAE;gBACT,OAAO,EAAE,OAAO,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC;aAC3C;YAED,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,OAAO,CAAC,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC,EAAE;gBACnD,MAAM,IAAI,KAAK,CAAC,qCAAqC,CAAC,CAAC;aACxD;YACD,MAAM,UAAU,GAAG,OAAO,CAAC,GAAG,CAAC,CAAC,GAAQ,EAAE,EAAE,CAAC,IAAI,GAAG,CAAC,IAAI,KAAK,GAAG,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACrF,MAAM,KAAK,GAAG,iBAAiB,SAAS,MAAM,UAAU,GAAG,CAAC;YAC5D,MAAM,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;YAC3B,OAAO;gBACL,OAAO,EAAE,IAAI;gBACb,OAAO,EAAE,UAAU,SAAS,yBAAyB;aACtD,CAAC;SACH;QAAC,OAAO,KAAK,EAAE;YACd,OAAO,CAAC,KAAK,CAAC,uBAAuB,EAAE,KAAK,CAAC,CAAC;YAC9C,OAAO;gBACL,OAAO,EAAE,KAAK;gBACd,OAAO,EAAE,2BAA2B,KAAK,EAAE;aAC5C,CAAC;SACH;IACH,CAAC;CACF"}
|