@mcp-abap-adt/proxy 1.6.4 → 4.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/CHANGELOG.md +217 -0
- package/LICENSE +669 -17
- package/README.md +79 -8
- package/bin/mcp-abap-adt-proxy-mcp.js +113 -0
- package/dist/index.d.ts +10 -4
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +54 -97
- package/dist/lib/stores.d.ts +23 -2
- package/dist/lib/stores.d.ts.map +1 -1
- package/dist/lib/stores.js +56 -1
- package/dist/mcp/cli.d.ts +2 -0
- package/dist/mcp/cli.d.ts.map +1 -0
- package/dist/mcp/cli.js +21 -0
- package/dist/mcp/configs.d.ts +33 -0
- package/dist/mcp/configs.d.ts.map +1 -0
- package/dist/mcp/configs.js +142 -0
- package/dist/mcp/ports.d.ts +15 -0
- package/dist/mcp/ports.d.ts.map +1 -0
- package/dist/mcp/ports.js +35 -0
- package/dist/mcp/registry.d.ts +57 -0
- package/dist/mcp/registry.d.ts.map +1 -0
- package/dist/mcp/registry.js +145 -0
- package/dist/mcp/server.d.ts +34 -0
- package/dist/mcp/server.d.ts.map +1 -0
- package/dist/mcp/server.js +79 -0
- package/dist/mcp/shutdown.d.ts +37 -0
- package/dist/mcp/shutdown.d.ts.map +1 -0
- package/dist/mcp/shutdown.js +82 -0
- package/dist/mcp/supervisor.d.ts +125 -0
- package/dist/mcp/supervisor.d.ts.map +1 -0
- package/dist/mcp/supervisor.js +330 -0
- package/dist/mcp/tools.d.ts +28 -0
- package/dist/mcp/tools.d.ts.map +1 -0
- package/dist/mcp/tools.js +152 -0
- package/dist/proxy/btpProxy.d.ts +24 -73
- package/dist/proxy/btpProxy.d.ts.map +1 -1
- package/dist/proxy/btpProxy.js +116 -631
- package/dist/proxy/credentials.d.ts +45 -0
- package/dist/proxy/credentials.d.ts.map +1 -0
- package/dist/proxy/credentials.js +41 -0
- package/dist/proxy/requestHandler.d.ts +38 -0
- package/dist/proxy/requestHandler.d.ts.map +1 -0
- package/dist/proxy/requestHandler.js +73 -0
- package/dist/proxy/reverseProxy.d.ts +11 -2
- package/dist/proxy/reverseProxy.d.ts.map +1 -1
- package/dist/proxy/reverseProxy.js +52 -9
- package/dist/router/headerAnalyzer.js +2 -2
- package/dist/router/requestInterceptor.js +9 -9
- package/docs/API.md +172 -0
- package/docs/ARCHITECTURE.md +322 -0
- package/docs/CLIENT_SETUP.md +413 -0
- package/docs/CONFIGURATION.md +258 -0
- package/docs/MIGRATION-4.0.md +125 -0
- package/docs/ROUTING_LOGIC.md +126 -0
- package/docs/TROUBLESHOOTING.md +488 -0
- package/docs/USAGE.md +422 -0
- package/docs/YAML_CONFIG.md +273 -0
- package/docs/mcp-proxy-config.example.yaml +62 -0
- package/package.json +17 -10
- package/dist/proxy/cloudLlmHubProxy.d.ts +0 -2
- package/dist/proxy/cloudLlmHubProxy.d.ts.map +0 -1
- package/dist/proxy/cloudLlmHubProxy.js +0 -3
|
@@ -0,0 +1,413 @@
|
|
|
1
|
+
# Client Setup Guide
|
|
2
|
+
|
|
3
|
+
This guide provides step-by-step instructions for configuring Cline and GitHub Copilot to connect to MCP servers through the proxy.
|
|
4
|
+
|
|
5
|
+
## Table of Contents
|
|
6
|
+
|
|
7
|
+
- [Prerequisites](#prerequisites)
|
|
8
|
+
- [Cline Configuration](#cline-configuration)
|
|
9
|
+
- [GitHub Copilot Configuration](#github-copilot-configuration)
|
|
10
|
+
- [Configuration Scenarios](#configuration-scenarios)
|
|
11
|
+
- [Troubleshooting](#troubleshooting)
|
|
12
|
+
|
|
13
|
+
## Prerequisites
|
|
14
|
+
|
|
15
|
+
1. **Install the proxy**:
|
|
16
|
+
```bash
|
|
17
|
+
npm install -g @mcp-abap-adt/proxy
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
2. **Set up service keys** (for BTP destination-based authentication):
|
|
21
|
+
- Place service key files in platform-specific directories:
|
|
22
|
+
- **Unix/Linux/macOS**: `~/.config/mcp-abap-adt/service-keys/`
|
|
23
|
+
- **Windows**: `%USERPROFILE%\Documents\mcp-abap-adt\service-keys\`
|
|
24
|
+
- Service key files should be named after the destination (e.g., `btp-cloud.json`)
|
|
25
|
+
|
|
26
|
+
3. **Start the proxy server** (see scenarios below for specific commands)
|
|
27
|
+
|
|
28
|
+
## Cline Configuration
|
|
29
|
+
|
|
30
|
+
Cline uses the `streamableHttp` transport type and requires HTTP endpoint configuration.
|
|
31
|
+
|
|
32
|
+
### Basic Configuration File
|
|
33
|
+
|
|
34
|
+
Cline configuration is typically stored in:
|
|
35
|
+
- **macOS**: `~/Library/Application Support/Cline/cline.json`
|
|
36
|
+
- **Windows**: `%APPDATA%\Cline\cline.json`
|
|
37
|
+
- **Linux**: `~/.config/Cline/cline.json`
|
|
38
|
+
|
|
39
|
+
### Scenario 1: BTP Auth with Target URL Override
|
|
40
|
+
|
|
41
|
+
**Use Case**: Authenticate with a BTP destination's service key, but forward requests
|
|
42
|
+
to a different URL (e.g. direct OData testing or a non-standard MCP path).
|
|
43
|
+
|
|
44
|
+
**1. Start the proxy**:
|
|
45
|
+
```bash
|
|
46
|
+
mcp-abap-adt-proxy --btp=btp-cloud \
|
|
47
|
+
--target-url=https://your-service.cfapps.eu10.hana.ondemand.com
|
|
48
|
+
```
|
|
49
|
+
|
|
50
|
+
**2. Configure Cline** (`cline.json`):
|
|
51
|
+
```json
|
|
52
|
+
{
|
|
53
|
+
"mcpServers": {
|
|
54
|
+
"mcp-abap-adt-proxy": {
|
|
55
|
+
"disabled": false,
|
|
56
|
+
"timeout": 60,
|
|
57
|
+
"type": "streamableHttp",
|
|
58
|
+
"url": "http://localhost:3001/mcp/stream/http",
|
|
59
|
+
"headers": {
|
|
60
|
+
"x-sap-destination": "btp-cloud",
|
|
61
|
+
"x-target-url": "https://your-service.cfapps.eu10.hana.ondemand.com"
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
```
|
|
67
|
+
|
|
68
|
+
**What happens**:
|
|
69
|
+
- Proxy obtains a BTP token from the `btp-cloud` service key
|
|
70
|
+
- Forwards requests to `x-target-url` instead of the key's `abap.url`, with `Authorization: Bearer <token>`
|
|
71
|
+
|
|
72
|
+
### Scenario 2: BTP MCP Server with BTP Authentication
|
|
73
|
+
|
|
74
|
+
**Use Case**: Connect to an MCP server deployed on SAP BTP that requires BTP authentication.
|
|
75
|
+
|
|
76
|
+
**1. Set up BTP service key**:
|
|
77
|
+
- Create service key file: `~/.config/mcp-abap-adt/service-keys/btp-cloud.json`
|
|
78
|
+
```json
|
|
79
|
+
{
|
|
80
|
+
"uaa": {
|
|
81
|
+
"url": "https://your-uaa-url.authentication.eu10.hana.ondemand.com",
|
|
82
|
+
"clientid": "your-client-id",
|
|
83
|
+
"clientsecret": "your-client-secret"
|
|
84
|
+
},
|
|
85
|
+
"abap": {
|
|
86
|
+
"url": "https://mcp-server.cfapps.eu10.hana.ondemand.com"
|
|
87
|
+
}
|
|
88
|
+
}
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
**2. Start the proxy**:
|
|
92
|
+
```bash
|
|
93
|
+
mcp-abap-adt-proxy --btp=btp-cloud
|
|
94
|
+
```
|
|
95
|
+
|
|
96
|
+
**3. Configure Cline** (`cline.json`):
|
|
97
|
+
```json
|
|
98
|
+
{
|
|
99
|
+
"mcpServers": {
|
|
100
|
+
"mcp-abap-adt-proxy": {
|
|
101
|
+
"disabled": false,
|
|
102
|
+
"timeout": 60,
|
|
103
|
+
"type": "streamableHttp",
|
|
104
|
+
"url": "http://localhost:3001/mcp/stream/http",
|
|
105
|
+
"headers": {
|
|
106
|
+
"x-sap-destination": "btp-cloud"
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
```
|
|
112
|
+
|
|
113
|
+
**Alternative: Use command-line override** (simpler, no headers needed):
|
|
114
|
+
```bash
|
|
115
|
+
# Start proxy with command-line overrides
|
|
116
|
+
mcp-abap-adt-proxy --btp=btp-cloud
|
|
117
|
+
```
|
|
118
|
+
|
|
119
|
+
```json
|
|
120
|
+
{
|
|
121
|
+
"mcpServers": {
|
|
122
|
+
"mcp-abap-adt-proxy": {
|
|
123
|
+
"disabled": false,
|
|
124
|
+
"timeout": 60,
|
|
125
|
+
"type": "streamableHttp",
|
|
126
|
+
"url": "http://localhost:3001/mcp/stream/http"
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
```
|
|
131
|
+
|
|
132
|
+
**What happens**:
|
|
133
|
+
- Proxy gets BTP token from `btp-cloud` destination
|
|
134
|
+
- Adds `Authorization: Bearer <token>` header
|
|
135
|
+
- Gets MCP server URL from service key (`abap.url`)
|
|
136
|
+
- Forwards request to MCP server on BTP
|
|
137
|
+
|
|
138
|
+
## GitHub Copilot Configuration
|
|
139
|
+
|
|
140
|
+
GitHub Copilot supports multiple transport types. The configuration depends on your setup.
|
|
141
|
+
|
|
142
|
+
### Configuration File Location
|
|
143
|
+
|
|
144
|
+
GitHub Copilot configuration is typically stored in:
|
|
145
|
+
- **macOS**: `~/Library/Application Support/GitHub Copilot/settings.json`
|
|
146
|
+
- **Windows**: `%APPDATA%\GitHub Copilot\settings.json`
|
|
147
|
+
- **Linux**: `~/.config/GitHub Copilot/settings.json`
|
|
148
|
+
|
|
149
|
+
### Scenario 1: HTTP Transport (Recommended)
|
|
150
|
+
|
|
151
|
+
**1. Start the proxy** (same as Cline scenarios above):
|
|
152
|
+
```bash
|
|
153
|
+
mcp-abap-adt-proxy --btp=btp-cloud
|
|
154
|
+
```
|
|
155
|
+
|
|
156
|
+
**2. Configure GitHub Copilot** (`settings.json`):
|
|
157
|
+
```json
|
|
158
|
+
{
|
|
159
|
+
"mcpServers": {
|
|
160
|
+
"mcp-abap-adt-proxy": {
|
|
161
|
+
"disabled": false,
|
|
162
|
+
"timeout": 60,
|
|
163
|
+
"type": "streamableHttp",
|
|
164
|
+
"url": "http://localhost:3001/mcp/stream/http",
|
|
165
|
+
"headers": {
|
|
166
|
+
"x-sap-destination": "btp-cloud"
|
|
167
|
+
}
|
|
168
|
+
}
|
|
169
|
+
}
|
|
170
|
+
}
|
|
171
|
+
```
|
|
172
|
+
|
|
173
|
+
### Scenario 2: SSE Transport
|
|
174
|
+
|
|
175
|
+
**1. Start the proxy with SSE transport**:
|
|
176
|
+
```bash
|
|
177
|
+
mcp-abap-adt-proxy --transport=sse --btp=btp-cloud
|
|
178
|
+
```
|
|
179
|
+
|
|
180
|
+
**2. Configure GitHub Copilot** (`settings.json`):
|
|
181
|
+
```json
|
|
182
|
+
{
|
|
183
|
+
"mcpServers": {
|
|
184
|
+
"mcp-abap-adt-proxy": {
|
|
185
|
+
"disabled": false,
|
|
186
|
+
"timeout": 60,
|
|
187
|
+
"type": "sse",
|
|
188
|
+
"url": "http://localhost:3002",
|
|
189
|
+
"headers": {
|
|
190
|
+
"x-sap-destination": "btp-cloud"
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
}
|
|
195
|
+
```
|
|
196
|
+
|
|
197
|
+
**Note**: SSE transport uses port 3002 by default (HTTP uses 3001).
|
|
198
|
+
|
|
199
|
+
### Scenario 3: Stdio Transport
|
|
200
|
+
|
|
201
|
+
**1. Start the proxy with stdio transport**:
|
|
202
|
+
```bash
|
|
203
|
+
mcp-abap-adt-proxy --transport=stdio --btp=btp-cloud
|
|
204
|
+
```
|
|
205
|
+
|
|
206
|
+
**2. Configure GitHub Copilot** (`settings.json`):
|
|
207
|
+
```json
|
|
208
|
+
{
|
|
209
|
+
"mcpServers": {
|
|
210
|
+
"mcp-abap-adt-proxy": {
|
|
211
|
+
"disabled": false,
|
|
212
|
+
"timeout": 60,
|
|
213
|
+
"type": "stdio",
|
|
214
|
+
"command": "mcp-abap-adt-proxy",
|
|
215
|
+
"args": [
|
|
216
|
+
"--transport=stdio",
|
|
217
|
+
"--btp=btp-cloud"
|
|
218
|
+
]
|
|
219
|
+
}
|
|
220
|
+
}
|
|
221
|
+
}
|
|
222
|
+
```
|
|
223
|
+
|
|
224
|
+
**Note**: For stdio transport, the destination must be provided via command-line arguments (`--btp`, `--target-url`), not headers.
|
|
225
|
+
|
|
226
|
+
## The management mode
|
|
227
|
+
|
|
228
|
+
A second command, `mcp-abap-adt-proxy-mcp`, speaks MCP over stdio and its tools
|
|
229
|
+
start and stop proxies. Use it when the client should decide which proxy runs and
|
|
230
|
+
when; use `mcp-abap-adt-proxy` when you want to be proxied.
|
|
231
|
+
|
|
232
|
+
```json
|
|
233
|
+
{
|
|
234
|
+
"mcpServers": {
|
|
235
|
+
"abap-proxy": { "command": "mcp-abap-adt-proxy-mcp" }
|
|
236
|
+
}
|
|
237
|
+
}
|
|
238
|
+
```
|
|
239
|
+
|
|
240
|
+
It works from the configs in `~/.config/mcp-abap-adt/proxy/` — the same files
|
|
241
|
+
`--config` takes — so starting a proxy is choosing a name:
|
|
242
|
+
|
|
243
|
+
| Tool | |
|
|
244
|
+
|---|---|
|
|
245
|
+
| `proxy_configs` | the names available; call it first, they cannot be guessed |
|
|
246
|
+
| `proxy_start` | starts one on a **free port** and returns the URL bound |
|
|
247
|
+
| `proxy_stop` | frees the port and releases the credential; never touches another session's proxy |
|
|
248
|
+
| `proxy_status` | this session's proxies and everyone else's, dead records pruned on read |
|
|
249
|
+
|
|
250
|
+
Two things worth knowing before you rely on it:
|
|
251
|
+
|
|
252
|
+
- **The proxies live in the management process.** Closing the session — or
|
|
253
|
+
`SIGINT`, or `SIGTERM` — stops all of them. A stop cuts requests still in
|
|
254
|
+
flight after a short grace, because a streamed response never ends on its own
|
|
255
|
+
and the port has to come back.
|
|
256
|
+
- **`proxy_start` proves the credential before reporting success**, so an
|
|
257
|
+
interactive login happens where you asked for it rather than inside whatever
|
|
258
|
+
tool call happens to make the first request.
|
|
259
|
+
|
|
260
|
+
See [Configuration](./CONFIGURATION.md#the-management-mode) for `idleTimeoutMs`
|
|
261
|
+
and what the mode deliberately ignores from a config.
|
|
262
|
+
|
|
263
|
+
## Configuration Scenarios Summary
|
|
264
|
+
|
|
265
|
+
| Scenario | BTP Auth | Proxy Command | Headers Required |
|
|
266
|
+
|----------|----------|---------------|------------------|
|
|
267
|
+
| BTP MCP | Yes | `--btp=<dest>` | `x-sap-destination` |
|
|
268
|
+
| BTP MCP + explicit URL | Yes | `--btp=<dest> --target-url=<url>` | `x-sap-destination`, `x-target-url` |
|
|
269
|
+
|
|
270
|
+
## Advanced Configuration
|
|
271
|
+
|
|
272
|
+
### Using Environment Variables
|
|
273
|
+
|
|
274
|
+
You can configure the proxy using environment variables:
|
|
275
|
+
|
|
276
|
+
```bash
|
|
277
|
+
export MCP_HTTP_PORT=8080
|
|
278
|
+
export LOG_LEVEL=debug
|
|
279
|
+
mcp-abap-adt-proxy --btp=btp-cloud
|
|
280
|
+
```
|
|
281
|
+
|
|
282
|
+
### Using Configuration File
|
|
283
|
+
|
|
284
|
+
Create `mcp-proxy-config.json`:
|
|
285
|
+
|
|
286
|
+
```json
|
|
287
|
+
{
|
|
288
|
+
"httpPort": 3001,
|
|
289
|
+
"logLevel": "info",
|
|
290
|
+
"maxRetries": 3,
|
|
291
|
+
"requestTimeout": 60000
|
|
292
|
+
}
|
|
293
|
+
```
|
|
294
|
+
|
|
295
|
+
Start proxy:
|
|
296
|
+
```bash
|
|
297
|
+
mcp-abap-adt-proxy --btp=btp-cloud
|
|
298
|
+
```
|
|
299
|
+
|
|
300
|
+
### Session Storage
|
|
301
|
+
|
|
302
|
+
By default, sessions are stored in-memory (secure, lost on restart). To persist sessions to disk:
|
|
303
|
+
|
|
304
|
+
```bash
|
|
305
|
+
mcp-abap-adt-proxy --unsafe --btp=btp-cloud
|
|
306
|
+
```
|
|
307
|
+
|
|
308
|
+
**Warning**: `--unsafe` mode persists tokens to disk. Use only in development environments.
|
|
309
|
+
|
|
310
|
+
## Troubleshooting
|
|
311
|
+
|
|
312
|
+
### Issue: Connection Refused
|
|
313
|
+
|
|
314
|
+
**Symptoms**: Client cannot connect to proxy.
|
|
315
|
+
|
|
316
|
+
**Solutions**:
|
|
317
|
+
1. Verify proxy is running: `curl http://localhost:3001/mcp/stream/http`
|
|
318
|
+
2. Check port number matches configuration (default: 3001 for HTTP, 3002 for SSE)
|
|
319
|
+
3. Verify firewall settings allow connections to proxy port
|
|
320
|
+
|
|
321
|
+
### Issue: Authentication Failed
|
|
322
|
+
|
|
323
|
+
**Symptoms**: Proxy returns 401/403 errors.
|
|
324
|
+
|
|
325
|
+
**Solutions**:
|
|
326
|
+
1. Verify service key files exist in correct location
|
|
327
|
+
2. Check service key format (must contain `uaa` section for BTP destinations)
|
|
328
|
+
3. Verify destination names match between configuration and service key filenames
|
|
329
|
+
4. Enable verbose logging: `LOG_LEVEL=debug mcp-abap-adt-proxy ...`
|
|
330
|
+
|
|
331
|
+
### Issue: MCP Server Not Found
|
|
332
|
+
|
|
333
|
+
**Symptoms**: Proxy cannot reach target MCP server.
|
|
334
|
+
|
|
335
|
+
**Solutions**:
|
|
336
|
+
1. Verify `abap.url` in the service key (or `x-target-url`/`--target-url` override) points to the MCP server
|
|
337
|
+
2. Check network connectivity to MCP server
|
|
338
|
+
3. Verify MCP server is running and accessible
|
|
339
|
+
4. Verify the BTP destination (`--btp`/`x-sap-destination`) matches an existing service key
|
|
340
|
+
|
|
341
|
+
### Issue: Headers Not Passed Through
|
|
342
|
+
|
|
343
|
+
**Symptoms**: MCP server doesn't receive expected headers.
|
|
344
|
+
|
|
345
|
+
**Solutions**:
|
|
346
|
+
1. Remember: Only `x-sap-destination` is validated by proxy
|
|
347
|
+
2. All other headers are passed directly to MCP server
|
|
348
|
+
3. Verify headers are correctly formatted in client configuration
|
|
349
|
+
4. Check proxy logs for routing decisions
|
|
350
|
+
|
|
351
|
+
### Debug Mode
|
|
352
|
+
|
|
353
|
+
Enable verbose logging to troubleshoot issues:
|
|
354
|
+
|
|
355
|
+
```bash
|
|
356
|
+
# Environment variable
|
|
357
|
+
LOG_LEVEL=debug mcp-abap-adt-proxy --btp=<dest>
|
|
358
|
+
```
|
|
359
|
+
|
|
360
|
+
This will output detailed information about:
|
|
361
|
+
- Routing decisions
|
|
362
|
+
- Token retrieval
|
|
363
|
+
- Request forwarding
|
|
364
|
+
- Error details
|
|
365
|
+
|
|
366
|
+
## Quick Reference
|
|
367
|
+
|
|
368
|
+
### Proxy Command-Line Options
|
|
369
|
+
|
|
370
|
+
```bash
|
|
371
|
+
# Basic usage
|
|
372
|
+
mcp-abap-adt-proxy [options]
|
|
373
|
+
|
|
374
|
+
# Transport options
|
|
375
|
+
--transport=streamable-http # HTTP transport (default, port 3001)
|
|
376
|
+
--transport=sse # SSE transport (port 3002)
|
|
377
|
+
--transport=stdio # Stdio transport
|
|
378
|
+
|
|
379
|
+
# Destination overrides
|
|
380
|
+
--btp=<destination> # BTP destination name
|
|
381
|
+
--target-url=<url> # Override target URL (auth still from --btp)
|
|
382
|
+
|
|
383
|
+
# Port configuration
|
|
384
|
+
--http-port=<port> # HTTP port (default: 3001)
|
|
385
|
+
--sse-port=<port> # SSE port (default: 3002)
|
|
386
|
+
|
|
387
|
+
# Session storage
|
|
388
|
+
--unsafe # Enable file-based session storage
|
|
389
|
+
|
|
390
|
+
# Help
|
|
391
|
+
--help # Show help message
|
|
392
|
+
```
|
|
393
|
+
|
|
394
|
+
### Client Configuration Headers
|
|
395
|
+
|
|
396
|
+
| Header | Required | Description |
|
|
397
|
+
|--------|----------|-------------|
|
|
398
|
+
| `x-sap-destination` | Required* | BTP destination name for authentication |
|
|
399
|
+
| `x-target-url` | Optional | Override the target URL (auth still from the BTP destination) |
|
|
400
|
+
|
|
401
|
+
\* `x-sap-destination` (or the `--btp` command-line parameter) must be provided.
|
|
402
|
+
|
|
403
|
+
### Service Key Locations
|
|
404
|
+
|
|
405
|
+
- **Unix/Linux/macOS**: `~/.config/mcp-abap-adt/service-keys/<destination>.json`
|
|
406
|
+
- **Windows**: `%USERPROFILE%\Documents\mcp-abap-adt\service-keys\<destination>.json`
|
|
407
|
+
|
|
408
|
+
## Additional Resources
|
|
409
|
+
|
|
410
|
+
- [Configuration Guide](./CONFIGURATION.md) - Complete configuration reference
|
|
411
|
+
- [Usage Examples](./USAGE.md) - More usage examples
|
|
412
|
+
- [Routing Logic](./ROUTING_LOGIC.md) - Detailed routing logic
|
|
413
|
+
- [Troubleshooting Guide](./TROUBLESHOOTING.md) - Common issues and solutions
|
|
@@ -0,0 +1,258 @@
|
|
|
1
|
+
# Configuration Guide
|
|
2
|
+
|
|
3
|
+
This guide explains how to configure the MCP ABAP ADT Proxy server.
|
|
4
|
+
|
|
5
|
+
## The four folders
|
|
6
|
+
|
|
7
|
+
Everything the toolchain keeps on disk lives under one base:
|
|
8
|
+
|
|
9
|
+
```
|
|
10
|
+
~/.config/mcp-abap-adt/ (Windows: %USERPROFILE%\Documents\mcp-abap-adt\)
|
|
11
|
+
├── service-keys/ BTP service keys, one JSON per destination
|
|
12
|
+
├── sessions/ .env files holding credentials, referenced by a config's envFile
|
|
13
|
+
├── proxy/ one ready proxy config per proxy — the files --config takes
|
|
14
|
+
└── runtime/ one record per live proxy, so one session can see another's
|
|
15
|
+
```
|
|
16
|
+
|
|
17
|
+
`AUTH_BROKER_PATH` relocates the base, and all four move with it.
|
|
18
|
+
|
|
19
|
+
`runtime/` is written by the management mode and is not configuration: a file
|
|
20
|
+
per running proxy, holding its pid, port, URL, destination and config name. A
|
|
21
|
+
record is a claim, not a fact — every read checks the process behind it and
|
|
22
|
+
deletes the ones whose writer has died, so a crashed session cannot leave a
|
|
23
|
+
ghost behind.
|
|
24
|
+
|
|
25
|
+
## Configuration Methods
|
|
26
|
+
|
|
27
|
+
The proxy can be configured from a YAML/JSON file, from CLI parameters, or from a combination of both.
|
|
28
|
+
|
|
29
|
+
### Mode 1: Config file (`--config` / `-c`)
|
|
30
|
+
|
|
31
|
+
```bash
|
|
32
|
+
mcp-abap-adt-proxy --config=mcp-proxy-config.yaml
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
The file provides the baseline values. **CLI flags override values from the file** — handy for tweaking a single setting (port, browser mode, headers) on top of a stable config.
|
|
36
|
+
|
|
37
|
+
```bash
|
|
38
|
+
# YAML provides everything; CLI overrides browser mode and callback port:
|
|
39
|
+
mcp-abap-adt-proxy --config=mcp-proxy-config.yaml \
|
|
40
|
+
--browser none --browser-auth-port 8888
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
When CLI values override the file, the proxy logs a `Note: CLI flags override values from <path>: ...` warning so the override is visible.
|
|
44
|
+
|
|
45
|
+
`--header key=value` flags are merged with `defaultHeaders` from the file (CLI keys win on conflict). All other overrides replace the file value entirely.
|
|
46
|
+
|
|
47
|
+
Config string values and `--header` values support `${VAR}` / `${VAR:-default}`
|
|
48
|
+
interpolation, resolved from `process.env` then a `.env` (`envFile` in YAML or
|
|
49
|
+
`--env-file`). `process.env` wins; an unresolved `${VAR}` without a default fails
|
|
50
|
+
at startup. See [YAML Configuration Guide](./YAML_CONFIG.md) for details.
|
|
51
|
+
|
|
52
|
+
See [YAML Configuration Guide](./YAML_CONFIG.md) for the file format.
|
|
53
|
+
|
|
54
|
+
### Mode 2: CLI params + environment variables + defaults
|
|
55
|
+
|
|
56
|
+
Without `--config`, values come from CLI parameters, environment variables, and
|
|
57
|
+
built-in defaults. The config file is **not** consulted in this mode (and there is
|
|
58
|
+
no auto-discovery).
|
|
59
|
+
|
|
60
|
+
#### CLI parameters
|
|
61
|
+
|
|
62
|
+
| Flag | Description |
|
|
63
|
+
|------|-------------|
|
|
64
|
+
| `--btp=<destination>` | BTP destination for Cloud authorization |
|
|
65
|
+
| `--target-url=<url>` (alias `--url`) | Override target URL |
|
|
66
|
+
| `--unsafe` | Persist tokens to disk (default: in-memory) |
|
|
67
|
+
| `--header key=value` | Default header injected into every request (repeatable) |
|
|
68
|
+
| `--env-file <path>` | Path to a `.env` file supplying variables for `${VAR}` interpolation in config/headers (overrides YAML `envFile`) |
|
|
69
|
+
| `--browser=<type>` | OAuth2 login browser: `system`, `headless`, `chrome`, `edge`, `firefox`, `none` |
|
|
70
|
+
| `--browser-auth-port=<port>` | Port for the local OAuth2 callback server |
|
|
71
|
+
| `--transport`, `--http-port`, `--http-host`, `--sse-port`, `--sse-host` | Transport settings |
|
|
72
|
+
|
|
73
|
+
Run `mcp-abap-adt-proxy --help` for the full list.
|
|
74
|
+
|
|
75
|
+
### Headless login (`--browser none`)
|
|
76
|
+
|
|
77
|
+
With `--browser none` (or `headless`) the proxy does **not** open a browser. It
|
|
78
|
+
prints the authorization URL to the console and waits. Complete login in one of
|
|
79
|
+
two ways — whichever happens first wins:
|
|
80
|
+
|
|
81
|
+
- **Automatic callback** — open the URL on the **same machine** as the proxy;
|
|
82
|
+
the browser redirects to `http://localhost:<browser-auth-port>/callback`.
|
|
83
|
+
- **Paste form** — if your browser is on a **different machine**, open
|
|
84
|
+
`http://<proxy-host>:<browser-auth-port>/` and paste the `code` from the
|
|
85
|
+
address bar (or the whole redirected URL).
|
|
86
|
+
|
|
87
|
+
As of `@mcp-abap-adt/auth-providers` 2.0.0, pasting the code straight into the
|
|
88
|
+
proxy's terminal is **no longer supported**. The callback strategy reads no
|
|
89
|
+
stdin at all, deliberately: under an MCP stdio transport, stdin carries the
|
|
90
|
+
protocol itself, so a provider that read from it there would corrupt the
|
|
91
|
+
stream. If you relied on terminal paste, use the paste form above instead —
|
|
92
|
+
it covers the same "my browser is somewhere else" case without touching
|
|
93
|
+
stdin.
|
|
94
|
+
|
|
95
|
+
You have **5 minutes** from when the URL is printed to complete the login;
|
|
96
|
+
after that the callback server times out and the attempt fails. Run the same
|
|
97
|
+
command again to retry.
|
|
98
|
+
|
|
99
|
+
```bash
|
|
100
|
+
mcp-abap-adt-proxy --btp <dest> --browser none --browser-auth-port 3333
|
|
101
|
+
```
|
|
102
|
+
|
|
103
|
+
#### How long the callback port is held
|
|
104
|
+
|
|
105
|
+
The callback port is bound when the login window opens and released as soon as
|
|
106
|
+
the authorization code arrives — **before** it is exchanged for a token, not
|
|
107
|
+
after. The exchange is a round trip to the identity provider, and holding the
|
|
108
|
+
socket across it would keep the port busy for reasons that have nothing to do
|
|
109
|
+
with receiving the callback. The proxy keeps running without it: this is not a
|
|
110
|
+
listening port of the running proxy, only of the login.
|
|
111
|
+
|
|
112
|
+
The release is also unconditional. Since `auth-providers@1.2.0` the socket has
|
|
113
|
+
one owner and one release point, and it is freed on whatever ends the login
|
|
114
|
+
first — the code arriving, an explicit failure, the timeout, or cancellation —
|
|
115
|
+
so a settled login always means the port is already free.
|
|
116
|
+
|
|
117
|
+
Two consequences:
|
|
118
|
+
|
|
119
|
+
- **Two proxies can share one `browserAuthPort`, as long as their logins do not
|
|
120
|
+
overlap.** Whichever opens its login window first holds the port; a second one
|
|
121
|
+
starting during that window fails with `Port <n> is already in use` and exits.
|
|
122
|
+
Give each config its own port if you start several proxies at once.
|
|
123
|
+
- **A callback port that stays busy after a login means something else holds
|
|
124
|
+
it.** See [Troubleshooting](./TROUBLESHOOTING.md#error-port-n-is-already-in-use-naming-your-browserauthport).
|
|
125
|
+
|
|
126
|
+
Choose a number that no other local service uses. The proxy's callback port and
|
|
127
|
+
some other tool's main port colliding is the most common cause of this error.
|
|
128
|
+
|
|
129
|
+
## Environment Variables
|
|
130
|
+
|
|
131
|
+
#### Server Configuration
|
|
132
|
+
- `MCP_HTTP_PORT` - HTTP server port (default: `3001`)
|
|
133
|
+
- `MCP_SSE_PORT` - SSE server port (default: `3002`)
|
|
134
|
+
- `MCP_HTTP_HOST` - HTTP server host (default: `127.0.0.1`)
|
|
135
|
+
- `MCP_SSE_HOST` - SSE server host (default: `127.0.0.1`)
|
|
136
|
+
|
|
137
|
+
> **Note:** The default is `127.0.0.1` (loopback only) — the proxy runs locally and holds
|
|
138
|
+
> auth tokens, so it does not listen on all interfaces by default. Set `httpHost`/`sseHost`
|
|
139
|
+
> (or `MCP_HTTP_HOST`/`MCP_SSE_HOST`) to `0.0.0.0` only if you deliberately need to expose
|
|
140
|
+
> it. (SSE additionally rejects non-local connections regardless of host.)
|
|
141
|
+
- `MCP_TRANSPORT` - Transport type: `stdio`, `http`, `streamable-http`, or `sse`
|
|
142
|
+
|
|
143
|
+
#### Session Storage
|
|
144
|
+
- `MCP_PROXY_UNSAFE` - Set to `"true"` to persist tokens to disk (default: in-memory)
|
|
145
|
+
|
|
146
|
+
#### Error Handling & Resilience
|
|
147
|
+
- `MCP_PROXY_MAX_RETRIES` - Maximum number of retry attempts (default: `3`)
|
|
148
|
+
- `MCP_PROXY_RETRY_DELAY` - Delay between retries in milliseconds (default: `1000`)
|
|
149
|
+
- `MCP_PROXY_REQUEST_TIMEOUT` - Request timeout in milliseconds (default: `60000`)
|
|
150
|
+
- ~~`MCP_PROXY_CIRCUIT_BREAKER_THRESHOLD`~~, ~~`MCP_PROXY_CIRCUIT_BREAKER_TIMEOUT`~~ — **no effect since 4.0.0.** Still read, so existing setups load unchanged. The circuit breaker guarded the buffered forward that 4.0.0 removed; the forwarding path now streams and a breaker there would mean buffering the response again
|
|
151
|
+
|
|
152
|
+
#### Logging
|
|
153
|
+
- `LOG_LEVEL` - Logging level: `debug`, `info`, `warn`, `error` (default: `info`)
|
|
154
|
+
|
|
155
|
+
> **Note:** `--config` is the **only** way to load a config file. The
|
|
156
|
+
> `MCP_PROXY_CONFIG` environment variable is **not** honored.
|
|
157
|
+
|
|
158
|
+
## Configuration File
|
|
159
|
+
|
|
160
|
+
For the YAML/JSON config-file format and the full field reference, see the
|
|
161
|
+
[YAML Configuration Guide](./YAML_CONFIG.md). The file is loaded only via
|
|
162
|
+
`--config=<path>` (or `-c`).
|
|
163
|
+
|
|
164
|
+
## Examples
|
|
165
|
+
|
|
166
|
+
### Example 1: CLI parameters
|
|
167
|
+
|
|
168
|
+
```bash
|
|
169
|
+
mcp-abap-adt-proxy --transport=streamable-http --btp=btp \
|
|
170
|
+
--header x-sap-destination=S4HANA_E19
|
|
171
|
+
```
|
|
172
|
+
|
|
173
|
+
### Example 2: Environment variables
|
|
174
|
+
|
|
175
|
+
```bash
|
|
176
|
+
export MCP_HTTP_PORT=8080
|
|
177
|
+
export LOG_LEVEL=debug
|
|
178
|
+
mcp-abap-adt-proxy --btp=btp
|
|
179
|
+
```
|
|
180
|
+
|
|
181
|
+
### Example 3: Config file
|
|
182
|
+
|
|
183
|
+
```bash
|
|
184
|
+
mcp-abap-adt-proxy --config=mcp-proxy-config.yaml
|
|
185
|
+
```
|
|
186
|
+
|
|
187
|
+
### Example 4: Config file with CLI overrides
|
|
188
|
+
|
|
189
|
+
```bash
|
|
190
|
+
mcp-abap-adt-proxy --config=mcp-proxy-config.yaml \
|
|
191
|
+
--http-port=3003 --browser none --browser-auth-port=8888
|
|
192
|
+
```
|
|
193
|
+
|
|
194
|
+
YAML supplies the baseline; the four flags override `httpPort`, `browser`, and `browserAuthPort` from the file. See [YAML Configuration Guide](./YAML_CONFIG.md).
|
|
195
|
+
|
|
196
|
+
## Validation
|
|
197
|
+
|
|
198
|
+
The configuration is validated on server startup. Errors will prevent the server from starting, while warnings will be logged but won't stop the server.
|
|
199
|
+
|
|
200
|
+
### Common Validation Errors
|
|
201
|
+
|
|
202
|
+
- `MCP_HTTP_PORT must be between 1 and 65535` - Invalid port number
|
|
203
|
+
- `MCP_SSE_PORT must be between 1 and 65535` - Invalid port number
|
|
204
|
+
- `MCP_HTTP_PORT and MCP_SSE_PORT must be different` - Ports must be unique
|
|
205
|
+
|
|
206
|
+
### Common Validation Warnings
|
|
207
|
+
|
|
208
|
+
- `No BTP destination provided (--btp)` - Proxy won't work unless requests include an `x-sap-destination` header
|
|
209
|
+
- `MCP_PROXY_MAX_RETRIES should be between 0 and 10` - Retry count out of recommended range
|
|
210
|
+
- `MCP_PROXY_RETRY_DELAY should be between 0 and 60000ms` - Retry delay out of recommended range
|
|
211
|
+
- `MCP_PROXY_REQUEST_TIMEOUT should be between 1000 and 300000ms` - Timeout out of recommended range
|
|
212
|
+
|
|
213
|
+
## Best Practices
|
|
214
|
+
|
|
215
|
+
1. **Use a config file for stable setups** - Keep per-subaccount settings in a YAML file loaded via `--config`
|
|
216
|
+
2. **Use CLI params for quick overrides** - CLI flags override matching values from `--config` (handy for one-off tweaks like a different `--browser-auth-port`)
|
|
217
|
+
3. **Validate configuration** - Check logs for validation warnings on startup
|
|
218
|
+
4. **Set appropriate timeouts** - Adjust `requestTimeout` based on your network conditions
|
|
219
|
+
5. **Give each proxy its own `browserAuthPort`** - the callback socket is bound only for the duration of a login, but two logins cannot overlap on one port
|
|
220
|
+
|
|
221
|
+
## The management mode
|
|
222
|
+
|
|
223
|
+
`mcp-abap-adt-proxy-mcp` starts proxies from the configs in `proxy/` and differs
|
|
224
|
+
from `mcp-abap-adt-proxy` in exactly two ways, both deliberate:
|
|
225
|
+
|
|
226
|
+
- **The port in the config is ignored.** A free one is bound instead and
|
|
227
|
+
`proxy_start` reports the URL it got. Four of eight configs in practice declare
|
|
228
|
+
`httpPort: 3001`, so honouring it is what made running two of them impossible.
|
|
229
|
+
- **`httpHost` is ignored too**; the listener always binds `127.0.0.1`.
|
|
230
|
+
|
|
231
|
+
Everything else — destination, `targetUrl`, `defaultHeaders`, `browser`,
|
|
232
|
+
`browserAuthPort`, timeouts, `envFile` interpolation — comes from the config as
|
|
233
|
+
written.
|
|
234
|
+
|
|
235
|
+
One setting exists only here:
|
|
236
|
+
|
|
237
|
+
| Setting | Default | What it does |
|
|
238
|
+
|---|---|---|
|
|
239
|
+
| `idleTimeoutMs` (a `proxy_start` argument) | `1800000` (30 min) | Stops a proxy after this long with **nothing in flight**. The countdown runs only while no request is being carried, so an open SSE connection — quiet or not — is never called idle. `0` disables it. A backstop for a client that finished and forgot, not a substitute for `proxy_stop` |
|
|
240
|
+
|
|
241
|
+
## Troubleshooting
|
|
242
|
+
|
|
243
|
+
### Server won't start
|
|
244
|
+
|
|
245
|
+
- Check configuration validation errors in logs
|
|
246
|
+
- Ensure port numbers are valid and not in use
|
|
247
|
+
|
|
248
|
+
### Proxy requests failing
|
|
249
|
+
|
|
250
|
+
- Verify the BTP destination (`--btp` or `btpDestination`) matches an existing service key
|
|
251
|
+
- Check network connectivity to the target service
|
|
252
|
+
- Check token expiration errors
|
|
253
|
+
|
|
254
|
+
### High latency
|
|
255
|
+
|
|
256
|
+
- Increase `requestTimeout` if requests are timing out
|
|
257
|
+
- Adjust `retryDelay` for faster retries
|
|
258
|
+
|