paygate-mcp 0.8.0 → 0.9.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/README.md CHANGED
@@ -30,6 +30,8 @@ Agent → PayGate (auth + billing) → Your MCP Server (stdio or HTTP)
30
30
  - **Credit Billing** — Each tool call costs credits (configurable per-tool)
31
31
  - **Rate Limiting** — Sliding window per-key rate limits + per-tool rate limits
32
32
  - **Usage Metering** — Track who called what, when, and how much they spent
33
+ - **Multi-Server Mode** — Wrap N MCP servers behind one PayGate with tool prefix routing
34
+ - **Client SDK** — `PayGateClient` with auto 402 retry, balance tracking, and typed errors
33
35
  - **Two Transports** — Wrap local servers via stdio or remote servers via Streamable HTTP
34
36
  - **Per-Tool ACL** — Whitelist/blacklist tools per API key (enterprise access control)
35
37
  - **Per-Tool Rate Limits** — Independent rate limits per tool, not just global
@@ -88,6 +90,75 @@ The proxy handles:
88
90
 
89
91
  When started, you'll see your admin key in the console. Save it.
90
92
 
93
+ ### Multi-Server Mode
94
+
95
+ Wrap multiple MCP servers behind a single PayGate instance. Tools are prefixed with the server name:
96
+
97
+ ```bash
98
+ npx paygate-mcp wrap --config multi-server.json
99
+ ```
100
+
101
+ Example `multi-server.json`:
102
+ ```json
103
+ {
104
+ "port": 3402,
105
+ "defaultCreditsPerCall": 1,
106
+ "servers": [
107
+ {
108
+ "prefix": "fs",
109
+ "serverCommand": "npx",
110
+ "serverArgs": ["@modelcontextprotocol/server-filesystem", "/tmp"]
111
+ },
112
+ {
113
+ "prefix": "github",
114
+ "remoteUrl": "https://github-mcp.example.com/mcp"
115
+ }
116
+ ]
117
+ }
118
+ ```
119
+
120
+ Tools are exposed with prefixes: `fs:read_file`, `fs:write_file`, `github:search_repos`, etc. Pricing and ACLs work on the prefixed names:
121
+
122
+ ```json
123
+ {
124
+ "toolPricing": {
125
+ "github:search_repos": { "creditsPerCall": 5 },
126
+ "fs:read_file": { "creditsPerCall": 1 }
127
+ }
128
+ }
129
+ ```
130
+
131
+ Credits are shared across all backends — one API key works for all servers.
132
+
133
+ ### Client SDK
134
+
135
+ Use `PayGateClient` to call tools from TypeScript/Node.js with auto 402 retry:
136
+
137
+ ```typescript
138
+ import { PayGateClient, PayGateError } from 'paygate-mcp/client';
139
+
140
+ const client = new PayGateClient({
141
+ url: 'http://localhost:3402',
142
+ apiKey: 'pg_abc123...',
143
+ autoRetry: true,
144
+ onCreditsNeeded: async (info) => {
145
+ // Called when credits run out — add credits and return true to retry
146
+ await topUpCredits(info.creditsRequired);
147
+ return true;
148
+ },
149
+ });
150
+
151
+ const tools = await client.listTools();
152
+ const result = await client.callTool('search', { query: 'hello' });
153
+ const balance = await client.getBalance();
154
+ ```
155
+
156
+ Features:
157
+ - **Auto 402 retry**: When a tool call returns payment-required, calls `onCreditsNeeded` and retries
158
+ - **Balance tracking**: `client.lastKnownBalance` tracks credits from `getBalance()` calls
159
+ - **Typed errors**: `PayGateError` with `.isPaymentRequired`, `.isRateLimited`, `.isExpired` helpers
160
+ - **Zero dependencies**: Uses Node.js built-in `http`/`https`
161
+
91
162
  ### Create API Keys
92
163
 
93
164
  ```bash
@@ -213,7 +284,7 @@ These MCP methods pass through without auth or billing:
213
284
  --config <path> Load settings from a JSON config file
214
285
  ```
215
286
 
216
- > **Note:** Use `--server` OR `--remote-url`, not both.
287
+ > **Note:** Use `--server` OR `--remote-url` for single-server mode. Use `servers` in a config file for multi-server mode.
217
288
 
218
289
  ### Persistent Storage
219
290
 
@@ -397,7 +468,7 @@ CLI flags override config file values when both are specified.
397
468
  ## Programmatic API
398
469
 
399
470
  ```typescript
400
- import { PayGateServer, HttpMcpProxy } from 'paygate-mcp';
471
+ import { PayGateServer } from 'paygate-mcp';
401
472
 
402
473
  // Wrap a local server (stdio)
403
474
  const server = new PayGateServer({
@@ -410,14 +481,28 @@ const server = new PayGateServer({
410
481
  },
411
482
  });
412
483
 
413
- // Or gate a remote server (Streamable HTTP)
414
- const remoteServer = new PayGateServer({
415
- serverCommand: '',
416
- port: 3402,
417
- defaultCreditsPerCall: 5,
418
- }, undefined, undefined, 'https://my-mcp-server.example.com/mcp');
419
-
420
484
  const { port, adminKey } = await server.start();
485
+
486
+ // Multi-server mode
487
+ const multiServer = new PayGateServer(
488
+ { serverCommand: '', port: 3402, defaultCreditsPerCall: 1 },
489
+ undefined, undefined, undefined, undefined,
490
+ [
491
+ { prefix: 'fs', serverCommand: 'npx', serverArgs: ['@modelcontextprotocol/server-filesystem', '/tmp'] },
492
+ { prefix: 'api', remoteUrl: 'https://my-mcp-server.example.com/mcp' },
493
+ ]
494
+ );
495
+
496
+ // Client SDK
497
+ import { PayGateClient } from 'paygate-mcp/client';
498
+
499
+ const client = new PayGateClient({
500
+ url: `http://localhost:${port}`,
501
+ apiKey: 'pg_...',
502
+ });
503
+
504
+ const tools = await client.listTools();
505
+ const result = await client.callTool('search', { query: 'hello' });
421
506
  ```
422
507
 
423
508
  ## Security
@@ -458,8 +543,8 @@ const { port, adminKey } = await server.start();
458
543
  - [x] Per-tool ACL — whitelist/blacklist tools per key
459
544
  - [x] Per-tool rate limits — independent limits per tool
460
545
  - [x] Key expiry (TTL) — auto-expire API keys
461
- - [ ] Multi-server mode — wrap N MCP servers behind one PayGate
462
- - [ ] Client SDK — `@paygate-mcp/client` with auto 402 retry
546
+ - [x] Multi-server mode — wrap N MCP servers behind one PayGate
547
+ - [x] Client SDK — `PayGateClient` with auto 402 retry
463
548
  - [ ] OAuth 2.1 — MCP spec mandates it for production
464
549
 
465
550
  ## Requirements
package/dist/cli.js CHANGED
@@ -76,6 +76,14 @@ function printUsage() {
76
76
  # Gate a remote MCP server (Streamable HTTP transport)
77
77
  paygate-mcp wrap --remote-url "https://my-server.example.com/mcp" --price 5
78
78
 
79
+ # Multi-server mode: wrap N servers behind one PayGate
80
+ paygate-mcp wrap --config multi-server.json
81
+ # Config file: { "servers": [
82
+ # { "prefix": "fs", "serverCommand": "npx", "serverArgs": ["@mcp/server-filesystem", "/tmp"] },
83
+ # { "prefix": "gh", "remoteUrl": "https://github-mcp.example.com/mcp" }
84
+ # ]}
85
+ # Tools become: "fs:read_file", "gh:search_repos", etc.
86
+
79
87
  # Custom pricing and rate limit
80
88
  paygate-mcp wrap --server "python my-server.py" --price 2 --rate-limit 30
81
89
 
@@ -114,13 +122,20 @@ async function main() {
114
122
  process.exit(1);
115
123
  }
116
124
  }
125
+ // Multi-server mode check
126
+ const multiServers = fileConfig.servers;
127
+ const isMultiServer = multiServers && multiServers.length > 0;
117
128
  const serverCmd = flags['server'] || (fileConfig.serverCommand ? [fileConfig.serverCommand, ...(fileConfig.serverArgs || [])].join(' ') : '');
118
129
  const remoteUrl = flags['remote-url'] || fileConfig.remoteUrl;
119
- if (!serverCmd && !remoteUrl) {
120
- console.error('Error: --server, --remote-url, or --config is required.\n');
130
+ if (!serverCmd && !remoteUrl && !isMultiServer) {
131
+ console.error('Error: --server, --remote-url, or --config (with servers[]) is required.\n');
121
132
  printUsage();
122
133
  process.exit(1);
123
134
  }
135
+ if (isMultiServer && (serverCmd || remoteUrl)) {
136
+ console.error('Error: use "servers" array OR --server/--remote-url, not both.\n');
137
+ process.exit(1);
138
+ }
124
139
  if (serverCmd && remoteUrl) {
125
140
  console.error('Error: use --server OR --remote-url, not both.\n');
126
141
  process.exit(1);
@@ -155,7 +170,7 @@ async function main() {
155
170
  toolPricing,
156
171
  webhookUrl,
157
172
  refundOnFailure: !!refundOnFailure,
158
- }, adminKey, stateFile, remoteUrl, stripeSecret);
173
+ }, adminKey, stateFile, remoteUrl, stripeSecret, multiServers);
159
174
  // Import keys from CLI flags
160
175
  if (flags['import-key']) {
161
176
  const pairs = flags['import-key'].split(',');
@@ -182,6 +197,18 @@ async function main() {
182
197
  process.on('SIGTERM', shutdown);
183
198
  try {
184
199
  const result = await server.start();
200
+ // Build backend display string
201
+ let backendDisplay;
202
+ if (isMultiServer) {
203
+ const prefixes = multiServers.map(s => s.prefix).join(', ');
204
+ backendDisplay = `multi (${multiServers.length}) → ${prefixes}`.slice(0, 35);
205
+ }
206
+ else if (remoteUrl) {
207
+ backendDisplay = ('HTTP → ' + remoteUrl.slice(0, 28));
208
+ }
209
+ else {
210
+ backendDisplay = ('stdio → ' + (serverCmd || serverCommand).slice(0, 27));
211
+ }
185
212
  console.log(`
186
213
  ╔══════════════════════════════════════════════════╗
187
214
  ║ PayGate MCP — Server Running ║
@@ -189,7 +216,7 @@ async function main() {
189
216
  ║ ║
190
217
  ║ Endpoint: http://localhost:${String(result.port).padEnd(5)} ║
191
218
  ║ Admin Key: ${result.adminKey.slice(0, 20)}... ║
192
- ║ Backend: ${(remoteUrl ? 'HTTP → ' + remoteUrl.slice(0, 28) : 'stdio → ' + (serverCmd || serverCommand).slice(0, 27)).padEnd(35)}║
219
+ ║ Backend: ${backendDisplay.padEnd(35)}║
193
220
  ║ ║
194
221
  ║ Pricing: ${String(price).padEnd(3)} credit(s) per tool call ║
195
222
  ║ Rate Limit: ${String(rateLimit).padEnd(3)} calls/min per key ║
@@ -208,6 +235,15 @@ async function main() {
208
235
  ║ POST /limits — Set spending limit (Admin) ║
209
236
  ╚══════════════════════════════════════════════════╝
210
237
  `);
238
+ // Show multi-server details
239
+ if (isMultiServer) {
240
+ console.log(' Multi-server backends:');
241
+ for (const s of multiServers) {
242
+ const transport = s.remoteUrl ? `HTTP → ${s.remoteUrl}` : `stdio → ${s.serverCommand} ${(s.serverArgs || []).join(' ')}`;
243
+ console.log(` ${s.prefix}: ${transport}`);
244
+ }
245
+ console.log('');
246
+ }
211
247
  console.log(` Admin key (save this): ${result.adminKey}\n`);
212
248
  }
213
249
  catch (error) {
package/dist/cli.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":";;AACA;;;;;;;GAOG;;AAEH,qCAAyC;AAEzC,2BAAkC;AAClC,+BAA4B;AAE5B,MAAM,WAAW,GAAG,CAAC,GAAG,EAAE;IACxB,IAAI,CAAC;QACH,MAAM,GAAG,GAAG,IAAI,CAAC,KAAK,CAAC,IAAA,iBAAY,EAAC,IAAA,WAAI,EAAC,SAAS,EAAE,IAAI,EAAE,cAAc,CAAC,EAAE,OAAO,CAAC,CAAC,CAAC;QACrF,OAAO,GAAG,CAAC,OAAO,IAAI,OAAO,CAAC;IAChC,CAAC;IAAC,MAAM,CAAC;QAAC,OAAO,OAAO,CAAC;IAAC,CAAC;AAC7B,CAAC,CAAC,EAAE,CAAC;AAEL,gFAAgF;AAEhF,SAAS,SAAS,CAAC,IAAc;IAC/B,MAAM,OAAO,GAAG,IAAI,CAAC,CAAC,CAAC,IAAI,MAAM,CAAC;IAClC,MAAM,KAAK,GAA2B,EAAE,CAAC;IAEzC,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,IAAI,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE,CAAC;QACrC,MAAM,GAAG,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;QACpB,IAAI,GAAG,CAAC,UAAU,CAAC,IAAI,CAAC,EAAE,CAAC;YACzB,MAAM,GAAG,GAAG,GAAG,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;YACzB,MAAM,IAAI,GAAG,IAAI,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;YACzB,IAAI,IAAI,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC,EAAE,CAAC;gBACnC,KAAK,CAAC,GAAG,CAAC,GAAG,IAAI,CAAC;gBAClB,CAAC,EAAE,CAAC;YACN,CAAC;iBAAM,CAAC;gBACN,KAAK,CAAC,GAAG,CAAC,GAAG,MAAM,CAAC;YACtB,CAAC;QACH,CAAC;IACH,CAAC;IAED,OAAO,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC;AAC5B,CAAC;AAED,SAAS,UAAU;IACjB,OAAO,CAAC,GAAG,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAkDX,CAAC,CAAC;AACL,CAAC;AAED,SAAS,gBAAgB,CAAC,KAAa;IACrC,MAAM,OAAO,GAAgC,EAAE,CAAC;IAChD,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;IAC/B,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,MAAM,CAAC,IAAI,EAAE,QAAQ,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;QACzC,IAAI,IAAI,IAAI,QAAQ,EAAE,CAAC;YACrB,OAAO,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC,GAAG,EAAE,cAAc,EAAE,QAAQ,CAAC,QAAQ,CAAC,IAAI,EAAE,EAAE,EAAE,CAAC,EAAE,CAAC;QAC3E,CAAC;IACH,CAAC;IACD,OAAO,OAAO,CAAC;AACjB,CAAC;AA0BD,gFAAgF;AAEhF,KAAK,UAAU,IAAI;IACjB,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,GAAG,SAAS,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;IAEnD,QAAQ,OAAO,EAAE,CAAC;QAChB,KAAK,MAAM,CAAC,CAAC,CAAC;YACZ,gCAAgC;YAChC,IAAI,UAAU,GAAe,EAAE,CAAC;YAChC,IAAI,KAAK,CAAC,QAAQ,CAAC,EAAE,CAAC;gBACpB,IAAI,CAAC;oBACH,MAAM,GAAG,GAAG,IAAA,iBAAY,EAAC,KAAK,CAAC,QAAQ,CAAC,EAAE,OAAO,CAAC,CAAC;oBACnD,UAAU,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;gBAC/B,CAAC;gBAAC,OAAO,GAAG,EAAE,CAAC;oBACb,OAAO,CAAC,KAAK,CAAC,8BAA+B,GAAa,CAAC,OAAO,EAAE,CAAC,CAAC;oBACtE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;gBAClB,CAAC;YACH,CAAC;YAED,0BAA0B;YAC1B,MAAM,YAAY,GAAsC,UAAU,CAAC,OAAO,CAAC;YAC3E,MAAM,aAAa,GAAG,YAAY,IAAI,YAAY,CAAC,MAAM,GAAG,CAAC,CAAC;YAE9D,MAAM,SAAS,GAAG,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,UAAU,CAAC,aAAa,CAAC,CAAC,CAAC,CAAC,UAAU,CAAC,aAAa,EAAE,GAAG,CAAC,UAAU,CAAC,UAAU,IAAI,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;YAC9I,MAAM,SAAS,GAAG,KAAK,CAAC,YAAY,CAAC,IAAI,UAAU,CAAC,SAAS,CAAC;YAE9D,IAAI,CAAC,SAAS,IAAI,CAAC,SAAS,IAAI,CAAC,aAAa,EAAE,CAAC;gBAC/C,OAAO,CAAC,KAAK,CAAC,4EAA4E,CAAC,CAAC;gBAC5F,UAAU,EAAE,CAAC;gBACb,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YAClB,CAAC;YAED,IAAI,aAAa,IAAI,CAAC,SAAS,IAAI,SAAS,CAAC,EAAE,CAAC;gBAC9C,OAAO,CAAC,KAAK,CAAC,kEAAkE,CAAC,CAAC;gBAClF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YAClB,CAAC;YAED,IAAI,SAAS,IAAI,SAAS,EAAE,CAAC;gBAC3B,OAAO,CAAC,KAAK,CAAC,kDAAkD,CAAC,CAAC;gBAClE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YAClB,CAAC;YAED,wDAAwD;YACxD,IAAI,aAAa,GAAG,UAAU,CAAC,aAAa,IAAI,EAAE,CAAC;YACnD,IAAI,UAAU,GAAa,UAAU,CAAC,UAAU,IAAI,EAAE,CAAC;YACvD,IAAI,KAAK,CAAC,QAAQ,CAAC,EAAE,CAAC;gBACpB,MAAM,KAAK,GAAG,KAAK,CAAC,QAAQ,CAAC,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;gBAC3C,aAAa,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;gBACzB,UAAU,GAAG,KAAK,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;YAC9B,CAAC;YAED,MAAM,IAAI,GAAG,QAAQ,CAAC,KAAK,CAAC,MAAM,CAAC,IAAI,MAAM,CAAC,UAAU,CAAC,IAAI,IAAI,IAAI,CAAC,EAAE,EAAE,CAAC,CAAC;YAC5E,MAAM,KAAK,GAAG,QAAQ,CAAC,KAAK,CAAC,OAAO,CAAC,IAAI,MAAM,CAAC,UAAU,CAAC,qBAAqB,IAAI,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;YAC5F,MAAM,SAAS,GAAG,QAAQ,CAAC,KAAK,CAAC,YAAY,CAAC,IAAI,MAAM,CAAC,UAAU,CAAC,qBAAqB,IAAI,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC;YACtG,MAAM,IAAI,GAAG,KAAK,CAAC,MAAM,CAAC,IAAI,UAAU,CAAC,aAAa,IAAI,oBAAoB,IAAI,oBAAoB,CAAC;YACvG,MAAM,UAAU,GAAG,KAAK,CAAC,QAAQ,CAAC,KAAK,MAAM,IAAI,CAAC,QAAQ,IAAI,KAAK,IAAI,KAAK,CAAC,QAAQ,CAAC,KAAK,SAAS,CAAC,IAAI,UAAU,CAAC,UAAU,IAAI,KAAK,CAAC;YACxI,MAAM,QAAQ,GAAG,KAAK,CAAC,WAAW,CAAC,IAAI,UAAU,CAAC,QAAQ,CAAC;YAC3D,MAAM,WAAW,GAAG,KAAK,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC,gBAAgB,CAAC,KAAK,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,UAAU,CAAC,WAAW,IAAI,EAAE,CAAC,CAAC;YACjH,MAAM,SAAS,GAAG,KAAK,CAAC,YAAY,CAAC,IAAI,UAAU,CAAC,SAAS,CAAC;YAC9D,MAAM,YAAY,GAAG,KAAK,CAAC,eAAe,CAAC,IAAI,UAAU,CAAC,mBAAmB,CAAC;YAC9E,MAAM,UAAU,GAAG,KAAK,CAAC,aAAa,CAAC,IAAI,UAAU,CAAC,UAAU,IAAI,IAAI,CAAC;YACzE,MAAM,eAAe,GAAG,KAAK,CAAC,mBAAmB,CAAC,KAAK,MAAM,IAAI,mBAAmB,IAAI,KAAK,IAAI,UAAU,CAAC,eAAe,IAAI,KAAK,CAAC;YAErI,MAAM,MAAM,GAAG,IAAI,sBAAa,CAAC;gBAC/B,aAAa;gBACb,UAAU;gBACV,IAAI;gBACJ,qBAAqB,EAAE,KAAK;gBAC5B,qBAAqB,EAAE,SAAS;gBAChC,IAAI;gBACJ,UAAU,EAAE,CAAC,CAAC,UAAU;gBACxB,WAAW;gBACX,UAAU;gBACV,eAAe,EAAE,CAAC,CAAC,eAAe;aACnC,EAAE,QAAQ,EAAE,SAAS,EAAE,SAAS,EAAE,YAAY,EAAE,YAAY,CAAC,CAAC;YAE/D,6BAA6B;YAC7B,IAAI,KAAK,CAAC,YAAY,CAAC,EAAE,CAAC;gBACxB,MAAM,KAAK,GAAG,KAAK,CAAC,YAAY,CAAC,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;gBAC7C,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;oBACzB,MAAM,CAAC,GAAG,EAAE,UAAU,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;oBAC1C,IAAI,GAAG,IAAI,UAAU,EAAE,CAAC;wBACtB,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,SAAS,CAAC,GAAG,CAAC,IAAI,EAAE,EAAE,UAAU,EAAE,QAAQ,CAAC,UAAU,CAAC,IAAI,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC;oBACvF,CAAC;gBACH,CAAC;YACH,CAAC;YAED,+BAA+B;YAC/B,IAAI,UAAU,CAAC,UAAU,EAAE,CAAC;gBAC1B,KAAK,MAAM,CAAC,GAAG,EAAE,OAAO,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,UAAU,CAAC,UAAU,CAAC,EAAE,CAAC;oBACnE,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,SAAS,CAAC,GAAG,EAAE,UAAU,EAAE,OAAO,CAAC,CAAC;gBACxD,CAAC;YACH,CAAC;YAED,2BAA2B;YAC3B,MAAM,QAAQ,GAAG,KAAK,IAAI,EAAE;gBAC1B,OAAO,CAAC,GAAG,CAAC,oBAAoB,CAAC,CAAC;gBAClC,MAAM,MAAM,CAAC,IAAI,EAAE,CAAC;gBACpB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YAClB,CAAC,CAAC;YACF,OAAO,CAAC,EAAE,CAAC,QAAQ,EAAE,QAAQ,CAAC,CAAC;YAC/B,OAAO,CAAC,EAAE,CAAC,SAAS,EAAE,QAAQ,CAAC,CAAC;YAEhC,IAAI,CAAC;gBACH,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,KAAK,EAAE,CAAC;gBAEpC,+BAA+B;gBAC/B,IAAI,cAAsB,CAAC;gBAC3B,IAAI,aAAa,EAAE,CAAC;oBAClB,MAAM,QAAQ,GAAG,YAAa,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;oBAC7D,cAAc,GAAG,UAAU,YAAa,CAAC,MAAM,OAAO,QAAQ,EAAE,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;gBAChF,CAAC;qBAAM,IAAI,SAAS,EAAE,CAAC;oBACrB,cAAc,GAAG,CAAC,SAAS,GAAG,SAAS,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;gBACxD,CAAC;qBAAM,CAAC;oBACN,cAAc,GAAG,CAAC,UAAU,GAAG,CAAC,SAAS,IAAI,aAAa,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;gBAC5E,CAAC;gBAED,OAAO,CAAC,GAAG,CAAC;;;;;oCAKgB,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC;mBAC9C,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC;mBAC5B,cAAc,CAAC,MAAM,CAAC,EAAE,CAAC;;mBAEzB,MAAM,CAAC,KAAK,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC;mBACvB,MAAM,CAAC,SAAS,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC;mBAC3B,MAAM,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC;mBAC9B,CAAC,SAAS,CAAC,CAAC,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,iBAAiB,CAAC,CAAC,MAAM,CAAC,EAAE,CAAC;mBACnE,CAAC,YAAY,CAAC,CAAC,CAAC,2BAA2B,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,MAAM,CAAC,EAAE,CAAC;mBAC/D,MAAM,CAAC,CAAC,CAAC,eAAe,CAAC,CAAC,MAAM,CAAC,EAAE,CAAC;mBACpC,CAAC,UAAU,CAAC,CAAC,CAAC,UAAU,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,MAAM,CAAC,EAAE,CAAC;;;;;;;;;;CAU3E,CAAC,CAAC;gBAEK,4BAA4B;gBAC5B,IAAI,aAAa,EAAE,CAAC;oBAClB,OAAO,CAAC,GAAG,CAAC,0BAA0B,CAAC,CAAC;oBACxC,KAAK,MAAM,CAAC,IAAI,YAAa,EAAE,CAAC;wBAC9B,MAAM,SAAS,GAAG,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,SAAS,EAAE,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC,aAAa,IAAI,CAAC,CAAC,CAAC,UAAU,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC;wBACzH,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC,MAAM,KAAK,SAAS,EAAE,CAAC,CAAC;oBAC/C,CAAC;oBACD,OAAO,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC;gBAClB,CAAC;gBAED,OAAO,CAAC,GAAG,CAAC,4BAA4B,MAAM,CAAC,QAAQ,IAAI,CAAC,CAAC;YAC/D,CAAC;YAAC,OAAO,KAAK,EAAE,CAAC;gBACf,OAAO,CAAC,KAAK,CAAC,yBAAyB,EAAE,KAAK,CAAC,CAAC;gBAChD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YAClB,CAAC;YACD,MAAM;QACR,CAAC;QAED,KAAK,MAAM,CAAC;QACZ,KAAK,QAAQ,CAAC;QACd,KAAK,IAAI;YACP,UAAU,EAAE,CAAC;YACb,MAAM;QAER,KAAK,SAAS,CAAC;QACf,KAAK,WAAW,CAAC;QACjB,KAAK,IAAI;YACP,OAAO,CAAC,GAAG,CAAC,gBAAgB,WAAW,EAAE,CAAC,CAAC;YAC3C,MAAM;QAER;YACE,OAAO,CAAC,KAAK,CAAC,oBAAoB,OAAO,IAAI,CAAC,CAAC;YAC/C,UAAU,EAAE,CAAC;YACb,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IACpB,CAAC;AACH,CAAC;AAED,IAAI,EAAE,CAAC,KAAK,CAAC,CAAC,KAAK,EAAE,EAAE;IACrB,OAAO,CAAC,KAAK,CAAC,cAAc,EAAE,KAAK,CAAC,CAAC;IACrC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC,CAAC,CAAC"}
@@ -0,0 +1,119 @@
1
+ /**
2
+ * PayGateClient — Client SDK for consuming PayGate-protected MCP servers.
3
+ *
4
+ * Features:
5
+ * - Auto 402 retry: when a tool call returns -32402 (payment required),
6
+ * the client can automatically call a top-up function and retry.
7
+ * - Balance tracking: monitors remaining credits locally.
8
+ * - Connection management: handles MCP Streamable HTTP transport.
9
+ *
10
+ * @example
11
+ * ```ts
12
+ * import { PayGateClient } from 'paygate-mcp/client';
13
+ *
14
+ * const client = new PayGateClient({
15
+ * url: 'http://localhost:3402',
16
+ * apiKey: 'pg_abc123...',
17
+ * });
18
+ *
19
+ * const tools = await client.listTools();
20
+ * const result = await client.callTool('search', { query: 'hello' });
21
+ * const balance = await client.getBalance();
22
+ * ```
23
+ */
24
+ export interface PayGateClientConfig {
25
+ /** PayGate server URL (e.g., "http://localhost:3402") */
26
+ url: string;
27
+ /** API key for authentication */
28
+ apiKey: string;
29
+ /** Request timeout in ms (default: 30000) */
30
+ timeout?: number;
31
+ /** Auto-retry on 402 (payment required). Calls onCreditsNeeded before retry.
32
+ * Default: false. */
33
+ autoRetry?: boolean;
34
+ /** Called when credits are needed (402 response). Return true if credits
35
+ * were added (e.g., via external top-up), false to abort. */
36
+ onCreditsNeeded?: (info: CreditsNeededInfo) => Promise<boolean>;
37
+ /** Max auto-retries per request (default: 1) */
38
+ maxRetries?: number;
39
+ }
40
+ export interface CreditsNeededInfo {
41
+ tool: string;
42
+ creditsRequired: number;
43
+ remainingCredits: number;
44
+ }
45
+ export interface ToolInfo {
46
+ name: string;
47
+ description?: string;
48
+ inputSchema?: Record<string, unknown>;
49
+ }
50
+ export interface ToolCallResult {
51
+ content: Array<{
52
+ type: string;
53
+ text?: string;
54
+ [k: string]: unknown;
55
+ }>;
56
+ isError?: boolean;
57
+ }
58
+ export interface BalanceInfo {
59
+ name: string;
60
+ credits: number;
61
+ totalSpent: number;
62
+ totalCalls: number;
63
+ spendingLimit: number;
64
+ remainingBudget: number | null;
65
+ lastUsedAt: string | null;
66
+ allowedTools: string[];
67
+ deniedTools: string[];
68
+ expiresAt: string | null;
69
+ }
70
+ export declare class PayGateClient {
71
+ private readonly baseUrl;
72
+ private readonly apiKey;
73
+ private readonly timeout;
74
+ private readonly autoRetry;
75
+ private readonly maxRetries;
76
+ private readonly onCreditsNeeded?;
77
+ private nextId;
78
+ private _lastBalance;
79
+ constructor(config: PayGateClientConfig);
80
+ /**
81
+ * List available tools from the gated MCP server.
82
+ */
83
+ listTools(): Promise<ToolInfo[]>;
84
+ /**
85
+ * Call a tool on the gated MCP server.
86
+ * If autoRetry is enabled and the server returns -32402 (payment required),
87
+ * the client will call onCreditsNeeded and retry.
88
+ */
89
+ callTool(name: string, args?: Record<string, unknown>): Promise<ToolCallResult>;
90
+ /**
91
+ * Get balance information for the current API key.
92
+ */
93
+ getBalance(): Promise<BalanceInfo>;
94
+ /**
95
+ * Send an initialize request to the MCP server.
96
+ */
97
+ initialize(): Promise<Record<string, unknown>>;
98
+ /**
99
+ * Ping the server.
100
+ */
101
+ ping(): Promise<boolean>;
102
+ /**
103
+ * Get the last known balance (from the last getBalance() call).
104
+ * Returns null if getBalance() hasn't been called yet.
105
+ */
106
+ get lastKnownBalance(): number | null;
107
+ private rpcCall;
108
+ private httpPost;
109
+ private httpGet;
110
+ }
111
+ export declare class PayGateError extends Error {
112
+ readonly code: number;
113
+ readonly data?: unknown;
114
+ constructor(code: number, message: string, data?: unknown);
115
+ get isPaymentRequired(): boolean;
116
+ get isRateLimited(): boolean;
117
+ get isExpired(): boolean;
118
+ }
119
+ //# sourceMappingURL=client.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;GAsBG;AAOH,MAAM,WAAW,mBAAmB;IAClC,yDAAyD;IACzD,GAAG,EAAE,MAAM,CAAC;IACZ,iCAAiC;IACjC,MAAM,EAAE,MAAM,CAAC;IACf,6CAA6C;IAC7C,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB;0BACsB;IACtB,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB;kEAC8D;IAC9D,eAAe,CAAC,EAAE,CAAC,IAAI,EAAE,iBAAiB,KAAK,OAAO,CAAC,OAAO,CAAC,CAAC;IAChE,gDAAgD;IAChD,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAED,MAAM,WAAW,iBAAiB;IAChC,IAAI,EAAE,MAAM,CAAC;IACb,eAAe,EAAE,MAAM,CAAC;IACxB,gBAAgB,EAAE,MAAM,CAAC;CAC1B;AAED,MAAM,WAAW,QAAQ;IACvB,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACvC;AAED,MAAM,WAAW,cAAc;IAC7B,OAAO,EAAE,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,IAAI,CAAC,EAAE,MAAM,CAAC;QAAC,CAAC,CAAC,EAAE,MAAM,GAAG,OAAO,CAAA;KAAE,CAAC,CAAC;IACtE,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AAED,MAAM,WAAW,WAAW;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,EAAE,MAAM,CAAC;IACnB,UAAU,EAAE,MAAM,CAAC;IACnB,aAAa,EAAE,MAAM,CAAC;IACtB,eAAe,EAAE,MAAM,GAAG,IAAI,CAAC;IAC/B,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;IAC1B,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,WAAW,EAAE,MAAM,EAAE,CAAC;IACtB,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;CAC1B;AAWD,qBAAa,aAAa;IACxB,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAM;IAC9B,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAS;IAChC,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAS;IACjC,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAU;IACpC,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAS;IACpC,OAAO,CAAC,QAAQ,CAAC,eAAe,CAAC,CAAgD;IACjF,OAAO,CAAC,MAAM,CAAK;IACnB,OAAO,CAAC,YAAY,CAAuB;gBAE/B,MAAM,EAAE,mBAAmB;IASvC;;OAEG;IACG,SAAS,IAAI,OAAO,CAAC,QAAQ,EAAE,CAAC;IAStC;;;;OAIG;IACG,QAAQ,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,OAAO,CAAC,cAAc,CAAC;IAmCrF;;OAEG;IACG,UAAU,IAAI,OAAO,CAAC,WAAW,CAAC;IAOxC;;OAEG;IACG,UAAU,IAAI,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAYpD;;OAEG;IACG,IAAI,IAAI,OAAO,CAAC,OAAO,CAAC;IAK9B;;;OAGG;IACH,IAAI,gBAAgB,IAAI,MAAM,GAAG,IAAI,CAEpC;YAIa,OAAO;IAiBrB,OAAO,CAAC,QAAQ;IAkChB,OAAO,CAAC,OAAO;CAqChB;AAID,qBAAa,YAAa,SAAQ,KAAK;IACrC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,IAAI,CAAC,EAAE,OAAO,CAAC;gBAEZ,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,OAAO;IAOzD,IAAI,iBAAiB,IAAI,OAAO,CAE/B;IAED,IAAI,aAAa,IAAI,OAAO,CAE3B;IAED,IAAI,SAAS,IAAI,OAAO,CAEvB;CACF"}
package/dist/client.js ADDED
@@ -0,0 +1,262 @@
1
+ "use strict";
2
+ /**
3
+ * PayGateClient — Client SDK for consuming PayGate-protected MCP servers.
4
+ *
5
+ * Features:
6
+ * - Auto 402 retry: when a tool call returns -32402 (payment required),
7
+ * the client can automatically call a top-up function and retry.
8
+ * - Balance tracking: monitors remaining credits locally.
9
+ * - Connection management: handles MCP Streamable HTTP transport.
10
+ *
11
+ * @example
12
+ * ```ts
13
+ * import { PayGateClient } from 'paygate-mcp/client';
14
+ *
15
+ * const client = new PayGateClient({
16
+ * url: 'http://localhost:3402',
17
+ * apiKey: 'pg_abc123...',
18
+ * });
19
+ *
20
+ * const tools = await client.listTools();
21
+ * const result = await client.callTool('search', { query: 'hello' });
22
+ * const balance = await client.getBalance();
23
+ * ```
24
+ */
25
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
26
+ if (k2 === undefined) k2 = k;
27
+ var desc = Object.getOwnPropertyDescriptor(m, k);
28
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
29
+ desc = { enumerable: true, get: function() { return m[k]; } };
30
+ }
31
+ Object.defineProperty(o, k2, desc);
32
+ }) : (function(o, m, k, k2) {
33
+ if (k2 === undefined) k2 = k;
34
+ o[k2] = m[k];
35
+ }));
36
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
37
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
38
+ }) : function(o, v) {
39
+ o["default"] = v;
40
+ });
41
+ var __importStar = (this && this.__importStar) || (function () {
42
+ var ownKeys = function(o) {
43
+ ownKeys = Object.getOwnPropertyNames || function (o) {
44
+ var ar = [];
45
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
46
+ return ar;
47
+ };
48
+ return ownKeys(o);
49
+ };
50
+ return function (mod) {
51
+ if (mod && mod.__esModule) return mod;
52
+ var result = {};
53
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
54
+ __setModuleDefault(result, mod);
55
+ return result;
56
+ };
57
+ })();
58
+ Object.defineProperty(exports, "__esModule", { value: true });
59
+ exports.PayGateError = exports.PayGateClient = void 0;
60
+ const http = __importStar(require("http"));
61
+ const https = __importStar(require("https"));
62
+ // ─── Client ─────────────────────────────────────────────────────────────────
63
+ class PayGateClient {
64
+ baseUrl;
65
+ apiKey;
66
+ timeout;
67
+ autoRetry;
68
+ maxRetries;
69
+ onCreditsNeeded;
70
+ nextId = 1;
71
+ _lastBalance = null;
72
+ constructor(config) {
73
+ this.baseUrl = new URL(config.url);
74
+ this.apiKey = config.apiKey;
75
+ this.timeout = config.timeout || 30_000;
76
+ this.autoRetry = config.autoRetry || false;
77
+ this.maxRetries = config.maxRetries || 1;
78
+ this.onCreditsNeeded = config.onCreditsNeeded;
79
+ }
80
+ /**
81
+ * List available tools from the gated MCP server.
82
+ */
83
+ async listTools() {
84
+ const response = await this.rpcCall('tools/list', {});
85
+ if (response.error) {
86
+ throw new PayGateError(response.error.code, response.error.message, response.error.data);
87
+ }
88
+ const result = response.result;
89
+ return result?.tools || [];
90
+ }
91
+ /**
92
+ * Call a tool on the gated MCP server.
93
+ * If autoRetry is enabled and the server returns -32402 (payment required),
94
+ * the client will call onCreditsNeeded and retry.
95
+ */
96
+ async callTool(name, args) {
97
+ let retries = 0;
98
+ while (true) {
99
+ const response = await this.rpcCall('tools/call', { name, arguments: args || {} });
100
+ if (response.error) {
101
+ // Check if it's a payment-required error
102
+ if (response.error.code === -32402 && this.autoRetry && retries < this.maxRetries) {
103
+ const data = response.error.data;
104
+ const creditsRequired = data?.creditsRequired || 0;
105
+ const remainingCredits = data?.remainingCredits || 0;
106
+ if (this.onCreditsNeeded) {
107
+ const shouldRetry = await this.onCreditsNeeded({
108
+ tool: name,
109
+ creditsRequired,
110
+ remainingCredits,
111
+ });
112
+ if (shouldRetry) {
113
+ retries++;
114
+ continue;
115
+ }
116
+ }
117
+ }
118
+ throw new PayGateError(response.error.code, response.error.message, response.error.data);
119
+ }
120
+ const result = response.result;
121
+ return result;
122
+ }
123
+ }
124
+ /**
125
+ * Get balance information for the current API key.
126
+ */
127
+ async getBalance() {
128
+ const response = await this.httpGet('/balance');
129
+ const balance = response;
130
+ this._lastBalance = balance.credits;
131
+ return balance;
132
+ }
133
+ /**
134
+ * Send an initialize request to the MCP server.
135
+ */
136
+ async initialize() {
137
+ const response = await this.rpcCall('initialize', {
138
+ protocolVersion: '2024-11-05',
139
+ capabilities: {},
140
+ clientInfo: { name: 'paygate-client', version: '1.0.0' },
141
+ });
142
+ if (response.error) {
143
+ throw new PayGateError(response.error.code, response.error.message, response.error.data);
144
+ }
145
+ return response.result;
146
+ }
147
+ /**
148
+ * Ping the server.
149
+ */
150
+ async ping() {
151
+ const response = await this.rpcCall('ping', {});
152
+ return !response.error;
153
+ }
154
+ /**
155
+ * Get the last known balance (from the last getBalance() call).
156
+ * Returns null if getBalance() hasn't been called yet.
157
+ */
158
+ get lastKnownBalance() {
159
+ return this._lastBalance;
160
+ }
161
+ // ─── Internal ─────────────────────────────────────────────────────────────
162
+ async rpcCall(method, params) {
163
+ const id = this.nextId++;
164
+ const body = JSON.stringify({
165
+ jsonrpc: '2.0',
166
+ id,
167
+ method,
168
+ params,
169
+ });
170
+ const responseBody = await this.httpPost('/mcp', body, {
171
+ 'Content-Type': 'application/json',
172
+ 'X-API-Key': this.apiKey,
173
+ });
174
+ return JSON.parse(responseBody);
175
+ }
176
+ httpPost(path, body, headers) {
177
+ return new Promise((resolve, reject) => {
178
+ const isHttps = this.baseUrl.protocol === 'https:';
179
+ const transport = isHttps ? https : http;
180
+ const options = {
181
+ hostname: this.baseUrl.hostname,
182
+ port: this.baseUrl.port || (isHttps ? 443 : 80),
183
+ path,
184
+ method: 'POST',
185
+ headers: {
186
+ ...headers,
187
+ 'Content-Length': String(Buffer.byteLength(body)),
188
+ },
189
+ timeout: this.timeout,
190
+ };
191
+ const req = transport.request(options, (res) => {
192
+ let data = '';
193
+ res.on('data', (chunk) => { data += chunk.toString(); });
194
+ res.on('end', () => resolve(data));
195
+ });
196
+ req.on('error', reject);
197
+ req.on('timeout', () => {
198
+ req.destroy();
199
+ reject(new Error(`Request timed out after ${this.timeout}ms`));
200
+ });
201
+ req.write(body);
202
+ req.end();
203
+ });
204
+ }
205
+ httpGet(path) {
206
+ return new Promise((resolve, reject) => {
207
+ const isHttps = this.baseUrl.protocol === 'https:';
208
+ const transport = isHttps ? https : http;
209
+ const options = {
210
+ hostname: this.baseUrl.hostname,
211
+ port: this.baseUrl.port || (isHttps ? 443 : 80),
212
+ path,
213
+ method: 'GET',
214
+ headers: {
215
+ 'X-API-Key': this.apiKey,
216
+ },
217
+ timeout: this.timeout,
218
+ };
219
+ const req = transport.request(options, (res) => {
220
+ let data = '';
221
+ res.on('data', (chunk) => { data += chunk.toString(); });
222
+ res.on('end', () => {
223
+ try {
224
+ resolve(JSON.parse(data));
225
+ }
226
+ catch {
227
+ reject(new Error(`Invalid JSON response: ${data.slice(0, 100)}`));
228
+ }
229
+ });
230
+ });
231
+ req.on('error', reject);
232
+ req.on('timeout', () => {
233
+ req.destroy();
234
+ reject(new Error(`Request timed out after ${this.timeout}ms`));
235
+ });
236
+ req.end();
237
+ });
238
+ }
239
+ }
240
+ exports.PayGateClient = PayGateClient;
241
+ // ─── Error class ──────────────────────────────────────────────────────────
242
+ class PayGateError extends Error {
243
+ code;
244
+ data;
245
+ constructor(code, message, data) {
246
+ super(message);
247
+ this.name = 'PayGateError';
248
+ this.code = code;
249
+ this.data = data;
250
+ }
251
+ get isPaymentRequired() {
252
+ return this.code === -32402;
253
+ }
254
+ get isRateLimited() {
255
+ return this.message.includes('rate_limit');
256
+ }
257
+ get isExpired() {
258
+ return this.message.includes('expired');
259
+ }
260
+ }
261
+ exports.PayGateError = PayGateError;
262
+ //# sourceMappingURL=client.js.map