mcp-subradar 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/dist/client.d.ts +6 -0
- package/dist/client.js +80 -0
- package/dist/client.js.map +1 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.js +88 -0
- package/dist/index.js.map +1 -0
- package/dist/tools/analytics.d.ts +3 -0
- package/dist/tools/analytics.js +42 -0
- package/dist/tools/analytics.js.map +1 -0
- package/dist/tools/cancel.d.ts +3 -0
- package/dist/tools/cancel.js +82 -0
- package/dist/tools/cancel.js.map +1 -0
- package/dist/tools/detect.d.ts +3 -0
- package/dist/tools/detect.js +66 -0
- package/dist/tools/detect.js.map +1 -0
- package/dist/tools/subscriptions.d.ts +3 -0
- package/dist/tools/subscriptions.js +110 -0
- package/dist/tools/subscriptions.js.map +1 -0
- package/package.json +46 -0
package/dist/client.d.ts
ADDED
package/dist/client.js
ADDED
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// ─────────────────────────────────────────────────────────────────────────────
|
|
3
|
+
// SubRadar MCP Server — HTTP client
|
|
4
|
+
//
|
|
5
|
+
// Wraps every SubRadar REST endpoint with a typed fetch call.
|
|
6
|
+
// Reads SUBRADAR_API_URL and SUBRADAR_API_KEY from the environment.
|
|
7
|
+
//
|
|
8
|
+
// Usage:
|
|
9
|
+
// import { client } from './client';
|
|
10
|
+
// const result = await client.post('/v1/detect', { userId, transactions });
|
|
11
|
+
// ─────────────────────────────────────────────────────────────────────────────
|
|
12
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
13
|
+
exports.client = void 0;
|
|
14
|
+
const BASE_URL = (process.env['SUBRADAR_API_URL'] ?? 'http://localhost:3001').replace(/\/$/, '');
|
|
15
|
+
const API_KEY = process.env['SUBRADAR_API_KEY'] ?? '';
|
|
16
|
+
function headers() {
|
|
17
|
+
return {
|
|
18
|
+
'Content-Type': 'application/json',
|
|
19
|
+
'X-API-Key': API_KEY,
|
|
20
|
+
};
|
|
21
|
+
}
|
|
22
|
+
function toQueryString(params) {
|
|
23
|
+
const parts = [];
|
|
24
|
+
for (const [k, v] of Object.entries(params)) {
|
|
25
|
+
if (v === undefined || v === null)
|
|
26
|
+
continue;
|
|
27
|
+
parts.push(`${encodeURIComponent(k)}=${encodeURIComponent(String(v))}`);
|
|
28
|
+
}
|
|
29
|
+
return parts.length ? '?' + parts.join('&') : '';
|
|
30
|
+
}
|
|
31
|
+
async function handleResponse(res) {
|
|
32
|
+
const text = await res.text();
|
|
33
|
+
let body;
|
|
34
|
+
try {
|
|
35
|
+
body = JSON.parse(text);
|
|
36
|
+
}
|
|
37
|
+
catch {
|
|
38
|
+
body = text;
|
|
39
|
+
}
|
|
40
|
+
if (!res.ok) {
|
|
41
|
+
const msg = typeof body === 'object' && body !== null
|
|
42
|
+
? JSON.stringify(body)
|
|
43
|
+
: text;
|
|
44
|
+
throw new Error(`SubRadar API error ${res.status}: ${msg}`);
|
|
45
|
+
}
|
|
46
|
+
return body;
|
|
47
|
+
}
|
|
48
|
+
exports.client = {
|
|
49
|
+
async get(path, params = {}) {
|
|
50
|
+
const url = `${BASE_URL}${path}${toQueryString(params)}`;
|
|
51
|
+
const res = await fetch(url, { method: 'GET', headers: headers() });
|
|
52
|
+
return handleResponse(res);
|
|
53
|
+
},
|
|
54
|
+
async post(path, body) {
|
|
55
|
+
const url = `${BASE_URL}${path}`;
|
|
56
|
+
const res = await fetch(url, {
|
|
57
|
+
method: 'POST',
|
|
58
|
+
headers: headers(),
|
|
59
|
+
body: JSON.stringify(body),
|
|
60
|
+
});
|
|
61
|
+
return handleResponse(res);
|
|
62
|
+
},
|
|
63
|
+
async patch(path, body) {
|
|
64
|
+
const url = `${BASE_URL}${path}`;
|
|
65
|
+
const res = await fetch(url, {
|
|
66
|
+
method: 'PATCH',
|
|
67
|
+
headers: headers(),
|
|
68
|
+
body: JSON.stringify(body),
|
|
69
|
+
});
|
|
70
|
+
return handleResponse(res);
|
|
71
|
+
},
|
|
72
|
+
async delete(path) {
|
|
73
|
+
const url = `${BASE_URL}${path}`;
|
|
74
|
+
const res = await fetch(url, { method: 'DELETE', headers: headers() });
|
|
75
|
+
if (res.status === 204)
|
|
76
|
+
return null;
|
|
77
|
+
return handleResponse(res);
|
|
78
|
+
},
|
|
79
|
+
};
|
|
80
|
+
//# sourceMappingURL=client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"client.js","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
ADDED
package/dist/index.js
ADDED
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
"use strict";
|
|
3
|
+
// ─────────────────────────────────────────────────────────────────────────────
|
|
4
|
+
// SubRadar MCP Server — entry point
|
|
5
|
+
//
|
|
6
|
+
// Exposes all SubRadar tools over stdio following the MCP protocol.
|
|
7
|
+
// Configure via environment variables:
|
|
8
|
+
// SUBRADAR_API_URL — base URL of the SubRadar API (default: http://localhost:3001)
|
|
9
|
+
// SUBRADAR_API_KEY — API key for X-API-Key header (required)
|
|
10
|
+
//
|
|
11
|
+
// Usage:
|
|
12
|
+
// node dist/index.js
|
|
13
|
+
// ─────────────────────────────────────────────────────────────────────────────
|
|
14
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
15
|
+
require("dotenv/config");
|
|
16
|
+
const index_js_1 = require("@modelcontextprotocol/sdk/server/index.js");
|
|
17
|
+
const stdio_js_1 = require("@modelcontextprotocol/sdk/server/stdio.js");
|
|
18
|
+
const types_js_1 = require("@modelcontextprotocol/sdk/types.js");
|
|
19
|
+
const detect_1 = require("./tools/detect");
|
|
20
|
+
const subscriptions_1 = require("./tools/subscriptions");
|
|
21
|
+
const cancel_1 = require("./tools/cancel");
|
|
22
|
+
const analytics_1 = require("./tools/analytics");
|
|
23
|
+
// ── Tool registry ─────────────────────────────────────────────────────────────
|
|
24
|
+
const ALL_TOOLS = [
|
|
25
|
+
...detect_1.detectTools,
|
|
26
|
+
...subscriptions_1.subscriptionTools,
|
|
27
|
+
...cancel_1.cancelTools,
|
|
28
|
+
...analytics_1.analyticsTools,
|
|
29
|
+
];
|
|
30
|
+
const DETECT_NAMES = new Set(detect_1.detectTools.map(t => t.name));
|
|
31
|
+
const SUBSCRIPTION_NAMES = new Set(subscriptions_1.subscriptionTools.map(t => t.name));
|
|
32
|
+
const CANCEL_NAMES = new Set(cancel_1.cancelTools.map(t => t.name));
|
|
33
|
+
const ANALYTICS_NAMES = new Set(analytics_1.analyticsTools.map(t => t.name));
|
|
34
|
+
// ── Server setup ──────────────────────────────────────────────────────────────
|
|
35
|
+
const server = new index_js_1.Server({ name: 'mcp-subRadar', version: '1.0.0' }, { capabilities: { tools: {} } });
|
|
36
|
+
// ── Handlers ──────────────────────────────────────────────────────────────────
|
|
37
|
+
server.setRequestHandler(types_js_1.ListToolsRequestSchema, async () => ({
|
|
38
|
+
tools: ALL_TOOLS,
|
|
39
|
+
}));
|
|
40
|
+
server.setRequestHandler(types_js_1.CallToolRequestSchema, async (request) => {
|
|
41
|
+
const { name, arguments: rawArgs } = request.params;
|
|
42
|
+
const args = (rawArgs ?? {});
|
|
43
|
+
try {
|
|
44
|
+
let result;
|
|
45
|
+
if (DETECT_NAMES.has(name)) {
|
|
46
|
+
result = await (0, detect_1.handleDetectTool)(name, args);
|
|
47
|
+
}
|
|
48
|
+
else if (SUBSCRIPTION_NAMES.has(name)) {
|
|
49
|
+
result = await (0, subscriptions_1.handleSubscriptionTool)(name, args);
|
|
50
|
+
}
|
|
51
|
+
else if (CANCEL_NAMES.has(name)) {
|
|
52
|
+
result = await (0, cancel_1.handleCancelTool)(name, args);
|
|
53
|
+
}
|
|
54
|
+
else if (ANALYTICS_NAMES.has(name)) {
|
|
55
|
+
result = await (0, analytics_1.handleAnalyticsTool)(name, args);
|
|
56
|
+
}
|
|
57
|
+
else {
|
|
58
|
+
return {
|
|
59
|
+
content: [{ type: 'text', text: `Unknown tool: ${name}` }],
|
|
60
|
+
isError: true,
|
|
61
|
+
};
|
|
62
|
+
}
|
|
63
|
+
return {
|
|
64
|
+
content: [{
|
|
65
|
+
type: 'text',
|
|
66
|
+
text: JSON.stringify(result, null, 2),
|
|
67
|
+
}],
|
|
68
|
+
};
|
|
69
|
+
}
|
|
70
|
+
catch (err) {
|
|
71
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
72
|
+
return {
|
|
73
|
+
content: [{ type: 'text', text: `Error calling ${name}: ${message}` }],
|
|
74
|
+
isError: true,
|
|
75
|
+
};
|
|
76
|
+
}
|
|
77
|
+
});
|
|
78
|
+
// ── Start ─────────────────────────────────────────────────────────────────────
|
|
79
|
+
async function main() {
|
|
80
|
+
const transport = new stdio_js_1.StdioServerTransport();
|
|
81
|
+
await server.connect(transport);
|
|
82
|
+
process.stderr.write('mcp-subRadar running\n');
|
|
83
|
+
}
|
|
84
|
+
main().catch((err) => {
|
|
85
|
+
process.stderr.write(`Fatal: ${err instanceof Error ? err.message : String(err)}\n`);
|
|
86
|
+
process.exit(1);
|
|
87
|
+
});
|
|
88
|
+
//# 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,42 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// ─────────────────────────────────────────────────────────────────────────────
|
|
3
|
+
// SubRadar MCP Tools — Analytics (1 tool)
|
|
4
|
+
//
|
|
5
|
+
// get_analytics GET /v1/analytics/:userId
|
|
6
|
+
// ─────────────────────────────────────────────────────────────────────────────
|
|
7
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
8
|
+
exports.analyticsTools = void 0;
|
|
9
|
+
exports.handleAnalyticsTool = handleAnalyticsTool;
|
|
10
|
+
const client_1 = require("../client");
|
|
11
|
+
exports.analyticsTools = [
|
|
12
|
+
{
|
|
13
|
+
name: 'get_analytics',
|
|
14
|
+
description: 'Use this tool to get a complete financial picture of a user\'s subscription spend. ' +
|
|
15
|
+
'Returns: total monthly spend, projected annual cost, subscription count broken down by status (active/cancelled/paused), ' +
|
|
16
|
+
'full subscription list, potential monthly savings if all active subscriptions were cancelled, ' +
|
|
17
|
+
'and high-spend alerts for subscriptions costing more than $30/month. ' +
|
|
18
|
+
'Run detect_subscriptions (with saveResults=true) or add_subscription before calling this tool to populate the user\'s data.',
|
|
19
|
+
inputSchema: {
|
|
20
|
+
type: 'object',
|
|
21
|
+
required: ['userId'],
|
|
22
|
+
properties: {
|
|
23
|
+
userId: {
|
|
24
|
+
type: 'string',
|
|
25
|
+
description: 'User identifier to fetch analytics for.',
|
|
26
|
+
},
|
|
27
|
+
},
|
|
28
|
+
additionalProperties: false,
|
|
29
|
+
},
|
|
30
|
+
},
|
|
31
|
+
];
|
|
32
|
+
async function handleAnalyticsTool(name, args) {
|
|
33
|
+
switch (name) {
|
|
34
|
+
case 'get_analytics': {
|
|
35
|
+
const { userId } = args;
|
|
36
|
+
return client_1.client.get(`/v1/analytics/${userId}`);
|
|
37
|
+
}
|
|
38
|
+
default:
|
|
39
|
+
throw new Error(`Unknown analytics tool: ${name}`);
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
//# sourceMappingURL=analytics.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"analytics.js","sourceRoot":"","sources":["../../src/tools/analytics.ts"],"names":[],"mappings":";AAAA,gFAAgF;AAChF,0CAA0C;AAC1C,EAAE;AACF,8CAA8C;AAC9C,gFAAgF;;;AA4BhF,kDAaC;AAtCD,sCAAmC;AAEtB,QAAA,cAAc,GAAW;IACpC;QACE,IAAI,EAAE,eAAe;QACrB,WAAW,EACT,qFAAqF;YACrF,2HAA2H;YAC3H,gGAAgG;YAChG,uEAAuE;YACvE,6HAA6H;QAC/H,WAAW,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,QAAQ,EAAE,CAAC,QAAQ,CAAC;YACpB,UAAU,EAAE;gBACV,MAAM,EAAE;oBACN,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,yCAAyC;iBACvD;aACF;YACD,oBAAoB,EAAE,KAAK;SAC5B;KACF;CACF,CAAC;AAEK,KAAK,UAAU,mBAAmB,CACvC,IAAY,EACZ,IAA6B;IAE7B,QAAQ,IAAI,EAAE,CAAC;QACb,KAAK,eAAe,CAAC,CAAC,CAAC;YACrB,MAAM,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;YACxB,OAAO,eAAM,CAAC,GAAG,CAAC,iBAAiB,MAAM,EAAE,CAAC,CAAC;QAC/C,CAAC;QAED;YACE,MAAM,IAAI,KAAK,CAAC,2BAA2B,IAAI,EAAE,CAAC,CAAC;IACvD,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// ─────────────────────────────────────────────────────────────────────────────
|
|
3
|
+
// SubRadar MCP Tools — Cancellation intelligence (2 tools)
|
|
4
|
+
//
|
|
5
|
+
// get_cancellation_info GET /v1/cancel/:merchantName
|
|
6
|
+
// draft_cancellation_message POST /v1/cancel/draft
|
|
7
|
+
// ─────────────────────────────────────────────────────────────────────────────
|
|
8
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
9
|
+
exports.cancelTools = void 0;
|
|
10
|
+
exports.handleCancelTool = handleCancelTool;
|
|
11
|
+
const client_1 = require("../client");
|
|
12
|
+
exports.cancelTools = [
|
|
13
|
+
{
|
|
14
|
+
name: 'get_cancellation_info',
|
|
15
|
+
description: 'Use this tool to look up step-by-step cancellation instructions for a specific merchant. ' +
|
|
16
|
+
'Returns: cancel URL, phone number, difficulty rating (easy/medium/hard), difficulty score (1–10), ' +
|
|
17
|
+
'step-by-step instructions, and warnings about dark patterns the merchant uses to prevent cancellation. ' +
|
|
18
|
+
'Supports 24+ major services including Netflix, Spotify, Adobe, Amazon Prime, gym memberships, and more. ' +
|
|
19
|
+
'Call list_cancellation_merchants first if you are unsure whether a merchant is in the database.',
|
|
20
|
+
inputSchema: {
|
|
21
|
+
type: 'object',
|
|
22
|
+
required: ['merchantName'],
|
|
23
|
+
properties: {
|
|
24
|
+
merchantName: {
|
|
25
|
+
type: 'string',
|
|
26
|
+
description: 'Name of the merchant to look up (e.g. "Netflix", "Adobe Creative Cloud", "Planet Fitness"). Partial matches are supported.',
|
|
27
|
+
},
|
|
28
|
+
},
|
|
29
|
+
additionalProperties: false,
|
|
30
|
+
},
|
|
31
|
+
},
|
|
32
|
+
{
|
|
33
|
+
name: 'draft_cancellation_message',
|
|
34
|
+
description: 'Use this tool to generate a ready-to-send cancellation email or phone script for a given merchant. ' +
|
|
35
|
+
'For "email" format: returns a formal cancellation email with subject line and body. ' +
|
|
36
|
+
'For "script" format: returns a guided phone call script with suggested responses to common retention tactics. ' +
|
|
37
|
+
'Also returns tips specific to the merchant (dark patterns, fees, gotchas) when available.',
|
|
38
|
+
inputSchema: {
|
|
39
|
+
type: 'object',
|
|
40
|
+
required: ['merchant'],
|
|
41
|
+
properties: {
|
|
42
|
+
merchant: {
|
|
43
|
+
type: 'string',
|
|
44
|
+
description: 'Merchant / service name to cancel (e.g. "Netflix").',
|
|
45
|
+
},
|
|
46
|
+
subscriptionId: {
|
|
47
|
+
type: 'string',
|
|
48
|
+
description: 'Optional subscription ID for reference in the message.',
|
|
49
|
+
},
|
|
50
|
+
userId: {
|
|
51
|
+
type: 'string',
|
|
52
|
+
description: 'Optional user identifier.',
|
|
53
|
+
},
|
|
54
|
+
reason: {
|
|
55
|
+
type: 'string',
|
|
56
|
+
description: 'Optional reason for cancellation (will be included in the message).',
|
|
57
|
+
example: 'I no longer use this service',
|
|
58
|
+
},
|
|
59
|
+
format: {
|
|
60
|
+
type: 'string',
|
|
61
|
+
enum: ['email', 'script'],
|
|
62
|
+
default: 'email',
|
|
63
|
+
description: '"email" generates a cancellation email; "script" generates a phone call guide.',
|
|
64
|
+
},
|
|
65
|
+
},
|
|
66
|
+
additionalProperties: false,
|
|
67
|
+
},
|
|
68
|
+
},
|
|
69
|
+
];
|
|
70
|
+
async function handleCancelTool(name, args) {
|
|
71
|
+
switch (name) {
|
|
72
|
+
case 'get_cancellation_info': {
|
|
73
|
+
const { merchantName } = args;
|
|
74
|
+
return client_1.client.get(`/v1/cancel/${encodeURIComponent(String(merchantName))}`);
|
|
75
|
+
}
|
|
76
|
+
case 'draft_cancellation_message':
|
|
77
|
+
return client_1.client.post('/v1/cancel/draft', args);
|
|
78
|
+
default:
|
|
79
|
+
throw new Error(`Unknown cancel tool: ${name}`);
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
//# sourceMappingURL=cancel.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cancel.js","sourceRoot":"","sources":["../../src/tools/cancel.ts"],"names":[],"mappings":";AAAA,gFAAgF;AAChF,2DAA2D;AAC3D,EAAE;AACF,6DAA6D;AAC7D,qDAAqD;AACrD,gFAAgF;;;AAmEhF,4CAgBC;AAhFD,sCAAmC;AAEtB,QAAA,WAAW,GAAW;IACjC;QACE,IAAI,EAAE,uBAAuB;QAC7B,WAAW,EACT,2FAA2F;YAC3F,oGAAoG;YACpG,yGAAyG;YACzG,0GAA0G;YAC1G,iGAAiG;QACnG,WAAW,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,QAAQ,EAAE,CAAC,cAAc,CAAC;YAC1B,UAAU,EAAE;gBACV,YAAY,EAAE;oBACZ,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,4HAA4H;iBAC1I;aACF;YACD,oBAAoB,EAAE,KAAK;SAC5B;KACF;IAED;QACE,IAAI,EAAE,4BAA4B;QAClC,WAAW,EACT,qGAAqG;YACrG,sFAAsF;YACtF,gHAAgH;YAChH,2FAA2F;QAC7F,WAAW,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,QAAQ,EAAE,CAAC,UAAU,CAAC;YACtB,UAAU,EAAE;gBACV,QAAQ,EAAE;oBACR,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,qDAAqD;iBACnE;gBACD,cAAc,EAAE;oBACd,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,wDAAwD;iBACtE;gBACD,MAAM,EAAE;oBACN,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,2BAA2B;iBACzC;gBACD,MAAM,EAAE;oBACN,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,qEAAqE;oBAClF,OAAO,EAAE,8BAA8B;iBACxC;gBACD,MAAM,EAAE;oBACN,IAAI,EAAE,QAAQ;oBACd,IAAI,EAAE,CAAC,OAAO,EAAE,QAAQ,CAAC;oBACzB,OAAO,EAAE,OAAO;oBAChB,WAAW,EAAE,gFAAgF;iBAC9F;aACF;YACD,oBAAoB,EAAE,KAAK;SAC5B;KACF;CACF,CAAC;AAEK,KAAK,UAAU,gBAAgB,CACpC,IAAY,EACZ,IAA6B;IAE7B,QAAQ,IAAI,EAAE,CAAC;QACb,KAAK,uBAAuB,CAAC,CAAC,CAAC;YAC7B,MAAM,EAAE,YAAY,EAAE,GAAG,IAAI,CAAC;YAC9B,OAAO,eAAM,CAAC,GAAG,CAAC,cAAc,kBAAkB,CAAC,MAAM,CAAC,YAAY,CAAC,CAAC,EAAE,CAAC,CAAC;QAC9E,CAAC;QAED,KAAK,4BAA4B;YAC/B,OAAO,eAAM,CAAC,IAAI,CAAC,kBAAkB,EAAE,IAAI,CAAC,CAAC;QAE/C;YACE,MAAM,IAAI,KAAK,CAAC,wBAAwB,IAAI,EAAE,CAAC,CAAC;IACpD,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// ─────────────────────────────────────────────────────────────────────────────
|
|
3
|
+
// SubRadar MCP Tools — Detection (1 tool)
|
|
4
|
+
//
|
|
5
|
+
// detect_subscriptions POST /v1/detect
|
|
6
|
+
// ─────────────────────────────────────────────────────────────────────────────
|
|
7
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
8
|
+
exports.detectTools = void 0;
|
|
9
|
+
exports.handleDetectTool = handleDetectTool;
|
|
10
|
+
const client_1 = require("../client");
|
|
11
|
+
const transactionSchema = {
|
|
12
|
+
type: 'object',
|
|
13
|
+
required: ['id', 'date', 'amount', 'merchant', 'description'],
|
|
14
|
+
properties: {
|
|
15
|
+
id: { type: 'string', description: 'Unique transaction ID' },
|
|
16
|
+
date: { type: 'string', description: 'Transaction date (YYYY-MM-DD or ISO 8601)' },
|
|
17
|
+
amount: { type: 'number', minimum: 0, description: 'Transaction amount in USD' },
|
|
18
|
+
merchant: { type: 'string', description: 'Merchant name as it appears on the statement' },
|
|
19
|
+
description: { type: 'string', description: 'Full transaction description string' },
|
|
20
|
+
},
|
|
21
|
+
additionalProperties: false,
|
|
22
|
+
};
|
|
23
|
+
exports.detectTools = [
|
|
24
|
+
{
|
|
25
|
+
name: 'detect_subscriptions',
|
|
26
|
+
description: 'Use this tool to analyze a user\'s bank transactions and identify recurring subscription charges. ' +
|
|
27
|
+
'It uses four detection strategies: (1) recurring amounts from the same merchant on monthly or weekly intervals, ' +
|
|
28
|
+
'(2) matching against 60+ known subscription merchant names (Netflix, Spotify, Adobe, etc.), ' +
|
|
29
|
+
'(3) common subscription price points ($9.99, $14.99, $29.99, etc.), ' +
|
|
30
|
+
'(4) annual recurring charges. ' +
|
|
31
|
+
'Returns each detected subscription with merchant name, amount, frequency, next charge date, and a confidence score (0–1). ' +
|
|
32
|
+
'Set saveResults=true to automatically save detected subscriptions to the user\'s tracking list.',
|
|
33
|
+
inputSchema: {
|
|
34
|
+
type: 'object',
|
|
35
|
+
required: ['userId', 'transactions'],
|
|
36
|
+
properties: {
|
|
37
|
+
userId: {
|
|
38
|
+
type: 'string',
|
|
39
|
+
description: 'User identifier to associate detected subscriptions with.',
|
|
40
|
+
},
|
|
41
|
+
transactions: {
|
|
42
|
+
type: 'array',
|
|
43
|
+
items: transactionSchema,
|
|
44
|
+
minItems: 1,
|
|
45
|
+
maxItems: 1000,
|
|
46
|
+
description: 'Array of bank transactions to analyze for subscription patterns.',
|
|
47
|
+
},
|
|
48
|
+
saveResults: {
|
|
49
|
+
type: 'boolean',
|
|
50
|
+
default: false,
|
|
51
|
+
description: 'If true, persist detected subscriptions to the user\'s tracking list.',
|
|
52
|
+
},
|
|
53
|
+
},
|
|
54
|
+
additionalProperties: false,
|
|
55
|
+
},
|
|
56
|
+
},
|
|
57
|
+
];
|
|
58
|
+
async function handleDetectTool(name, args) {
|
|
59
|
+
switch (name) {
|
|
60
|
+
case 'detect_subscriptions':
|
|
61
|
+
return client_1.client.post('/v1/detect', args);
|
|
62
|
+
default:
|
|
63
|
+
throw new Error(`Unknown detect tool: ${name}`);
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
//# sourceMappingURL=detect.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"detect.js","sourceRoot":"","sources":["../../src/tools/detect.ts"],"names":[],"mappings":";AAAA,gFAAgF;AAChF,0CAA0C;AAC1C,EAAE;AACF,2CAA2C;AAC3C,gFAAgF;;;AAuDhF,4CAWC;AA/DD,sCAAmC;AAEnC,MAAM,iBAAiB,GAAG;IACxB,IAAI,EAAE,QAAQ;IACd,QAAQ,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,aAAa,CAAC;IAC7D,UAAU,EAAE;QACV,EAAE,EAAW,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,uBAAuB,EAAE;QACrE,IAAI,EAAS,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,2CAA2C,EAAE;QACzF,MAAM,EAAO,EAAE,IAAI,EAAE,QAAQ,EAAE,OAAO,EAAE,CAAC,EAAE,WAAW,EAAE,2BAA2B,EAAE;QACrF,QAAQ,EAAK,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,8CAA8C,EAAE;QAC5F,WAAW,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,qCAAqC,EAAE;KACpF;IACD,oBAAoB,EAAE,KAAK;CAC5B,CAAC;AAEW,QAAA,WAAW,GAAW;IACjC;QACE,IAAI,EAAE,sBAAsB;QAC5B,WAAW,EACT,oGAAoG;YACpG,kHAAkH;YAClH,8FAA8F;YAC9F,sEAAsE;YACtE,gCAAgC;YAChC,4HAA4H;YAC5H,iGAAiG;QACnG,WAAW,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,QAAQ,EAAE,CAAC,QAAQ,EAAE,cAAc,CAAC;YACpC,UAAU,EAAE;gBACV,MAAM,EAAE;oBACN,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,2DAA2D;iBACzE;gBACD,YAAY,EAAE;oBACZ,IAAI,EAAE,OAAO;oBACb,KAAK,EAAE,iBAAiB;oBACxB,QAAQ,EAAE,CAAC;oBACX,QAAQ,EAAE,IAAI;oBACd,WAAW,EAAE,kEAAkE;iBAChF;gBACD,WAAW,EAAE;oBACX,IAAI,EAAE,SAAS;oBACf,OAAO,EAAE,KAAK;oBACd,WAAW,EAAE,uEAAuE;iBACrF;aACF;YACD,oBAAoB,EAAE,KAAK;SAC5B;KACF;CACF,CAAC;AAEK,KAAK,UAAU,gBAAgB,CACpC,IAAY,EACZ,IAA6B;IAE7B,QAAQ,IAAI,EAAE,CAAC;QACb,KAAK,sBAAsB;YACzB,OAAO,eAAM,CAAC,IAAI,CAAC,YAAY,EAAE,IAAI,CAAC,CAAC;QAEzC;YACE,MAAM,IAAI,KAAK,CAAC,wBAAwB,IAAI,EAAE,CAAC,CAAC;IACpD,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1,110 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// ─────────────────────────────────────────────────────────────────────────────
|
|
3
|
+
// SubRadar MCP Tools — Subscription management (4 tools)
|
|
4
|
+
//
|
|
5
|
+
// list_subscriptions GET /v1/subscriptions/:userId
|
|
6
|
+
// add_subscription POST /v1/subscriptions/:userId
|
|
7
|
+
// remove_subscription DELETE /v1/subscriptions/:userId/:subscriptionId
|
|
8
|
+
// update_subscription PATCH /v1/subscriptions/:userId/:subscriptionId
|
|
9
|
+
// ─────────────────────────────────────────────────────────────────────────────
|
|
10
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
11
|
+
exports.subscriptionTools = void 0;
|
|
12
|
+
exports.handleSubscriptionTool = handleSubscriptionTool;
|
|
13
|
+
const client_1 = require("../client");
|
|
14
|
+
exports.subscriptionTools = [
|
|
15
|
+
{
|
|
16
|
+
name: 'list_subscriptions',
|
|
17
|
+
description: 'Use this tool to retrieve all tracked subscriptions for a user. ' +
|
|
18
|
+
'Returns merchant name, amount, frequency, next charge date, status, confidence score, and cancellation metadata. ' +
|
|
19
|
+
'Use this before checking analytics or before cancelling to get subscription IDs.',
|
|
20
|
+
inputSchema: {
|
|
21
|
+
type: 'object',
|
|
22
|
+
required: ['userId'],
|
|
23
|
+
properties: {
|
|
24
|
+
userId: {
|
|
25
|
+
type: 'string',
|
|
26
|
+
description: 'User identifier whose subscriptions to list.',
|
|
27
|
+
},
|
|
28
|
+
},
|
|
29
|
+
additionalProperties: false,
|
|
30
|
+
},
|
|
31
|
+
},
|
|
32
|
+
{
|
|
33
|
+
name: 'add_subscription',
|
|
34
|
+
description: 'Use this tool to manually add a known subscription to a user\'s tracking list. ' +
|
|
35
|
+
'Useful when the user knows about a subscription that was not caught by detect_subscriptions ' +
|
|
36
|
+
'(e.g. an annual subscription with only one transaction in history). ' +
|
|
37
|
+
'Cancellation metadata (URL, difficulty) is automatically looked up if the merchant is in the knowledge base.',
|
|
38
|
+
inputSchema: {
|
|
39
|
+
type: 'object',
|
|
40
|
+
required: ['userId', 'merchant', 'amount', 'frequency', 'nextChargeDate'],
|
|
41
|
+
properties: {
|
|
42
|
+
userId: { type: 'string', description: 'User identifier.' },
|
|
43
|
+
merchant: { type: 'string', description: 'Merchant / service name (e.g. "Netflix").' },
|
|
44
|
+
amount: { type: 'number', minimum: 0, description: 'Subscription amount in USD.' },
|
|
45
|
+
frequency: { type: 'string', enum: ['weekly', 'monthly', 'annual'], description: 'Billing frequency.' },
|
|
46
|
+
nextChargeDate: { type: 'string', description: 'Expected next charge date (YYYY-MM-DD).' },
|
|
47
|
+
status: { type: 'string', enum: ['active', 'cancelled', 'paused', 'unknown'], description: 'Current status (defaults to "active").' },
|
|
48
|
+
cancelUrl: { type: 'string', description: 'Optional direct cancellation URL.' },
|
|
49
|
+
},
|
|
50
|
+
additionalProperties: false,
|
|
51
|
+
},
|
|
52
|
+
},
|
|
53
|
+
{
|
|
54
|
+
name: 'remove_subscription',
|
|
55
|
+
description: 'Use this tool to permanently remove a subscription from a user\'s tracking list. ' +
|
|
56
|
+
'This does NOT cancel the subscription with the merchant — use get_cancellation_info or draft_cancellation_message for that. ' +
|
|
57
|
+
'Use list_subscriptions first to obtain the subscriptionId.',
|
|
58
|
+
inputSchema: {
|
|
59
|
+
type: 'object',
|
|
60
|
+
required: ['userId', 'subscriptionId'],
|
|
61
|
+
properties: {
|
|
62
|
+
userId: { type: 'string', description: 'User identifier.' },
|
|
63
|
+
subscriptionId: { type: 'string', description: 'UUID of the subscription to remove.' },
|
|
64
|
+
},
|
|
65
|
+
additionalProperties: false,
|
|
66
|
+
},
|
|
67
|
+
},
|
|
68
|
+
{
|
|
69
|
+
name: 'update_subscription',
|
|
70
|
+
description: 'Use this tool to update the status or details of a tracked subscription. ' +
|
|
71
|
+
'Most commonly used to mark a subscription as "cancelled" or "paused" after the user has completed cancellation. ' +
|
|
72
|
+
'Updatable fields: status, amount, nextChargeDate, cancelUrl.',
|
|
73
|
+
inputSchema: {
|
|
74
|
+
type: 'object',
|
|
75
|
+
required: ['userId', 'subscriptionId'],
|
|
76
|
+
properties: {
|
|
77
|
+
userId: { type: 'string', description: 'User identifier.' },
|
|
78
|
+
subscriptionId: { type: 'string', description: 'UUID of the subscription to update.' },
|
|
79
|
+
status: { type: 'string', enum: ['active', 'cancelled', 'paused', 'unknown'], description: 'New status.' },
|
|
80
|
+
amount: { type: 'number', description: 'Updated billing amount.' },
|
|
81
|
+
nextChargeDate: { type: 'string', description: 'Updated next charge date (YYYY-MM-DD).' },
|
|
82
|
+
cancelUrl: { type: 'string', description: 'Updated cancellation URL.' },
|
|
83
|
+
},
|
|
84
|
+
additionalProperties: false,
|
|
85
|
+
},
|
|
86
|
+
},
|
|
87
|
+
];
|
|
88
|
+
async function handleSubscriptionTool(name, args) {
|
|
89
|
+
switch (name) {
|
|
90
|
+
case 'list_subscriptions': {
|
|
91
|
+
const { userId } = args;
|
|
92
|
+
return client_1.client.get(`/v1/subscriptions/${userId}`);
|
|
93
|
+
}
|
|
94
|
+
case 'add_subscription': {
|
|
95
|
+
const { userId, ...body } = args;
|
|
96
|
+
return client_1.client.post(`/v1/subscriptions/${userId}`, body);
|
|
97
|
+
}
|
|
98
|
+
case 'remove_subscription': {
|
|
99
|
+
const { userId, subscriptionId } = args;
|
|
100
|
+
return client_1.client.delete(`/v1/subscriptions/${userId}/${subscriptionId}`);
|
|
101
|
+
}
|
|
102
|
+
case 'update_subscription': {
|
|
103
|
+
const { userId, subscriptionId, ...body } = args;
|
|
104
|
+
return client_1.client.patch(`/v1/subscriptions/${userId}/${subscriptionId}`, body);
|
|
105
|
+
}
|
|
106
|
+
default:
|
|
107
|
+
throw new Error(`Unknown subscription tool: ${name}`);
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
//# sourceMappingURL=subscriptions.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"subscriptions.js","sourceRoot":"","sources":["../../src/tools/subscriptions.ts"],"names":[],"mappings":"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"}
|
package/package.json
ADDED
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "mcp-subradar",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"description": "MCP server for SubRadar — subscription detection and cancellation for AI agents",
|
|
5
|
+
"license": "MIT",
|
|
6
|
+
"main": "dist/index.js",
|
|
7
|
+
"bin": {
|
|
8
|
+
"mcp-subradar": "dist/index.js"
|
|
9
|
+
},
|
|
10
|
+
"files": [
|
|
11
|
+
"dist",
|
|
12
|
+
"README.md"
|
|
13
|
+
],
|
|
14
|
+
"publishConfig": {
|
|
15
|
+
"access": "public"
|
|
16
|
+
},
|
|
17
|
+
"engines": {
|
|
18
|
+
"node": ">=18"
|
|
19
|
+
},
|
|
20
|
+
"keywords": [
|
|
21
|
+
"mcp",
|
|
22
|
+
"model-context-protocol",
|
|
23
|
+
"subradar",
|
|
24
|
+
"subscriptions",
|
|
25
|
+
"cancellation",
|
|
26
|
+
"personal-finance",
|
|
27
|
+
"ai-agent",
|
|
28
|
+
"cosmic-api"
|
|
29
|
+
],
|
|
30
|
+
"scripts": {
|
|
31
|
+
"prepare": "npm run build",
|
|
32
|
+
"dev": "ts-node-dev --respawn --transpile-only --exit-child src/index.ts",
|
|
33
|
+
"build": "tsc",
|
|
34
|
+
"start": "node dist/index.js",
|
|
35
|
+
"typecheck": "tsc --noEmit"
|
|
36
|
+
},
|
|
37
|
+
"dependencies": {
|
|
38
|
+
"@modelcontextprotocol/sdk": "^1.0.0",
|
|
39
|
+
"dotenv": "^16.3.1"
|
|
40
|
+
},
|
|
41
|
+
"devDependencies": {
|
|
42
|
+
"@types/node": "^20.10.0",
|
|
43
|
+
"ts-node-dev": "^2.0.0",
|
|
44
|
+
"typescript": "^5.3.2"
|
|
45
|
+
}
|
|
46
|
+
}
|