@scrapi.ai/mcp-server 2.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.
Files changed (39) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +715 -0
  3. package/dist/http.d.ts +3 -0
  4. package/dist/http.d.ts.map +1 -0
  5. package/dist/http.js +89 -0
  6. package/dist/http.js.map +1 -0
  7. package/dist/index.d.ts +3 -0
  8. package/dist/index.d.ts.map +1 -0
  9. package/dist/index.js +14 -0
  10. package/dist/index.js.map +1 -0
  11. package/dist/server.d.ts +3 -0
  12. package/dist/server.d.ts.map +1 -0
  13. package/dist/server.js +19 -0
  14. package/dist/server.js.map +1 -0
  15. package/dist/tools/get-billing.d.ts +3 -0
  16. package/dist/tools/get-billing.d.ts.map +1 -0
  17. package/dist/tools/get-billing.js +179 -0
  18. package/dist/tools/get-billing.js.map +1 -0
  19. package/dist/tools/get-usage.d.ts +3 -0
  20. package/dist/tools/get-usage.d.ts.map +1 -0
  21. package/dist/tools/get-usage.js +96 -0
  22. package/dist/tools/get-usage.js.map +1 -0
  23. package/dist/tools/scrape-url.d.ts +3 -0
  24. package/dist/tools/scrape-url.d.ts.map +1 -0
  25. package/dist/tools/scrape-url.js +77 -0
  26. package/dist/tools/scrape-url.js.map +1 -0
  27. package/dist/tools/scrape-urls.d.ts +3 -0
  28. package/dist/tools/scrape-urls.d.ts.map +1 -0
  29. package/dist/tools/scrape-urls.js +96 -0
  30. package/dist/tools/scrape-urls.js.map +1 -0
  31. package/dist/tools/scraper-server-status.d.ts +3 -0
  32. package/dist/tools/scraper-server-status.d.ts.map +1 -0
  33. package/dist/tools/scraper-server-status.js +87 -0
  34. package/dist/tools/scraper-server-status.js.map +1 -0
  35. package/dist/utils/api.d.ts +150 -0
  36. package/dist/utils/api.d.ts.map +1 -0
  37. package/dist/utils/api.js +142 -0
  38. package/dist/utils/api.js.map +1 -0
  39. package/package.json +63 -0
package/dist/http.js ADDED
@@ -0,0 +1,89 @@
1
+ #!/usr/bin/env node
2
+ import { StreamableHTTPServerTransport } from "@modelcontextprotocol/sdk/server/streamableHttp.js";
3
+ import { createMcpExpressApp } from "@modelcontextprotocol/sdk/server/express.js";
4
+ import { createMcpServer } from "./server.js";
5
+ const PORT = parseInt(process.env.PORT || "3000", 10);
6
+ const HOST = process.env.HOST || "127.0.0.1";
7
+ const app = createMcpExpressApp({ host: HOST });
8
+ // ── Stats ──────────────────────────────────────
9
+ const stats = {
10
+ startedAt: new Date(),
11
+ requests: 0,
12
+ errors: 0,
13
+ lastRequestAt: null,
14
+ };
15
+ // ── Request logging middleware ──────────────────
16
+ app.use("/api", (req, _res, next) => {
17
+ if (req.method === "POST") {
18
+ stats.requests++;
19
+ stats.lastRequestAt = new Date();
20
+ const ip = req.headers["x-forwarded-for"] || req.socket.remoteAddress;
21
+ const body = req.body;
22
+ const method = body?.method || "unknown";
23
+ console.error(`[${new Date().toISOString()}] MCP ${method} from ${ip} (total: ${stats.requests})`);
24
+ }
25
+ next();
26
+ });
27
+ // ── Health check ───────────────────────────────
28
+ app.get("/health", (_req, res) => {
29
+ const uptimeMs = Date.now() - stats.startedAt.getTime();
30
+ const uptimeHours = Math.floor(uptimeMs / 3600000);
31
+ const uptimeMinutes = Math.floor((uptimeMs % 3600000) / 60000);
32
+ res.json({
33
+ status: "ok",
34
+ uptime: `${uptimeHours}h ${uptimeMinutes}m`,
35
+ requests: stats.requests,
36
+ errors: stats.errors,
37
+ lastRequestAt: stats.lastRequestAt?.toISOString() || null,
38
+ });
39
+ });
40
+ // ── MCP Streamable HTTP endpoint ───────────────
41
+ app.post("/api", async (req, res) => {
42
+ const server = createMcpServer();
43
+ const transport = new StreamableHTTPServerTransport({
44
+ sessionIdGenerator: undefined,
45
+ });
46
+ try {
47
+ await server.connect(transport);
48
+ await transport.handleRequest(req, res, req.body);
49
+ res.on("close", () => {
50
+ transport.close();
51
+ server.close();
52
+ });
53
+ }
54
+ catch (error) {
55
+ stats.errors++;
56
+ console.error(`[${new Date().toISOString()}] MCP error:`, error);
57
+ if (!res.headersSent) {
58
+ res.status(500).json({
59
+ jsonrpc: "2.0",
60
+ error: { code: -32603, message: "Internal server error" },
61
+ id: null,
62
+ });
63
+ }
64
+ }
65
+ });
66
+ // GET and DELETE are not supported in stateless mode
67
+ app.get("/api", (_req, res) => {
68
+ res.status(405).json({
69
+ jsonrpc: "2.0",
70
+ error: { code: -32000, message: "Method not allowed. Use POST." },
71
+ id: null,
72
+ });
73
+ });
74
+ app.delete("/api", (_req, res) => {
75
+ res.status(405).json({
76
+ jsonrpc: "2.0",
77
+ error: { code: -32000, message: "Method not allowed." },
78
+ id: null,
79
+ });
80
+ });
81
+ // ── Start server ───────────────────────────────
82
+ app.listen(PORT, HOST, () => {
83
+ console.error(`Scrapi MCP server running on http://${HOST}:${PORT}/api`);
84
+ });
85
+ process.on("SIGINT", () => {
86
+ console.error("Shutting down...");
87
+ process.exit(0);
88
+ });
89
+ //# sourceMappingURL=http.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"http.js","sourceRoot":"","sources":["../src/http.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ export {};
3
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":""}
package/dist/index.js ADDED
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env node
2
+ import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
3
+ import { createMcpServer } from "./server.js";
4
+ async function main() {
5
+ const server = createMcpServer();
6
+ const transport = new StdioServerTransport();
7
+ await server.connect(transport);
8
+ console.error("Scrapi MCP server running on stdio");
9
+ }
10
+ main().catch((error) => {
11
+ console.error("Failed to start MCP server:", error);
12
+ process.exit(1);
13
+ });
14
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AAEA,OAAO,EAAE,oBAAoB,EAAE,MAAM,2CAA2C,CAAC;AACjF,OAAO,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AAE9C,KAAK,UAAU,IAAI;IACjB,MAAM,MAAM,GAAG,eAAe,EAAE,CAAC;IACjC,MAAM,SAAS,GAAG,IAAI,oBAAoB,EAAE,CAAC;IAC7C,MAAM,MAAM,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC;IAChC,OAAO,CAAC,KAAK,CAAC,oCAAoC,CAAC,CAAC;AACtD,CAAC;AAED,IAAI,EAAE,CAAC,KAAK,CAAC,CAAC,KAAK,EAAE,EAAE;IACrB,OAAO,CAAC,KAAK,CAAC,6BAA6B,EAAE,KAAK,CAAC,CAAC;IACpD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC,CAAC,CAAC"}
@@ -0,0 +1,3 @@
1
+ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ export declare function createMcpServer(): McpServer;
3
+ //# sourceMappingURL=server.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"server.d.ts","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AAOpE,wBAAgB,eAAe,IAAI,SAAS,CAa3C"}
package/dist/server.js ADDED
@@ -0,0 +1,19 @@
1
+ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ import { registerScrapeUrlTool } from "./tools/scrape-url.js";
3
+ import { registerScrapeUrlsTool } from "./tools/scrape-urls.js";
4
+ import { registerGetUsageTool } from "./tools/get-usage.js";
5
+ import { registerScraperServerStatusTool } from "./tools/scraper-server-status.js";
6
+ import { registerGetBillingTool } from "./tools/get-billing.js";
7
+ export function createMcpServer() {
8
+ const server = new McpServer({
9
+ name: "scrapi",
10
+ version: "2.0.0",
11
+ });
12
+ registerScrapeUrlTool(server);
13
+ registerScrapeUrlsTool(server);
14
+ registerGetUsageTool(server);
15
+ registerScraperServerStatusTool(server);
16
+ registerGetBillingTool(server);
17
+ return server;
18
+ }
19
+ //# sourceMappingURL=server.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AACpE,OAAO,EAAE,qBAAqB,EAAE,MAAM,uBAAuB,CAAC;AAC9D,OAAO,EAAE,sBAAsB,EAAE,MAAM,wBAAwB,CAAC;AAChE,OAAO,EAAE,oBAAoB,EAAE,MAAM,sBAAsB,CAAC;AAC5D,OAAO,EAAE,+BAA+B,EAAE,MAAM,kCAAkC,CAAC;AACnF,OAAO,EAAE,sBAAsB,EAAE,MAAM,wBAAwB,CAAC;AAEhE,MAAM,UAAU,eAAe;IAC7B,MAAM,MAAM,GAAG,IAAI,SAAS,CAAC;QAC3B,IAAI,EAAE,QAAQ;QACd,OAAO,EAAE,OAAO;KACjB,CAAC,CAAC;IAEH,qBAAqB,CAAC,MAAM,CAAC,CAAC;IAC9B,sBAAsB,CAAC,MAAM,CAAC,CAAC;IAC/B,oBAAoB,CAAC,MAAM,CAAC,CAAC;IAC7B,+BAA+B,CAAC,MAAM,CAAC,CAAC;IACxC,sBAAsB,CAAC,MAAM,CAAC,CAAC;IAE/B,OAAO,MAAM,CAAC;AAChB,CAAC"}
@@ -0,0 +1,3 @@
1
+ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ export declare function registerGetBillingTool(server: McpServer): void;
3
+ //# sourceMappingURL=get-billing.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"get-billing.d.ts","sourceRoot":"","sources":["../../src/tools/get-billing.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AA2BpE,wBAAgB,sBAAsB,CAAC,MAAM,EAAE,SAAS,QA8CvD"}
@@ -0,0 +1,179 @@
1
+ import { z } from "zod";
2
+ import { getMcpSubscription, getMcpPlans, getMcpDailyUsage, getMcpSpendingLimits, isMcpMode, formatCreditWarning, } from "../utils/api.js";
3
+ const BillingSchema = z.object({
4
+ action: z
5
+ .enum(["subscription", "plans", "daily_usage", "spending_limits"])
6
+ .describe("What billing info to retrieve: subscription (current plan details), plans (available plans), daily_usage (credit usage history), spending_limits (daily spend limit status)"),
7
+ start_date: z
8
+ .string()
9
+ .optional()
10
+ .describe("Start date for daily_usage (YYYY-MM-DD). Default: 30 days ago"),
11
+ end_date: z
12
+ .string()
13
+ .optional()
14
+ .describe("End date for daily_usage (YYYY-MM-DD). Default: today"),
15
+ });
16
+ export function registerGetBillingTool(server) {
17
+ server.tool("get_billing", "Retrieve MCP billing information: subscription details, available plans, daily usage history, or spending limits. Requires MCP API key (hsmcp_ prefix).", BillingSchema.shape, async (params) => {
18
+ const { action, start_date, end_date } = BillingSchema.parse(params);
19
+ if (!isMcpMode()) {
20
+ return {
21
+ isError: true,
22
+ content: [
23
+ {
24
+ type: "text",
25
+ text: "Error: This tool requires an MCP API key (hsmcp_ prefix). Your current key is a Legacy key.",
26
+ },
27
+ ],
28
+ };
29
+ }
30
+ try {
31
+ switch (action) {
32
+ case "subscription":
33
+ return await handleSubscription();
34
+ case "plans":
35
+ return await handlePlans();
36
+ case "daily_usage":
37
+ return await handleDailyUsage(start_date, end_date);
38
+ case "spending_limits":
39
+ return await handleSpendingLimits();
40
+ }
41
+ }
42
+ catch (error) {
43
+ const message = error instanceof Error ? error.message : "Unknown error";
44
+ return {
45
+ isError: true,
46
+ content: [
47
+ {
48
+ type: "text",
49
+ text: `Error: ${message}`,
50
+ },
51
+ ],
52
+ };
53
+ }
54
+ });
55
+ }
56
+ async function handleSubscription() {
57
+ const response = await getMcpSubscription();
58
+ if (!response.success) {
59
+ return {
60
+ isError: true,
61
+ content: [
62
+ { type: "text", text: `Error: ${response.error}` },
63
+ ],
64
+ };
65
+ }
66
+ const s = response.data.subscription;
67
+ const lines = [
68
+ "## MCP Subscription",
69
+ "",
70
+ `| Item | Value |`,
71
+ `|------|-------|`,
72
+ `| Plan | ${s.plan} (${s.plan_name || "-"}) |`,
73
+ `| Status | ${s.status} |`,
74
+ `| Monthly Credits | ${s.monthly_credits.toLocaleString()} |`,
75
+ `| Price | $${(s.price_cents / 100).toFixed(2)}/mo |`,
76
+ `| Rate Limit | ${s.rate_limit_rpm} RPM |`,
77
+ `| Burst Limit | ${s.burst_limit} concurrent |`,
78
+ ];
79
+ if (s.current_period_end) {
80
+ lines.push(`| Period End | ${s.current_period_end.split("T")[0]} |`);
81
+ }
82
+ if (s.daily_spending_limit != null) {
83
+ lines.push(`| Daily Spending Limit | ${s.daily_spending_limit.toLocaleString()} credits |`);
84
+ }
85
+ const warning = formatCreditWarning();
86
+ return {
87
+ content: [
88
+ { type: "text", text: lines.join("\n") + (warning || "") },
89
+ ],
90
+ };
91
+ }
92
+ async function handlePlans() {
93
+ const response = await getMcpPlans();
94
+ if (!response.success) {
95
+ return {
96
+ isError: true,
97
+ content: [
98
+ { type: "text", text: `Error: ${response.error}` },
99
+ ],
100
+ };
101
+ }
102
+ const lines = [
103
+ "## Available MCP Plans",
104
+ "",
105
+ "| Plan | Credits/mo | Price | RPM | Burst |",
106
+ "|------|-----------|-------|-----|-------|",
107
+ ];
108
+ for (const p of response.data.plans) {
109
+ const price = p.price_cents === 0 ? "Free" : `$${(p.price_cents / 100).toFixed(2)}/mo`;
110
+ lines.push(`| ${p.name} (${p.slug}) | ${p.monthly_credits.toLocaleString()} | ${price} | ${p.rate_limit_rpm} | ${p.burst_limit} |`);
111
+ }
112
+ return {
113
+ content: [{ type: "text", text: lines.join("\n") }],
114
+ };
115
+ }
116
+ async function handleDailyUsage(startDate, endDate) {
117
+ const response = await getMcpDailyUsage(startDate, endDate);
118
+ if (!response.success) {
119
+ return {
120
+ isError: true,
121
+ content: [
122
+ { type: "text", text: `Error: ${response.error}` },
123
+ ],
124
+ };
125
+ }
126
+ const { daily_usage, period } = response.data;
127
+ const lines = [
128
+ `## Daily Usage (${period.start} ~ ${period.end})`,
129
+ "",
130
+ "| Date | Requests | Credits | Top Tool |",
131
+ "|------|----------|---------|----------|",
132
+ ];
133
+ for (const d of daily_usage) {
134
+ const topTool = Object.entries(d.tools || {}).sort(([, a], [, b]) => b - a)[0];
135
+ const toolStr = topTool ? `${topTool[0]} (${topTool[1]})` : "-";
136
+ lines.push(`| ${d.date} | ${d.requests.toLocaleString()} | ${d.credits.toLocaleString()} | ${toolStr} |`);
137
+ }
138
+ if (daily_usage.length === 0) {
139
+ lines.push("| (no usage data) | - | - | - |");
140
+ }
141
+ const totalCredits = daily_usage.reduce((sum, d) => sum + d.credits, 0);
142
+ const totalRequests = daily_usage.reduce((sum, d) => sum + d.requests, 0);
143
+ lines.push("");
144
+ lines.push(`**Total**: ${totalRequests.toLocaleString()} requests, ${totalCredits.toLocaleString()} credits`);
145
+ return {
146
+ content: [{ type: "text", text: lines.join("\n") }],
147
+ };
148
+ }
149
+ async function handleSpendingLimits() {
150
+ const response = await getMcpSpendingLimits();
151
+ if (!response.success) {
152
+ return {
153
+ isError: true,
154
+ content: [
155
+ { type: "text", text: `Error: ${response.error}` },
156
+ ],
157
+ };
158
+ }
159
+ const { daily_limit, current_usage } = response.data;
160
+ const pct = daily_limit && daily_limit > 0
161
+ ? ((current_usage / daily_limit) * 100).toFixed(1)
162
+ : "N/A";
163
+ const lines = [
164
+ "## Spending Limits",
165
+ "",
166
+ `| Item | Value |`,
167
+ `|------|-------|`,
168
+ `| Daily Limit | ${daily_limit != null ? daily_limit.toLocaleString() + " credits" : "Unlimited"} |`,
169
+ `| Today's Usage | ${current_usage.toLocaleString()} credits |`,
170
+ `| Usage % | ${pct}${pct !== "N/A" ? "%" : ""} |`,
171
+ ];
172
+ const warning = formatCreditWarning();
173
+ return {
174
+ content: [
175
+ { type: "text", text: lines.join("\n") + (warning || "") },
176
+ ],
177
+ };
178
+ }
179
+ //# sourceMappingURL=get-billing.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"get-billing.js","sourceRoot":"","sources":["../../src/tools/get-billing.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ export declare function registerGetUsageTool(server: McpServer): void;
3
+ //# sourceMappingURL=get-usage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"get-usage.d.ts","sourceRoot":"","sources":["../../src/tools/get-usage.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AAQpE,wBAAgB,oBAAoB,CAAC,MAAM,EAAE,SAAS,QAyBrD"}
@@ -0,0 +1,96 @@
1
+ import { getUsage, getMcpCredits, isMcpMode, formatCreditWarning, } from "../utils/api.js";
2
+ export function registerGetUsageTool(server) {
3
+ server.tool("get_usage", "Check API usage and remaining credits. Returns current plan, total credits, usage, remaining credits, and reset date. Supports both MCP and Legacy API keys.", {}, async () => {
4
+ try {
5
+ if (isMcpMode()) {
6
+ return await getMcpUsage();
7
+ }
8
+ return await getLegacyUsage();
9
+ }
10
+ catch (error) {
11
+ const message = error instanceof Error ? error.message : "Unknown error";
12
+ return {
13
+ isError: true,
14
+ content: [
15
+ {
16
+ type: "text",
17
+ text: `Error: ${message}`,
18
+ },
19
+ ],
20
+ };
21
+ }
22
+ });
23
+ }
24
+ async function getMcpUsage() {
25
+ const response = await getMcpCredits();
26
+ if (!response.success) {
27
+ return {
28
+ isError: true,
29
+ content: [
30
+ {
31
+ type: "text",
32
+ text: `Error: ${response.error || "Failed to retrieve MCP credit information."}`,
33
+ },
34
+ ],
35
+ };
36
+ }
37
+ const d = response.data;
38
+ const lines = [
39
+ "## MCP Credits",
40
+ "",
41
+ `| Item | Value |`,
42
+ `|------|-------|`,
43
+ `| Mode | MCP |`,
44
+ `| Plan | ${d.plan || "none"} |`,
45
+ `| Subscription Credits | ${(d.subscription_credits ?? 0).toLocaleString()} |`,
46
+ `| Purchased Credits | ${(d.purchased_credits ?? 0).toLocaleString()} |`,
47
+ `| Total Remaining | ${(d.total_remaining ?? 0).toLocaleString()} |`,
48
+ ];
49
+ if (d.current_period_end) {
50
+ lines.push(`| Period End | ${d.current_period_end.split("T")[0]} |`);
51
+ }
52
+ const warning = formatCreditWarning();
53
+ return {
54
+ content: [
55
+ {
56
+ type: "text",
57
+ text: lines.join("\n") + (warning || ""),
58
+ },
59
+ ],
60
+ };
61
+ }
62
+ async function getLegacyUsage() {
63
+ const response = await getUsage();
64
+ if (!response.success) {
65
+ return {
66
+ isError: true,
67
+ content: [
68
+ {
69
+ type: "text",
70
+ text: `Error: ${response.error || "Failed to retrieve usage information."}`,
71
+ },
72
+ ],
73
+ };
74
+ }
75
+ const { plan, credits_total, credits_used, credits_remaining, reset_date } = response.data;
76
+ const result = [
77
+ "## API Usage",
78
+ "",
79
+ `| Item | Value |`,
80
+ `|------|-------|`,
81
+ `| Plan | ${plan} |`,
82
+ `| Total Credits | ${credits_total.toLocaleString()} |`,
83
+ `| Used Credits | ${credits_used.toLocaleString()} |`,
84
+ `| Remaining Credits | ${credits_remaining.toLocaleString()} |`,
85
+ `| Reset Date | ${reset_date} |`,
86
+ ].join("\n");
87
+ return {
88
+ content: [
89
+ {
90
+ type: "text",
91
+ text: result,
92
+ },
93
+ ],
94
+ };
95
+ }
96
+ //# sourceMappingURL=get-usage.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"get-usage.js","sourceRoot":"","sources":["../../src/tools/get-usage.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ export declare function registerScrapeUrlTool(server: McpServer): void;
3
+ //# sourceMappingURL=scrape-url.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"scrape-url.d.ts","sourceRoot":"","sources":["../../src/tools/scrape-url.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AAYpE,wBAAgB,qBAAqB,CAAC,MAAM,EAAE,SAAS,QA0EtD"}
@@ -0,0 +1,77 @@
1
+ import { z } from "zod";
2
+ import { scrapeUrl, getApiUrl, formatCreditWarning } from "../utils/api.js";
3
+ const ScrapeUrlSchema = z.object({
4
+ url: z.string().url().describe("The URL of the webpage to scrape"),
5
+ format: z
6
+ .enum(["markdown", "text"])
7
+ .default("markdown")
8
+ .describe("Output format: markdown (default) or text"),
9
+ });
10
+ export function registerScrapeUrlTool(server) {
11
+ server.tool("scrape_url", "Scrapes a webpage and returns the content in AI-readable Markdown format. Can access blocked sites through browser rendering.", ScrapeUrlSchema.shape, async (params) => {
12
+ const { url, format } = ScrapeUrlSchema.parse(params);
13
+ try {
14
+ // 1. Request browser rendering via Scrapi API
15
+ const response = await scrapeUrl({
16
+ url,
17
+ format,
18
+ javascript: true,
19
+ });
20
+ if (!response.success) {
21
+ return {
22
+ isError: true,
23
+ content: [
24
+ {
25
+ type: "text",
26
+ text: `Error: ${response.error || "Failed to scrape the page."}`,
27
+ },
28
+ ],
29
+ };
30
+ }
31
+ // 2. Return to AI
32
+ const result = [
33
+ `# ${response.data.title || "Untitled"}`,
34
+ "",
35
+ `> Source: ${response.data.url}`,
36
+ "",
37
+ response.data.content,
38
+ ].join("\n");
39
+ const warning = formatCreditWarning();
40
+ return {
41
+ content: [
42
+ {
43
+ type: "text",
44
+ text: result + (warning || ""),
45
+ },
46
+ ],
47
+ };
48
+ }
49
+ catch (error) {
50
+ let message = "Unknown error";
51
+ const apiUrl = getApiUrl();
52
+ if (error instanceof Error) {
53
+ message = error.message;
54
+ // axios 에러인 경우 더 자세한 정보 추출
55
+ const axiosError = error;
56
+ if (axiosError.response) {
57
+ // 서버가 응답했지만 에러 상태
58
+ message = `HTTP ${axiosError.response.status}: ${JSON.stringify(axiosError.response.data)}`;
59
+ }
60
+ else if (axiosError.request) {
61
+ // 요청은 보냈지만 응답 없음
62
+ message = `No response received: ${axiosError.code || 'Unknown'} (API URL: ${apiUrl})`;
63
+ }
64
+ }
65
+ return {
66
+ isError: true,
67
+ content: [
68
+ {
69
+ type: "text",
70
+ text: `Error: ${message}`,
71
+ },
72
+ ],
73
+ };
74
+ }
75
+ });
76
+ }
77
+ //# sourceMappingURL=scrape-url.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"scrape-url.js","sourceRoot":"","sources":["../../src/tools/scrape-url.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AACxB,OAAO,EAAE,SAAS,EAAE,SAAS,EAAE,mBAAmB,EAAE,MAAM,iBAAiB,CAAC;AAE5E,MAAM,eAAe,GAAG,CAAC,CAAC,MAAM,CAAC;IAC/B,GAAG,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,GAAG,EAAE,CAAC,QAAQ,CAAC,kCAAkC,CAAC;IAClE,MAAM,EAAE,CAAC;SACN,IAAI,CAAC,CAAC,UAAU,EAAE,MAAM,CAAC,CAAC;SAC1B,OAAO,CAAC,UAAU,CAAC;SACnB,QAAQ,CAAC,2CAA2C,CAAC;CACzD,CAAC,CAAC;AAEH,MAAM,UAAU,qBAAqB,CAAC,MAAiB;IACrD,MAAM,CAAC,IAAI,CACT,YAAY,EACZ,+HAA+H,EAC/H,eAAe,CAAC,KAAK,EACrB,KAAK,EAAE,MAAM,EAAE,EAAE;QACf,MAAM,EAAE,GAAG,EAAE,MAAM,EAAE,GAAG,eAAe,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC;QAEtD,IAAI,CAAC;YACH,8CAA8C;YAC9C,MAAM,QAAQ,GAAG,MAAM,SAAS,CAAC;gBAC/B,GAAG;gBACH,MAAM;gBACN,UAAU,EAAE,IAAI;aACjB,CAAC,CAAC;YAEH,IAAI,CAAC,QAAQ,CAAC,OAAO,EAAE,CAAC;gBACtB,OAAO;oBACL,OAAO,EAAE,IAAI;oBACb,OAAO,EAAE;wBACP;4BACE,IAAI,EAAE,MAAe;4BACrB,IAAI,EAAE,UAAU,QAAQ,CAAC,KAAK,IAAI,4BAA4B,EAAE;yBACjE;qBACF;iBACF,CAAC;YACJ,CAAC;YAED,kBAAkB;YAClB,MAAM,MAAM,GAAG;gBACb,KAAK,QAAQ,CAAC,IAAI,CAAC,KAAK,IAAI,UAAU,EAAE;gBACxC,EAAE;gBACF,aAAa,QAAQ,CAAC,IAAI,CAAC,GAAG,EAAE;gBAChC,EAAE;gBACF,QAAQ,CAAC,IAAI,CAAC,OAAO;aACtB,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YAEb,MAAM,OAAO,GAAG,mBAAmB,EAAE,CAAC;YAEtC,OAAO;gBACL,OAAO,EAAE;oBACP;wBACE,IAAI,EAAE,MAAe;wBACrB,IAAI,EAAE,MAAM,GAAG,CAAC,OAAO,IAAI,EAAE,CAAC;qBAC/B;iBACF;aACF,CAAC;QACJ,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,IAAI,OAAO,GAAG,eAAe,CAAC;YAC9B,MAAM,MAAM,GAAG,SAAS,EAAE,CAAC;YAC3B,IAAI,KAAK,YAAY,KAAK,EAAE,CAAC;gBAC3B,OAAO,GAAG,KAAK,CAAC,OAAO,CAAC;gBACxB,2BAA2B;gBAC3B,MAAM,UAAU,GAAG,KAAY,CAAC;gBAChC,IAAI,UAAU,CAAC,QAAQ,EAAE,CAAC;oBACxB,kBAAkB;oBAClB,OAAO,GAAG,QAAQ,UAAU,CAAC,QAAQ,CAAC,MAAM,KAAK,IAAI,CAAC,SAAS,CAAC,UAAU,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE,CAAC;gBAC9F,CAAC;qBAAM,IAAI,UAAU,CAAC,OAAO,EAAE,CAAC;oBAC9B,iBAAiB;oBACjB,OAAO,GAAG,yBAAyB,UAAU,CAAC,IAAI,IAAI,SAAS,cAAc,MAAM,GAAG,CAAC;gBACzF,CAAC;YACH,CAAC;YACD,OAAO;gBACL,OAAO,EAAE,IAAI;gBACb,OAAO,EAAE;oBACP;wBACE,IAAI,EAAE,MAAe;wBACrB,IAAI,EAAE,UAAU,OAAO,EAAE;qBAC1B;iBACF;aACF,CAAC;QACJ,CAAC;IACH,CAAC,CACF,CAAC;AACJ,CAAC"}
@@ -0,0 +1,3 @@
1
+ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ export declare function registerScrapeUrlsTool(server: McpServer): void;
3
+ //# sourceMappingURL=scrape-urls.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"scrape-urls.d.ts","sourceRoot":"","sources":["../../src/tools/scrape-urls.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AAgBpE,wBAAgB,sBAAsB,CAAC,MAAM,EAAE,SAAS,QA2FvD"}