@forgemeshlabs/seo-authority-mcp 0.1.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 +7 -0
- package/GLAMA.md +44 -0
- package/LICENSE +9 -0
- package/README.md +93 -0
- package/SECURITY.md +13 -0
- package/dist/client.d.ts +9 -0
- package/dist/client.js +101 -0
- package/dist/client.js.map +1 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.js +20 -0
- package/dist/index.js.map +1 -0
- package/dist/tools.d.ts +3 -0
- package/dist/tools.js +55 -0
- package/dist/tools.js.map +1 -0
- package/examples/claude_desktop_config.json +11 -0
- package/glama.json +4 -0
- package/package.json +35 -0
- package/server.json +18 -0
- package/smithery.yaml +27 -0
- package/tool_manifest.json +465 -0
package/CHANGELOG.md
ADDED
package/GLAMA.md
ADDED
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
# SEO Authority MCP for Glama
|
|
2
|
+
|
|
3
|
+
Canonical MCP server: `seo-authority-mcp`
|
|
4
|
+
|
|
5
|
+
Use this repository's Dockerfile in the Glama Dockerfile admin page:
|
|
6
|
+
|
|
7
|
+
```text
|
|
8
|
+
https://glama.ai/mcp/servers/forgemeshlabs/seo-authority-mcp/admin/dockerfile
|
|
9
|
+
```
|
|
10
|
+
|
|
11
|
+
Build steps:
|
|
12
|
+
|
|
13
|
+
```json
|
|
14
|
+
["npm ci", "npm run build", "npm prune --omit=dev"]
|
|
15
|
+
```
|
|
16
|
+
|
|
17
|
+
Command arguments:
|
|
18
|
+
|
|
19
|
+
```json
|
|
20
|
+
["node", "dist/index.js"]
|
|
21
|
+
```
|
|
22
|
+
|
|
23
|
+
Environment schema:
|
|
24
|
+
|
|
25
|
+
```json
|
|
26
|
+
{
|
|
27
|
+
"type": "object",
|
|
28
|
+
"properties": {
|
|
29
|
+
"SEO_API_BASE": { "type": "string", "default": "https://seo.forgemesh.io" },
|
|
30
|
+
"SEO_X402_PRIVATE_KEY": { "type": "string", "description": "Optional secret EVM private key for automatic payment." },
|
|
31
|
+
"SEO_MAX_PAYMENT_USDC": { "type": "string", "default": "0.15" }
|
|
32
|
+
},
|
|
33
|
+
"required": []
|
|
34
|
+
}
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
Runtime notes:
|
|
38
|
+
|
|
39
|
+
- Transport: stdio; no inbound port.
|
|
40
|
+
- Node.js 22 or newer.
|
|
41
|
+
- Without a private key, paid tools return structured x402 challenge metadata and spend nothing.
|
|
42
|
+
- With a private key, the MCP settles exact USDC payments on Base and requires a non-empty transaction hash.
|
|
43
|
+
- The default backend allowlist contains only `seo.forgemesh.io`.
|
|
44
|
+
- `SEO_MAX_PAYMENT_USDC` limits each automatic settlement; default `0.15` covers every current tool.
|
package/LICENSE
ADDED
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 ForgeMesh
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
|
|
6
|
+
|
|
7
|
+
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
|
|
8
|
+
|
|
9
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
package/README.md
ADDED
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
# SEO Authority MCP
|
|
2
|
+
|
|
3
|
+
[](https://glama.ai/mcp/servers/forgemeshlabs/seo-authority-mcp)
|
|
4
|
+
|
|
5
|
+
Give AI agents typed SEO authority, keyword, competitor, content, audit, and internal-link tools backed by [seo.forgemesh.io](https://seo.forgemesh.io). Authority scores use open Common Crawl graph data. The server does not invent search volume, CPC, live SERP positions, complete backlinks, or Google metrics.
|
|
6
|
+
|
|
7
|
+
## Install
|
|
8
|
+
|
|
9
|
+
```bash
|
|
10
|
+
npx -y @forgemeshlabs/seo-authority-mcp
|
|
11
|
+
```
|
|
12
|
+
|
|
13
|
+
## Claude Desktop
|
|
14
|
+
|
|
15
|
+
Challenge-only mode—safe default, never spends:
|
|
16
|
+
|
|
17
|
+
```json
|
|
18
|
+
{
|
|
19
|
+
"mcpServers": {
|
|
20
|
+
"seo-authority": {
|
|
21
|
+
"command": "npx",
|
|
22
|
+
"args": ["-y", "@forgemeshlabs/seo-authority-mcp"]
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
Automatic x402 settlement:
|
|
29
|
+
|
|
30
|
+
```json
|
|
31
|
+
{
|
|
32
|
+
"mcpServers": {
|
|
33
|
+
"seo-authority": {
|
|
34
|
+
"command": "npx",
|
|
35
|
+
"args": ["-y", "@forgemeshlabs/seo-authority-mcp"],
|
|
36
|
+
"env": {
|
|
37
|
+
"SEO_X402_PRIVATE_KEY": "YOUR_DEDICATED_LOW_BALANCE_WALLET_KEY",
|
|
38
|
+
"SEO_MAX_PAYMENT_USDC": "0.15"
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
Use a dedicated low-balance wallet. Never commit its private key.
|
|
46
|
+
|
|
47
|
+
## Tools
|
|
48
|
+
|
|
49
|
+
| MCP tool | Purpose | Price |
|
|
50
|
+
|---|---|---:|
|
|
51
|
+
| `get_seo_capabilities` | Source and metric disclosures | Free |
|
|
52
|
+
| `get_domain_authority` | Common Crawl graph authority | $0.01 |
|
|
53
|
+
| `compare_domain_authority` | Compare 2–20 domains | $0.02 |
|
|
54
|
+
| `score_page_seo` | Deterministic on-page checks | $0.01 |
|
|
55
|
+
| `correct_seo_query` | Did-you-mean correction | $0.005 |
|
|
56
|
+
| `expand_seo_query` | Long-tail query variants | $0.01 |
|
|
57
|
+
| `find_keyword_opportunities` | Prioritized keyword ideas | $0.05 |
|
|
58
|
+
| `find_competitor_content_gaps` | Supplied-content gap analysis | $0.10 |
|
|
59
|
+
| `create_seo_content_brief` | Evidence-tagged brief | $0.10 |
|
|
60
|
+
| `audit_site_seo` | Multi-page SEO audit | $0.15 |
|
|
61
|
+
| `find_internal_link_opportunities` | Contextual internal links | $0.05 |
|
|
62
|
+
|
|
63
|
+
Paid tools use exact USDC settlement on Base. Without `SEO_X402_PRIVATE_KEY`, each tool returns price, network, receiver, and retry guidance instead of spending.
|
|
64
|
+
|
|
65
|
+
## Docker
|
|
66
|
+
|
|
67
|
+
```bash
|
|
68
|
+
docker build -t seo-authority-mcp:0.1.0 .
|
|
69
|
+
docker run --rm -i --read-only --cap-drop=ALL seo-authority-mcp:0.1.0
|
|
70
|
+
```
|
|
71
|
+
|
|
72
|
+
For automatic payment, pass the private key at runtime using your secret manager. Do not bake it into the image.
|
|
73
|
+
|
|
74
|
+
## Environment
|
|
75
|
+
|
|
76
|
+
| Variable | Required | Default | Purpose |
|
|
77
|
+
|---|---|---|---|
|
|
78
|
+
| `SEO_X402_PRIVATE_KEY` | No | unset | Enables automatic payment |
|
|
79
|
+
| `SEO_MAX_PAYMENT_USDC` | No | `0.15` | Per-call payment ceiling |
|
|
80
|
+
| `SEO_API_BASE` | No | `https://seo.forgemesh.io` | Backend URL |
|
|
81
|
+
| `SEO_ALLOW_CUSTOM_API_BASE` | No | `false` | Explicitly allows a custom HTTPS backend |
|
|
82
|
+
| `SEO_REQUEST_TIMEOUT_MS` | No | `30000` | Upstream timeout, capped at 120 seconds |
|
|
83
|
+
|
|
84
|
+
## Links
|
|
85
|
+
|
|
86
|
+
- API: https://seo.forgemesh.io
|
|
87
|
+
- OpenAPI: https://seo.forgemesh.io/openapi.json
|
|
88
|
+
- x402 discovery: https://seo.forgemesh.io/.well-known/x402
|
|
89
|
+
- Contact: clawdbotworker@gmail.com
|
|
90
|
+
|
|
91
|
+
## License
|
|
92
|
+
|
|
93
|
+
MIT
|
package/SECURITY.md
ADDED
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
# Security Policy
|
|
2
|
+
|
|
3
|
+
## Supported versions
|
|
4
|
+
|
|
5
|
+
Security fixes are provided for the latest published release.
|
|
6
|
+
|
|
7
|
+
## Reporting
|
|
8
|
+
|
|
9
|
+
Report vulnerabilities privately to clawdbotworker@gmail.com. Do not include wallet private keys, payment signatures, or other credentials in reports.
|
|
10
|
+
|
|
11
|
+
## Wallet safety
|
|
12
|
+
|
|
13
|
+
Use a dedicated low-balance wallet. Keep `SEO_X402_PRIVATE_KEY` in the MCP client's secret environment configuration, never in source control. Automatic payments are capped per call by `SEO_MAX_PAYMENT_USDC`.
|
package/dist/client.d.ts
ADDED
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
type Args = Record<string, unknown>;
|
|
2
|
+
type RequestSpec = {
|
|
3
|
+
path: string;
|
|
4
|
+
method?: "GET" | "POST";
|
|
5
|
+
body?: Args;
|
|
6
|
+
};
|
|
7
|
+
export declare function requestForTool(name: string, args: Args): RequestSpec;
|
|
8
|
+
export declare function callSeoTool(name: string, args: Args): Promise<unknown>;
|
|
9
|
+
export {};
|
package/dist/client.js
ADDED
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
import { x402Client, x402HTTPClient } from "@x402/core/client";
|
|
2
|
+
import { ExactEvmScheme } from "@x402/evm/exact/client";
|
|
3
|
+
import { toClientEvmSigner } from "@x402/evm";
|
|
4
|
+
import { privateKeyToAccount } from "viem/accounts";
|
|
5
|
+
const configuredBase = (process.env.SEO_API_BASE || "https://seo.forgemesh.io").replace(/\/+$/, "");
|
|
6
|
+
const parsedBase = new URL(configuredBase);
|
|
7
|
+
if (parsedBase.protocol !== "https:")
|
|
8
|
+
throw new Error("SEO_API_BASE must use HTTPS");
|
|
9
|
+
if (parsedBase.hostname !== "seo.forgemesh.io" && process.env.SEO_ALLOW_CUSTOM_API_BASE !== "true") {
|
|
10
|
+
throw new Error("Custom SEO_API_BASE requires SEO_ALLOW_CUSTOM_API_BASE=true");
|
|
11
|
+
}
|
|
12
|
+
const API_BASE = parsedBase.toString().replace(/\/$/, "");
|
|
13
|
+
const timeoutMs = Math.max(1_000, Math.min(120_000, Number(process.env.SEO_REQUEST_TIMEOUT_MS || 30_000)));
|
|
14
|
+
const maxAtomic = BigInt(Math.round(Number(process.env.SEO_MAX_PAYMENT_USDC || "0.15") * 1_000_000));
|
|
15
|
+
function encodeQuery(path, params) {
|
|
16
|
+
const url = new URL(path, `${API_BASE}/`);
|
|
17
|
+
for (const [key, value] of Object.entries(params))
|
|
18
|
+
url.searchParams.set(key, value);
|
|
19
|
+
return `${url.pathname}${url.search}`;
|
|
20
|
+
}
|
|
21
|
+
export function requestForTool(name, args) {
|
|
22
|
+
switch (name) {
|
|
23
|
+
case "get_seo_capabilities": return { path: "/capabilities" };
|
|
24
|
+
case "get_domain_authority": return { path: encodeQuery("/v1/domain-authority", { domain: String(args.domain) }) };
|
|
25
|
+
case "compare_domain_authority": return { path: "/v1/authority-compare", method: "POST", body: { domains: args.domains } };
|
|
26
|
+
case "score_page_seo": return { path: "/v1/url-seo-score", method: "POST", body: { url: args.url, html: args.html } };
|
|
27
|
+
case "correct_seo_query": return { path: encodeQuery("/v1/query-correct", { q: String(args.query) }) };
|
|
28
|
+
case "expand_seo_query": return { path: encodeQuery("/v1/query-expand", { q: String(args.query) }) };
|
|
29
|
+
case "find_keyword_opportunities": return { path: "/v1/keyword-opportunity", method: "POST", body: args };
|
|
30
|
+
case "find_competitor_content_gaps": return { path: "/v1/competitor-gap", method: "POST", body: args };
|
|
31
|
+
case "create_seo_content_brief": return { path: "/v1/content-brief", method: "POST", body: args };
|
|
32
|
+
case "audit_site_seo": return { path: "/v1/site-audit", method: "POST", body: args };
|
|
33
|
+
case "find_internal_link_opportunities": return { path: "/v1/internal-link-opportunities", method: "POST", body: args };
|
|
34
|
+
default: throw new Error(`Unknown tool: ${name}`);
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
function parseChallenge(response, body) {
|
|
38
|
+
const raw = response.headers.get("payment-required");
|
|
39
|
+
if (!raw)
|
|
40
|
+
return null;
|
|
41
|
+
try {
|
|
42
|
+
return JSON.parse(Buffer.from(raw, "base64").toString("utf8"));
|
|
43
|
+
}
|
|
44
|
+
catch {
|
|
45
|
+
return body;
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
function safeChallenge(challenge) {
|
|
49
|
+
const accept = challenge?.accepts?.[0] || {};
|
|
50
|
+
const amount = String(accept.amount || "0");
|
|
51
|
+
return { payment_required: true, amount_usdc: /^\d+$/.test(amount) ? Number(amount) / 1_000_000 : null, network: accept.network || null, pay_to: accept.payTo || null, scheme: accept.scheme || null, resource: challenge?.resource?.url || null, next_step: "Set SEO_X402_PRIVATE_KEY to let this MCP settle automatically, or pay the challenge with another x402 client." };
|
|
52
|
+
}
|
|
53
|
+
function findTx(value) {
|
|
54
|
+
if (typeof value === "string" && /^0x[a-fA-F0-9]{64}$/.test(value))
|
|
55
|
+
return value;
|
|
56
|
+
if (!value || typeof value !== "object")
|
|
57
|
+
return null;
|
|
58
|
+
for (const item of Object.values(value)) {
|
|
59
|
+
const found = findTx(item);
|
|
60
|
+
if (found)
|
|
61
|
+
return found;
|
|
62
|
+
}
|
|
63
|
+
return null;
|
|
64
|
+
}
|
|
65
|
+
function init(spec, extraHeaders = {}) {
|
|
66
|
+
return { method: spec.method || "GET", headers: { accept: "application/json", ...extraHeaders, ...(spec.body ? { "content-type": "application/json" } : {}) }, ...(spec.body ? { body: JSON.stringify(spec.body) } : {}), signal: AbortSignal.timeout(timeoutMs) };
|
|
67
|
+
}
|
|
68
|
+
export async function callSeoTool(name, args) {
|
|
69
|
+
const spec = requestForTool(name, args);
|
|
70
|
+
const url = `${API_BASE}${spec.path}`;
|
|
71
|
+
const challengeResponse = await fetch(url, init(spec));
|
|
72
|
+
const challengeBody = await challengeResponse.clone().json().catch(() => null);
|
|
73
|
+
if (challengeResponse.status !== 402) {
|
|
74
|
+
if (!challengeResponse.ok)
|
|
75
|
+
throw new Error(`SEO API ${challengeResponse.status}: ${JSON.stringify(challengeBody).slice(0, 300)}`);
|
|
76
|
+
return challengeBody;
|
|
77
|
+
}
|
|
78
|
+
const challenge = parseChallenge(challengeResponse, challengeBody);
|
|
79
|
+
const privateKey = process.env.SEO_X402_PRIVATE_KEY;
|
|
80
|
+
if (!privateKey)
|
|
81
|
+
return safeChallenge(challenge);
|
|
82
|
+
if (!/^0x[a-fA-F0-9]{64}$/.test(privateKey))
|
|
83
|
+
throw new Error("SEO_X402_PRIVATE_KEY must be a 32-byte hex private key");
|
|
84
|
+
const amount = BigInt(challenge?.accepts?.[0]?.amount || 0);
|
|
85
|
+
if (amount <= 0n || amount > maxAtomic)
|
|
86
|
+
throw new Error(`Payment exceeds SEO_MAX_PAYMENT_USDC (${Number(maxAtomic) / 1_000_000})`);
|
|
87
|
+
const account = privateKeyToAccount(privateKey);
|
|
88
|
+
const httpClient = new x402HTTPClient(new x402Client().register("eip155:*", new ExactEvmScheme(toClientEvmSigner(account))));
|
|
89
|
+
const required = httpClient.getPaymentRequiredResponse(header => challengeResponse.headers.get(header), challengeBody);
|
|
90
|
+
const payload = await httpClient.createPaymentPayload(required);
|
|
91
|
+
const paid = await fetch(url, init(spec, httpClient.encodePaymentSignatureHeader(payload)));
|
|
92
|
+
const paidBody = await paid.json().catch(() => null);
|
|
93
|
+
if (!paid.ok)
|
|
94
|
+
throw new Error(`Paid SEO API ${paid.status}: ${JSON.stringify(paidBody).slice(0, 300)}`);
|
|
95
|
+
const receipt = httpClient.getPaymentSettleResponse(header => paid.headers.get(header));
|
|
96
|
+
const transaction = findTx(receipt);
|
|
97
|
+
if (!transaction)
|
|
98
|
+
throw new Error("Facilitator returned no settlement transaction hash");
|
|
99
|
+
return { ...paidBody, x402_settlement: { amount_usdc: Number(amount) / 1_000_000, network: challenge?.accepts?.[0]?.network, transaction } };
|
|
100
|
+
}
|
|
101
|
+
//# sourceMappingURL=client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"client.js","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,cAAc,EAAE,MAAM,mBAAmB,CAAC;AAC/D,OAAO,EAAE,cAAc,EAAE,MAAM,wBAAwB,CAAC;AACxD,OAAO,EAAE,iBAAiB,EAAE,MAAM,WAAW,CAAC;AAC9C,OAAO,EAAE,mBAAmB,EAAE,MAAM,eAAe,CAAC;AAKpD,MAAM,cAAc,GAAG,CAAC,OAAO,CAAC,GAAG,CAAC,YAAY,IAAI,0BAA0B,CAAC,CAAC,OAAO,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC;AACpG,MAAM,UAAU,GAAG,IAAI,GAAG,CAAC,cAAc,CAAC,CAAC;AAC3C,IAAI,UAAU,CAAC,QAAQ,KAAK,QAAQ;IAAE,MAAM,IAAI,KAAK,CAAC,6BAA6B,CAAC,CAAC;AACrF,IAAI,UAAU,CAAC,QAAQ,KAAK,kBAAkB,IAAI,OAAO,CAAC,GAAG,CAAC,yBAAyB,KAAK,MAAM,EAAE,CAAC;IACnG,MAAM,IAAI,KAAK,CAAC,6DAA6D,CAAC,CAAC;AACjF,CAAC;AACD,MAAM,QAAQ,GAAG,UAAU,CAAC,QAAQ,EAAE,CAAC,OAAO,CAAC,KAAK,EAAE,EAAE,CAAC,CAAC;AAC1D,MAAM,SAAS,GAAG,IAAI,CAAC,GAAG,CAAC,KAAK,EAAE,IAAI,CAAC,GAAG,CAAC,OAAO,EAAE,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,sBAAsB,IAAI,MAAM,CAAC,CAAC,CAAC,CAAC;AAC3G,MAAM,SAAS,GAAG,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,oBAAoB,IAAI,MAAM,CAAC,GAAG,SAAS,CAAC,CAAC,CAAC;AAErG,SAAS,WAAW,CAAC,IAAY,EAAE,MAA8B;IAC/D,MAAM,GAAG,GAAG,IAAI,GAAG,CAAC,IAAI,EAAE,GAAG,QAAQ,GAAG,CAAC,CAAC;IAC1C,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,MAAM,CAAC;QAAE,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;IACpF,OAAO,GAAG,GAAG,CAAC,QAAQ,GAAG,GAAG,CAAC,MAAM,EAAE,CAAC;AACxC,CAAC;AAED,MAAM,UAAU,cAAc,CAAC,IAAY,EAAE,IAAU;IACrD,QAAQ,IAAI,EAAE,CAAC;QACb,KAAK,sBAAsB,CAAC,CAAC,OAAO,EAAE,IAAI,EAAE,eAAe,EAAE,CAAC;QAC9D,KAAK,sBAAsB,CAAC,CAAC,OAAO,EAAE,IAAI,EAAE,WAAW,CAAC,sBAAsB,EAAE,EAAE,MAAM,EAAE,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,EAAE,CAAC,EAAE,CAAC;QACnH,KAAK,0BAA0B,CAAC,CAAC,OAAO,EAAE,IAAI,EAAE,uBAAuB,EAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,EAAE,OAAO,EAAE,IAAI,CAAC,OAAO,EAAE,EAAE,CAAC;QAC3H,KAAK,gBAAgB,CAAC,CAAC,OAAO,EAAE,IAAI,EAAE,mBAAmB,EAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,EAAE,GAAG,EAAE,IAAI,CAAC,GAAG,EAAE,IAAI,EAAE,IAAI,CAAC,IAAI,EAAE,EAAE,CAAC;QACtH,KAAK,mBAAmB,CAAC,CAAC,OAAO,EAAE,IAAI,EAAE,WAAW,CAAC,mBAAmB,EAAE,EAAE,CAAC,EAAE,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC,EAAE,CAAC;QACvG,KAAK,kBAAkB,CAAC,CAAC,OAAO,EAAE,IAAI,EAAE,WAAW,CAAC,kBAAkB,EAAE,EAAE,CAAC,EAAE,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC,EAAE,CAAC;QACrG,KAAK,4BAA4B,CAAC,CAAC,OAAO,EAAE,IAAI,EAAE,yBAAyB,EAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC;QAC1G,KAAK,8BAA8B,CAAC,CAAC,OAAO,EAAE,IAAI,EAAE,oBAAoB,EAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC;QACvG,KAAK,0BAA0B,CAAC,CAAC,OAAO,EAAE,IAAI,EAAE,mBAAmB,EAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC;QAClG,KAAK,gBAAgB,CAAC,CAAC,OAAO,EAAE,IAAI,EAAE,gBAAgB,EAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC;QACrF,KAAK,kCAAkC,CAAC,CAAC,OAAO,EAAE,IAAI,EAAE,iCAAiC,EAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC;QACxH,OAAO,CAAC,CAAC,MAAM,IAAI,KAAK,CAAC,iBAAiB,IAAI,EAAE,CAAC,CAAC;IACpD,CAAC;AACH,CAAC;AAED,SAAS,cAAc,CAAC,QAAkB,EAAE,IAAa;IACvD,MAAM,GAAG,GAAG,QAAQ,CAAC,OAAO,CAAC,GAAG,CAAC,kBAAkB,CAAC,CAAC;IACrD,IAAI,CAAC,GAAG;QAAE,OAAO,IAAI,CAAC;IACtB,IAAI,CAAC;QAAC,OAAO,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,EAAE,QAAQ,CAAC,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC;IAAC,CAAC;IAAC,MAAM,CAAC;QAAC,OAAO,IAAI,CAAC;IAAC,CAAC;AAChG,CAAC;AAED,SAAS,aAAa,CAAC,SAAc;IACnC,MAAM,MAAM,GAAG,SAAS,EAAE,OAAO,EAAE,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC;IAC7C,MAAM,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,MAAM,IAAI,GAAG,CAAC,CAAC;IAC5C,OAAO,EAAE,gBAAgB,EAAE,IAAI,EAAE,WAAW,EAAE,OAAO,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,MAAM,CAAC,GAAG,SAAS,CAAC,CAAC,CAAC,IAAI,EAAE,OAAO,EAAE,MAAM,CAAC,OAAO,IAAI,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC,KAAK,IAAI,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC,MAAM,IAAI,IAAI,EAAE,QAAQ,EAAE,SAAS,EAAE,QAAQ,EAAE,GAAG,IAAI,IAAI,EAAE,SAAS,EAAE,+GAA+G,EAAE,CAAC;AACjX,CAAC;AAED,SAAS,MAAM,CAAC,KAAc;IAC5B,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,qBAAqB,CAAC,IAAI,CAAC,KAAK,CAAC;QAAE,OAAO,KAAK,CAAC;IACjF,IAAI,CAAC,KAAK,IAAI,OAAO,KAAK,KAAK,QAAQ;QAAE,OAAO,IAAI,CAAC;IACrD,KAAK,MAAM,IAAI,IAAI,MAAM,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC;QAAC,MAAM,KAAK,GAAG,MAAM,CAAC,IAAI,CAAC,CAAC;QAAC,IAAI,KAAK;YAAE,OAAO,KAAK,CAAC;IAAC,CAAC;IACjG,OAAO,IAAI,CAAC;AACd,CAAC;AAED,SAAS,IAAI,CAAC,IAAiB,EAAE,eAAuC,EAAE;IACxE,OAAO,EAAE,MAAM,EAAE,IAAI,CAAC,MAAM,IAAI,KAAK,EAAE,OAAO,EAAE,EAAE,MAAM,EAAE,kBAAkB,EAAE,GAAG,YAAY,EAAE,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,cAAc,EAAE,kBAAkB,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,MAAM,EAAE,WAAW,CAAC,OAAO,CAAC,SAAS,CAAC,EAAE,CAAC;AACrQ,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,WAAW,CAAC,IAAY,EAAE,IAAU;IACxD,MAAM,IAAI,GAAG,cAAc,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC;IACxC,MAAM,GAAG,GAAG,GAAG,QAAQ,GAAG,IAAI,CAAC,IAAI,EAAE,CAAC;IACtC,MAAM,iBAAiB,GAAG,MAAM,KAAK,CAAC,GAAG,EAAE,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;IACvD,MAAM,aAAa,GAAG,MAAM,iBAAiB,CAAC,KAAK,EAAE,CAAC,IAAI,EAAE,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,CAAC;IAC/E,IAAI,iBAAiB,CAAC,MAAM,KAAK,GAAG,EAAE,CAAC;QACrC,IAAI,CAAC,iBAAiB,CAAC,EAAE;YAAE,MAAM,IAAI,KAAK,CAAC,WAAW,iBAAiB,CAAC,MAAM,KAAK,IAAI,CAAC,SAAS,CAAC,aAAa,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,GAAG,CAAC,EAAE,CAAC,CAAC;QAClI,OAAO,aAAa,CAAC;IACvB,CAAC;IACD,MAAM,SAAS,GAAG,cAAc,CAAC,iBAAiB,EAAE,aAAa,CAAC,CAAC;IACnE,MAAM,UAAU,GAAG,OAAO,CAAC,GAAG,CAAC,oBAAoB,CAAC;IACpD,IAAI,CAAC,UAAU;QAAE,OAAO,aAAa,CAAC,SAAS,CAAC,CAAC;IACjD,IAAI,CAAC,qBAAqB,CAAC,IAAI,CAAC,UAAU,CAAC;QAAE,MAAM,IAAI,KAAK,CAAC,wDAAwD,CAAC,CAAC;IACvH,MAAM,MAAM,GAAG,MAAM,CAAC,SAAS,EAAE,OAAO,EAAE,CAAC,CAAC,CAAC,EAAE,MAAM,IAAI,CAAC,CAAC,CAAC;IAC5D,IAAI,MAAM,IAAI,EAAE,IAAI,MAAM,GAAG,SAAS;QAAE,MAAM,IAAI,KAAK,CAAC,yCAAyC,MAAM,CAAC,SAAS,CAAC,GAAG,SAAS,GAAG,CAAC,CAAC;IACnI,MAAM,OAAO,GAAG,mBAAmB,CAAC,UAA2B,CAAC,CAAC;IACjE,MAAM,UAAU,GAAG,IAAI,cAAc,CAAC,IAAI,UAAU,EAAE,CAAC,QAAQ,CAAC,UAAU,EAAE,IAAI,cAAc,CAAC,iBAAiB,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC;IAC7H,MAAM,QAAQ,GAAG,UAAU,CAAC,0BAA0B,CAAC,MAAM,CAAC,EAAE,CAAC,iBAAiB,CAAC,OAAO,CAAC,GAAG,CAAC,MAAM,CAAC,EAAE,aAAa,CAAC,CAAC;IACvH,MAAM,OAAO,GAAG,MAAM,UAAU,CAAC,oBAAoB,CAAC,QAAQ,CAAC,CAAC;IAChE,MAAM,IAAI,GAAG,MAAM,KAAK,CAAC,GAAG,EAAE,IAAI,CAAC,IAAI,EAAE,UAAU,CAAC,4BAA4B,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC;IAC5F,MAAM,QAAQ,GAAG,MAAM,IAAI,CAAC,IAAI,EAAE,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,CAAC;IACrD,IAAI,CAAC,IAAI,CAAC,EAAE;QAAE,MAAM,IAAI,KAAK,CAAC,gBAAgB,IAAI,CAAC,MAAM,KAAK,IAAI,CAAC,SAAS,CAAC,QAAQ,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,GAAG,CAAC,EAAE,CAAC,CAAC;IACxG,MAAM,OAAO,GAAG,UAAU,CAAC,wBAAwB,CAAC,MAAM,CAAC,EAAE,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC,CAAC;IACxF,MAAM,WAAW,GAAG,MAAM,CAAC,OAAO,CAAC,CAAC;IACpC,IAAI,CAAC,WAAW;QAAE,MAAM,IAAI,KAAK,CAAC,qDAAqD,CAAC,CAAC;IACzF,OAAO,EAAE,GAAG,QAAQ,EAAE,eAAe,EAAE,EAAE,WAAW,EAAE,MAAM,CAAC,MAAM,CAAC,GAAG,SAAS,EAAE,OAAO,EAAE,SAAS,EAAE,OAAO,EAAE,CAAC,CAAC,CAAC,EAAE,OAAO,EAAE,WAAW,EAAE,EAAE,CAAC;AAC/I,CAAC"}
|
package/dist/index.d.ts
ADDED
package/dist/index.js
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import { Server } from "@modelcontextprotocol/sdk/server/index.js";
|
|
3
|
+
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
|
|
4
|
+
import { CallToolRequestSchema, ListToolsRequestSchema } from "@modelcontextprotocol/sdk/types.js";
|
|
5
|
+
import { callSeoTool } from "./client.js";
|
|
6
|
+
import { tools } from "./tools.js";
|
|
7
|
+
const server = new Server({ name: "seo-authority-mcp", version: "0.1.0" }, { capabilities: { tools: {} } });
|
|
8
|
+
server.setRequestHandler(ListToolsRequestSchema, async () => ({ tools }));
|
|
9
|
+
server.setRequestHandler(CallToolRequestSchema, async (request) => {
|
|
10
|
+
try {
|
|
11
|
+
const data = await callSeoTool(request.params.name, (request.params.arguments || {}));
|
|
12
|
+
return { content: [{ type: "text", text: JSON.stringify(data) }] };
|
|
13
|
+
}
|
|
14
|
+
catch (error) {
|
|
15
|
+
const message = error instanceof Error ? error.message : "Unknown error";
|
|
16
|
+
return { content: [{ type: "text", text: JSON.stringify({ error: { code: "SEO_TOOL_ERROR", message } }) }], isError: true };
|
|
17
|
+
}
|
|
18
|
+
});
|
|
19
|
+
await server.connect(new StdioServerTransport());
|
|
20
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AACA,OAAO,EAAE,MAAM,EAAE,MAAM,2CAA2C,CAAC;AACnE,OAAO,EAAE,oBAAoB,EAAE,MAAM,2CAA2C,CAAC;AACjF,OAAO,EAAE,qBAAqB,EAAE,sBAAsB,EAAE,MAAM,oCAAoC,CAAC;AACnG,OAAO,EAAE,WAAW,EAAE,MAAM,aAAa,CAAC;AAC1C,OAAO,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;AAEnC,MAAM,MAAM,GAAG,IAAI,MAAM,CAAC,EAAE,IAAI,EAAE,mBAAmB,EAAE,OAAO,EAAE,OAAO,EAAE,EAAE,EAAE,YAAY,EAAE,EAAE,KAAK,EAAE,EAAE,EAAE,EAAE,CAAC,CAAC;AAC5G,MAAM,CAAC,iBAAiB,CAAC,sBAAsB,EAAE,KAAK,IAAI,EAAE,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,CAAC,CAAC;AAC1E,MAAM,CAAC,iBAAiB,CAAC,qBAAqB,EAAE,KAAK,EAAC,OAAO,EAAC,EAAE;IAC9D,IAAI,CAAC;QACH,MAAM,IAAI,GAAG,MAAM,WAAW,CAAC,OAAO,CAAC,MAAM,CAAC,IAAI,EAAE,CAAC,OAAO,CAAC,MAAM,CAAC,SAAS,IAAI,EAAE,CAA4B,CAAC,CAAC;QACjH,OAAO,EAAE,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,EAAE,CAAC,EAAE,CAAC;IACrE,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,MAAM,OAAO,GAAG,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,eAAe,CAAC;QACzE,OAAO,EAAE,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,EAAE,KAAK,EAAE,EAAE,IAAI,EAAE,gBAAgB,EAAE,OAAO,EAAE,EAAE,CAAC,EAAE,CAAC,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC;IAC9H,CAAC;AACH,CAAC,CAAC,CAAC;AAEH,MAAM,MAAM,CAAC,OAAO,CAAC,IAAI,oBAAoB,EAAE,CAAC,CAAC"}
|
package/dist/tools.d.ts
ADDED
package/dist/tools.js
ADDED
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
const readOnly = { readOnlyHint: true, destructiveHint: false, idempotentHint: true, openWorldHint: true };
|
|
2
|
+
const string = (description) => ({ type: "string", description });
|
|
3
|
+
const page = {
|
|
4
|
+
type: "object",
|
|
5
|
+
properties: { url: string("Absolute page URL."), title: string("Page title."), text: string("Visible page text."), html: string("Page HTML, when required.") },
|
|
6
|
+
required: ["url"]
|
|
7
|
+
};
|
|
8
|
+
export const tools = [
|
|
9
|
+
{ name: "get_seo_capabilities", description: "Retrieve free capability, provenance, and unavailable-metric disclosures before choosing a paid SEO tool.", annotations: readOnly, inputSchema: { type: "object", properties: {} } },
|
|
10
|
+
{ name: "get_domain_authority", description: "Measure one domain's open-web SEO authority using Common Crawl harmonic centrality and PageRank graph data; costs $0.01 USDC.", annotations: readOnly, inputSchema: { type: "object", properties: { domain: string("Domain or URL to measure, such as example.com.") }, required: ["domain"] } },
|
|
11
|
+
{ name: "compare_domain_authority", description: "Compare open-web SEO authority for 2 to 20 domains and rank the results; costs $0.02 USDC.", annotations: readOnly, inputSchema: { type: "object", properties: { domains: { type: "array", description: "Two to twenty domains or URLs.", minItems: 2, maxItems: 20, items: { type: "string" } } }, required: ["domains"] } },
|
|
12
|
+
{ name: "score_page_seo", description: "Score supplied page HTML for deterministic on-page SEO checks without claiming page authority; costs $0.01 USDC.", annotations: readOnly, inputSchema: { type: "object", properties: { url: string("Canonical URL for the supplied page."), html: string("Complete page HTML, up to 512 KB.") }, required: ["url", "html"] } },
|
|
13
|
+
{ name: "correct_seo_query", description: "Correct likely spelling errors in an SEO search query; costs $0.005 USDC.", annotations: readOnly, inputSchema: { type: "object", properties: { query: string("SEO query to correct.") }, required: ["query"] } },
|
|
14
|
+
{ name: "expand_seo_query", description: "Generate deterministic long-tail and intent-oriented variants of an SEO query; costs $0.01 USDC.", annotations: readOnly, inputSchema: { type: "object", properties: { query: string("Seed SEO query to expand.") }, required: ["query"] } },
|
|
15
|
+
{ name: "find_keyword_opportunities", description: "Generate and prioritize long-tail keyword opportunities without fabricating volume, CPC, SERP, or difficulty metrics; costs $0.05 USDC.", annotations: readOnly, inputSchema: { type: "object", properties: { seed: string("Seed topic or keyword."), audience: string("Optional target audience."), domain_authority_score: { type: "number", minimum: 0, maximum: 100, description: "Optional known authority score used for prioritization." } }, required: ["seed"] } },
|
|
16
|
+
{
|
|
17
|
+
name: "find_competitor_content_gaps",
|
|
18
|
+
description: "Find content gaps from customer-supplied site and competitor pages without claiming live SERP verification; costs $0.10 USDC.",
|
|
19
|
+
annotations: readOnly,
|
|
20
|
+
inputSchema: {
|
|
21
|
+
type: "object",
|
|
22
|
+
properties: {
|
|
23
|
+
site: {
|
|
24
|
+
type: "object",
|
|
25
|
+
description: "Your domain and supplied pages.",
|
|
26
|
+
properties: {
|
|
27
|
+
domain: string("Your domain."),
|
|
28
|
+
pages: { type: "array", minItems: 1, maxItems: 50, items: page }
|
|
29
|
+
},
|
|
30
|
+
required: ["domain", "pages"]
|
|
31
|
+
},
|
|
32
|
+
competitors: {
|
|
33
|
+
type: "array",
|
|
34
|
+
description: "One to ten competitors with supplied pages.",
|
|
35
|
+
minItems: 1,
|
|
36
|
+
maxItems: 10,
|
|
37
|
+
items: {
|
|
38
|
+
type: "object",
|
|
39
|
+
properties: {
|
|
40
|
+
domain: string("Competitor domain."),
|
|
41
|
+
pages: { type: "array", minItems: 1, maxItems: 50, items: page }
|
|
42
|
+
},
|
|
43
|
+
required: ["domain", "pages"]
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
},
|
|
47
|
+
required: ["site", "competitors"]
|
|
48
|
+
}
|
|
49
|
+
},
|
|
50
|
+
{ name: "create_seo_content_brief", description: "Create an evidence-tagged SEO content brief from a keyword and supplied competitor or site pages; costs $0.10 USDC.", annotations: readOnly, inputSchema: { type: "object", properties: { keyword: string("Primary keyword or topic."), competitor_pages: { type: "array", maxItems: 50, items: page, description: "Optional competitor pages providing evidence." }, site_pages: { type: "array", maxItems: 50, items: page, description: "Optional existing site pages for differentiation and linking." } }, required: ["keyword"] } },
|
|
51
|
+
{ name: "audit_site_seo", description: "Audit supplied page HTML for on-page, duplication, and internal-link problems; costs $0.15 USDC.", annotations: readOnly, inputSchema: { type: "object", properties: { pages: { type: "array", minItems: 1, maxItems: 50, description: "Pages to audit; each requires url and html.", items: { ...page, required: ["url", "html"] } } }, required: ["pages"] } },
|
|
52
|
+
{ name: "find_internal_link_opportunities", description: "Find missing contextually relevant internal links across supplied pages; costs $0.05 USDC.", annotations: readOnly, inputSchema: { type: "object", properties: { domain: string("Site domain."), pages: { type: "array", minItems: 2, maxItems: 50, items: page, description: "Two or more site pages with title and text for best results." } }, required: ["domain", "pages"] } }
|
|
53
|
+
];
|
|
54
|
+
export const paidToolNames = new Set(tools.slice(1).map(tool => tool.name));
|
|
55
|
+
//# sourceMappingURL=tools.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tools.js","sourceRoot":"","sources":["../src/tools.ts"],"names":[],"mappings":"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"}
|
package/glama.json
ADDED
package/package.json
ADDED
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@forgemeshlabs/seo-authority-mcp",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"mcpName": "io.github.forgemeshlabs/seo-authority-mcp",
|
|
5
|
+
"description": "SEO authority, keyword opportunities, competitor gaps, content briefs, site audits, and internal-link intelligence via x402.",
|
|
6
|
+
"type": "module",
|
|
7
|
+
"main": "dist/index.js",
|
|
8
|
+
"bin": { "seo-authority-mcp": "dist/index.js" },
|
|
9
|
+
"files": ["dist", "tool_manifest.json", "README.md", "GLAMA.md", "glama.json", "server.json", "smithery.yaml", "LICENSE", "SECURITY.md", "CHANGELOG.md", "examples"],
|
|
10
|
+
"scripts": {
|
|
11
|
+
"build": "tsc -p tsconfig.json && node scripts/generate-manifest.mjs",
|
|
12
|
+
"typecheck": "tsc -p tsconfig.json --noEmit",
|
|
13
|
+
"start": "node dist/index.js",
|
|
14
|
+
"test": "vitest run --cache=false"
|
|
15
|
+
},
|
|
16
|
+
"dependencies": {
|
|
17
|
+
"@modelcontextprotocol/sdk": "^1.30.0",
|
|
18
|
+
"@x402/core": "^2.16.0",
|
|
19
|
+
"@x402/evm": "^2.16.0",
|
|
20
|
+
"viem": "^2.38.0"
|
|
21
|
+
},
|
|
22
|
+
"devDependencies": {
|
|
23
|
+
"@types/node": "^22.10.0",
|
|
24
|
+
"typescript": "^5.7.3",
|
|
25
|
+
"vitest": "^4.1.10"
|
|
26
|
+
},
|
|
27
|
+
"keywords": ["mcp", "model-context-protocol", "seo", "domain-authority", "keyword-research", "competitor-analysis", "site-audit", "x402", "usdc", "base", "glama", "forgemesh"],
|
|
28
|
+
"author": "ForgeMesh",
|
|
29
|
+
"license": "MIT",
|
|
30
|
+
"repository": { "type": "git", "url": "git+https://github.com/forgemeshlabs/seo-authority-mcp.git" },
|
|
31
|
+
"bugs": { "url": "https://github.com/forgemeshlabs/seo-authority-mcp/issues" },
|
|
32
|
+
"homepage": "https://github.com/forgemeshlabs/seo-authority-mcp#readme",
|
|
33
|
+
"publishConfig": { "access": "public" },
|
|
34
|
+
"engines": { "node": ">=22" }
|
|
35
|
+
}
|
package/server.json
ADDED
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
{
|
|
2
|
+
"$schema": "https://static.modelcontextprotocol.io/schemas/2025-12-11/server.schema.json",
|
|
3
|
+
"name": "io.github.forgemeshlabs/seo-authority-mcp",
|
|
4
|
+
"description": "SEO authority, keyword, competitor, content, site-audit, and internal-link tools with optional automatic x402 payments.",
|
|
5
|
+
"repository": { "url": "https://github.com/forgemeshlabs/seo-authority-mcp", "source": "github" },
|
|
6
|
+
"version": "0.1.0",
|
|
7
|
+
"packages": [{
|
|
8
|
+
"registryType": "npm",
|
|
9
|
+
"identifier": "@forgemeshlabs/seo-authority-mcp",
|
|
10
|
+
"version": "0.1.0",
|
|
11
|
+
"transport": { "type": "stdio" },
|
|
12
|
+
"environmentVariables": [
|
|
13
|
+
{ "name": "SEO_API_BASE", "description": "Optional backend override; defaults to https://seo.forgemesh.io.", "isRequired": false, "isSecret": false, "format": "string" },
|
|
14
|
+
{ "name": "SEO_X402_PRIVATE_KEY", "description": "Optional EVM wallet private key for automatic x402 USDC settlement.", "isRequired": false, "isSecret": true, "format": "string" },
|
|
15
|
+
{ "name": "SEO_MAX_PAYMENT_USDC", "description": "Maximum automatic payment per tool call; defaults to 0.15 USDC.", "isRequired": false, "isSecret": false, "format": "string" }
|
|
16
|
+
]
|
|
17
|
+
}]
|
|
18
|
+
}
|
package/smithery.yaml
ADDED
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
startCommand:
|
|
2
|
+
type: stdio
|
|
3
|
+
configSchema:
|
|
4
|
+
type: object
|
|
5
|
+
properties:
|
|
6
|
+
seoApiBase:
|
|
7
|
+
type: string
|
|
8
|
+
description: SEO API base URL. Defaults to https://seo.forgemesh.io.
|
|
9
|
+
seoX402PrivateKey:
|
|
10
|
+
type: string
|
|
11
|
+
description: Optional EVM private key for automatic x402 settlement.
|
|
12
|
+
seoMaxPaymentUsdc:
|
|
13
|
+
type: string
|
|
14
|
+
description: Maximum automatic USDC payment per call. Defaults to 0.15.
|
|
15
|
+
commandFunction: |-
|
|
16
|
+
(config) => ({
|
|
17
|
+
command: 'npx',
|
|
18
|
+
args: ['-y', '@forgemeshlabs/seo-authority-mcp'],
|
|
19
|
+
env: {
|
|
20
|
+
SEO_API_BASE: config.seoApiBase || 'https://seo.forgemesh.io',
|
|
21
|
+
SEO_X402_PRIVATE_KEY: config.seoX402PrivateKey || '',
|
|
22
|
+
SEO_MAX_PAYMENT_USDC: config.seoMaxPaymentUsdc || '0.15'
|
|
23
|
+
}
|
|
24
|
+
})
|
|
25
|
+
exampleConfig:
|
|
26
|
+
seoApiBase: https://seo.forgemesh.io
|
|
27
|
+
seoMaxPaymentUsdc: '0.15'
|
|
@@ -0,0 +1,465 @@
|
|
|
1
|
+
{
|
|
2
|
+
"server": "seo-authority-mcp",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"source": "https://seo.forgemesh.io/openapi.json",
|
|
5
|
+
"tools": [
|
|
6
|
+
{
|
|
7
|
+
"name": "get_seo_capabilities",
|
|
8
|
+
"description": "Retrieve free capability, provenance, and unavailable-metric disclosures before choosing a paid SEO tool.",
|
|
9
|
+
"annotations": {
|
|
10
|
+
"readOnlyHint": true,
|
|
11
|
+
"destructiveHint": false,
|
|
12
|
+
"idempotentHint": true,
|
|
13
|
+
"openWorldHint": true
|
|
14
|
+
},
|
|
15
|
+
"inputSchema": {
|
|
16
|
+
"type": "object",
|
|
17
|
+
"properties": {}
|
|
18
|
+
}
|
|
19
|
+
},
|
|
20
|
+
{
|
|
21
|
+
"name": "get_domain_authority",
|
|
22
|
+
"description": "Measure one domain's open-web SEO authority using Common Crawl harmonic centrality and PageRank graph data; costs $0.01 USDC.",
|
|
23
|
+
"annotations": {
|
|
24
|
+
"readOnlyHint": true,
|
|
25
|
+
"destructiveHint": false,
|
|
26
|
+
"idempotentHint": true,
|
|
27
|
+
"openWorldHint": true
|
|
28
|
+
},
|
|
29
|
+
"inputSchema": {
|
|
30
|
+
"type": "object",
|
|
31
|
+
"properties": {
|
|
32
|
+
"domain": {
|
|
33
|
+
"type": "string",
|
|
34
|
+
"description": "Domain or URL to measure, such as example.com."
|
|
35
|
+
}
|
|
36
|
+
},
|
|
37
|
+
"required": [
|
|
38
|
+
"domain"
|
|
39
|
+
]
|
|
40
|
+
}
|
|
41
|
+
},
|
|
42
|
+
{
|
|
43
|
+
"name": "compare_domain_authority",
|
|
44
|
+
"description": "Compare open-web SEO authority for 2 to 20 domains and rank the results; costs $0.02 USDC.",
|
|
45
|
+
"annotations": {
|
|
46
|
+
"readOnlyHint": true,
|
|
47
|
+
"destructiveHint": false,
|
|
48
|
+
"idempotentHint": true,
|
|
49
|
+
"openWorldHint": true
|
|
50
|
+
},
|
|
51
|
+
"inputSchema": {
|
|
52
|
+
"type": "object",
|
|
53
|
+
"properties": {
|
|
54
|
+
"domains": {
|
|
55
|
+
"type": "array",
|
|
56
|
+
"description": "Two to twenty domains or URLs.",
|
|
57
|
+
"minItems": 2,
|
|
58
|
+
"maxItems": 20,
|
|
59
|
+
"items": {
|
|
60
|
+
"type": "string"
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
},
|
|
64
|
+
"required": [
|
|
65
|
+
"domains"
|
|
66
|
+
]
|
|
67
|
+
}
|
|
68
|
+
},
|
|
69
|
+
{
|
|
70
|
+
"name": "score_page_seo",
|
|
71
|
+
"description": "Score supplied page HTML for deterministic on-page SEO checks without claiming page authority; costs $0.01 USDC.",
|
|
72
|
+
"annotations": {
|
|
73
|
+
"readOnlyHint": true,
|
|
74
|
+
"destructiveHint": false,
|
|
75
|
+
"idempotentHint": true,
|
|
76
|
+
"openWorldHint": true
|
|
77
|
+
},
|
|
78
|
+
"inputSchema": {
|
|
79
|
+
"type": "object",
|
|
80
|
+
"properties": {
|
|
81
|
+
"url": {
|
|
82
|
+
"type": "string",
|
|
83
|
+
"description": "Canonical URL for the supplied page."
|
|
84
|
+
},
|
|
85
|
+
"html": {
|
|
86
|
+
"type": "string",
|
|
87
|
+
"description": "Complete page HTML, up to 512 KB."
|
|
88
|
+
}
|
|
89
|
+
},
|
|
90
|
+
"required": [
|
|
91
|
+
"url",
|
|
92
|
+
"html"
|
|
93
|
+
]
|
|
94
|
+
}
|
|
95
|
+
},
|
|
96
|
+
{
|
|
97
|
+
"name": "correct_seo_query",
|
|
98
|
+
"description": "Correct likely spelling errors in an SEO search query; costs $0.005 USDC.",
|
|
99
|
+
"annotations": {
|
|
100
|
+
"readOnlyHint": true,
|
|
101
|
+
"destructiveHint": false,
|
|
102
|
+
"idempotentHint": true,
|
|
103
|
+
"openWorldHint": true
|
|
104
|
+
},
|
|
105
|
+
"inputSchema": {
|
|
106
|
+
"type": "object",
|
|
107
|
+
"properties": {
|
|
108
|
+
"query": {
|
|
109
|
+
"type": "string",
|
|
110
|
+
"description": "SEO query to correct."
|
|
111
|
+
}
|
|
112
|
+
},
|
|
113
|
+
"required": [
|
|
114
|
+
"query"
|
|
115
|
+
]
|
|
116
|
+
}
|
|
117
|
+
},
|
|
118
|
+
{
|
|
119
|
+
"name": "expand_seo_query",
|
|
120
|
+
"description": "Generate deterministic long-tail and intent-oriented variants of an SEO query; costs $0.01 USDC.",
|
|
121
|
+
"annotations": {
|
|
122
|
+
"readOnlyHint": true,
|
|
123
|
+
"destructiveHint": false,
|
|
124
|
+
"idempotentHint": true,
|
|
125
|
+
"openWorldHint": true
|
|
126
|
+
},
|
|
127
|
+
"inputSchema": {
|
|
128
|
+
"type": "object",
|
|
129
|
+
"properties": {
|
|
130
|
+
"query": {
|
|
131
|
+
"type": "string",
|
|
132
|
+
"description": "Seed SEO query to expand."
|
|
133
|
+
}
|
|
134
|
+
},
|
|
135
|
+
"required": [
|
|
136
|
+
"query"
|
|
137
|
+
]
|
|
138
|
+
}
|
|
139
|
+
},
|
|
140
|
+
{
|
|
141
|
+
"name": "find_keyword_opportunities",
|
|
142
|
+
"description": "Generate and prioritize long-tail keyword opportunities without fabricating volume, CPC, SERP, or difficulty metrics; costs $0.05 USDC.",
|
|
143
|
+
"annotations": {
|
|
144
|
+
"readOnlyHint": true,
|
|
145
|
+
"destructiveHint": false,
|
|
146
|
+
"idempotentHint": true,
|
|
147
|
+
"openWorldHint": true
|
|
148
|
+
},
|
|
149
|
+
"inputSchema": {
|
|
150
|
+
"type": "object",
|
|
151
|
+
"properties": {
|
|
152
|
+
"seed": {
|
|
153
|
+
"type": "string",
|
|
154
|
+
"description": "Seed topic or keyword."
|
|
155
|
+
},
|
|
156
|
+
"audience": {
|
|
157
|
+
"type": "string",
|
|
158
|
+
"description": "Optional target audience."
|
|
159
|
+
},
|
|
160
|
+
"domain_authority_score": {
|
|
161
|
+
"type": "number",
|
|
162
|
+
"minimum": 0,
|
|
163
|
+
"maximum": 100,
|
|
164
|
+
"description": "Optional known authority score used for prioritization."
|
|
165
|
+
}
|
|
166
|
+
},
|
|
167
|
+
"required": [
|
|
168
|
+
"seed"
|
|
169
|
+
]
|
|
170
|
+
}
|
|
171
|
+
},
|
|
172
|
+
{
|
|
173
|
+
"name": "find_competitor_content_gaps",
|
|
174
|
+
"description": "Find content gaps from customer-supplied site and competitor pages without claiming live SERP verification; costs $0.10 USDC.",
|
|
175
|
+
"annotations": {
|
|
176
|
+
"readOnlyHint": true,
|
|
177
|
+
"destructiveHint": false,
|
|
178
|
+
"idempotentHint": true,
|
|
179
|
+
"openWorldHint": true
|
|
180
|
+
},
|
|
181
|
+
"inputSchema": {
|
|
182
|
+
"type": "object",
|
|
183
|
+
"properties": {
|
|
184
|
+
"site": {
|
|
185
|
+
"type": "object",
|
|
186
|
+
"description": "Your domain and supplied pages.",
|
|
187
|
+
"properties": {
|
|
188
|
+
"domain": {
|
|
189
|
+
"type": "string",
|
|
190
|
+
"description": "Your domain."
|
|
191
|
+
},
|
|
192
|
+
"pages": {
|
|
193
|
+
"type": "array",
|
|
194
|
+
"minItems": 1,
|
|
195
|
+
"maxItems": 50,
|
|
196
|
+
"items": {
|
|
197
|
+
"type": "object",
|
|
198
|
+
"properties": {
|
|
199
|
+
"url": {
|
|
200
|
+
"type": "string",
|
|
201
|
+
"description": "Absolute page URL."
|
|
202
|
+
},
|
|
203
|
+
"title": {
|
|
204
|
+
"type": "string",
|
|
205
|
+
"description": "Page title."
|
|
206
|
+
},
|
|
207
|
+
"text": {
|
|
208
|
+
"type": "string",
|
|
209
|
+
"description": "Visible page text."
|
|
210
|
+
},
|
|
211
|
+
"html": {
|
|
212
|
+
"type": "string",
|
|
213
|
+
"description": "Page HTML, when required."
|
|
214
|
+
}
|
|
215
|
+
},
|
|
216
|
+
"required": [
|
|
217
|
+
"url"
|
|
218
|
+
]
|
|
219
|
+
}
|
|
220
|
+
}
|
|
221
|
+
},
|
|
222
|
+
"required": [
|
|
223
|
+
"domain",
|
|
224
|
+
"pages"
|
|
225
|
+
]
|
|
226
|
+
},
|
|
227
|
+
"competitors": {
|
|
228
|
+
"type": "array",
|
|
229
|
+
"description": "One to ten competitors with supplied pages.",
|
|
230
|
+
"minItems": 1,
|
|
231
|
+
"maxItems": 10,
|
|
232
|
+
"items": {
|
|
233
|
+
"type": "object",
|
|
234
|
+
"properties": {
|
|
235
|
+
"domain": {
|
|
236
|
+
"type": "string",
|
|
237
|
+
"description": "Competitor domain."
|
|
238
|
+
},
|
|
239
|
+
"pages": {
|
|
240
|
+
"type": "array",
|
|
241
|
+
"minItems": 1,
|
|
242
|
+
"maxItems": 50,
|
|
243
|
+
"items": {
|
|
244
|
+
"type": "object",
|
|
245
|
+
"properties": {
|
|
246
|
+
"url": {
|
|
247
|
+
"type": "string",
|
|
248
|
+
"description": "Absolute page URL."
|
|
249
|
+
},
|
|
250
|
+
"title": {
|
|
251
|
+
"type": "string",
|
|
252
|
+
"description": "Page title."
|
|
253
|
+
},
|
|
254
|
+
"text": {
|
|
255
|
+
"type": "string",
|
|
256
|
+
"description": "Visible page text."
|
|
257
|
+
},
|
|
258
|
+
"html": {
|
|
259
|
+
"type": "string",
|
|
260
|
+
"description": "Page HTML, when required."
|
|
261
|
+
}
|
|
262
|
+
},
|
|
263
|
+
"required": [
|
|
264
|
+
"url"
|
|
265
|
+
]
|
|
266
|
+
}
|
|
267
|
+
}
|
|
268
|
+
},
|
|
269
|
+
"required": [
|
|
270
|
+
"domain",
|
|
271
|
+
"pages"
|
|
272
|
+
]
|
|
273
|
+
}
|
|
274
|
+
}
|
|
275
|
+
},
|
|
276
|
+
"required": [
|
|
277
|
+
"site",
|
|
278
|
+
"competitors"
|
|
279
|
+
]
|
|
280
|
+
}
|
|
281
|
+
},
|
|
282
|
+
{
|
|
283
|
+
"name": "create_seo_content_brief",
|
|
284
|
+
"description": "Create an evidence-tagged SEO content brief from a keyword and supplied competitor or site pages; costs $0.10 USDC.",
|
|
285
|
+
"annotations": {
|
|
286
|
+
"readOnlyHint": true,
|
|
287
|
+
"destructiveHint": false,
|
|
288
|
+
"idempotentHint": true,
|
|
289
|
+
"openWorldHint": true
|
|
290
|
+
},
|
|
291
|
+
"inputSchema": {
|
|
292
|
+
"type": "object",
|
|
293
|
+
"properties": {
|
|
294
|
+
"keyword": {
|
|
295
|
+
"type": "string",
|
|
296
|
+
"description": "Primary keyword or topic."
|
|
297
|
+
},
|
|
298
|
+
"competitor_pages": {
|
|
299
|
+
"type": "array",
|
|
300
|
+
"maxItems": 50,
|
|
301
|
+
"items": {
|
|
302
|
+
"type": "object",
|
|
303
|
+
"properties": {
|
|
304
|
+
"url": {
|
|
305
|
+
"type": "string",
|
|
306
|
+
"description": "Absolute page URL."
|
|
307
|
+
},
|
|
308
|
+
"title": {
|
|
309
|
+
"type": "string",
|
|
310
|
+
"description": "Page title."
|
|
311
|
+
},
|
|
312
|
+
"text": {
|
|
313
|
+
"type": "string",
|
|
314
|
+
"description": "Visible page text."
|
|
315
|
+
},
|
|
316
|
+
"html": {
|
|
317
|
+
"type": "string",
|
|
318
|
+
"description": "Page HTML, when required."
|
|
319
|
+
}
|
|
320
|
+
},
|
|
321
|
+
"required": [
|
|
322
|
+
"url"
|
|
323
|
+
]
|
|
324
|
+
},
|
|
325
|
+
"description": "Optional competitor pages providing evidence."
|
|
326
|
+
},
|
|
327
|
+
"site_pages": {
|
|
328
|
+
"type": "array",
|
|
329
|
+
"maxItems": 50,
|
|
330
|
+
"items": {
|
|
331
|
+
"type": "object",
|
|
332
|
+
"properties": {
|
|
333
|
+
"url": {
|
|
334
|
+
"type": "string",
|
|
335
|
+
"description": "Absolute page URL."
|
|
336
|
+
},
|
|
337
|
+
"title": {
|
|
338
|
+
"type": "string",
|
|
339
|
+
"description": "Page title."
|
|
340
|
+
},
|
|
341
|
+
"text": {
|
|
342
|
+
"type": "string",
|
|
343
|
+
"description": "Visible page text."
|
|
344
|
+
},
|
|
345
|
+
"html": {
|
|
346
|
+
"type": "string",
|
|
347
|
+
"description": "Page HTML, when required."
|
|
348
|
+
}
|
|
349
|
+
},
|
|
350
|
+
"required": [
|
|
351
|
+
"url"
|
|
352
|
+
]
|
|
353
|
+
},
|
|
354
|
+
"description": "Optional existing site pages for differentiation and linking."
|
|
355
|
+
}
|
|
356
|
+
},
|
|
357
|
+
"required": [
|
|
358
|
+
"keyword"
|
|
359
|
+
]
|
|
360
|
+
}
|
|
361
|
+
},
|
|
362
|
+
{
|
|
363
|
+
"name": "audit_site_seo",
|
|
364
|
+
"description": "Audit supplied page HTML for on-page, duplication, and internal-link problems; costs $0.15 USDC.",
|
|
365
|
+
"annotations": {
|
|
366
|
+
"readOnlyHint": true,
|
|
367
|
+
"destructiveHint": false,
|
|
368
|
+
"idempotentHint": true,
|
|
369
|
+
"openWorldHint": true
|
|
370
|
+
},
|
|
371
|
+
"inputSchema": {
|
|
372
|
+
"type": "object",
|
|
373
|
+
"properties": {
|
|
374
|
+
"pages": {
|
|
375
|
+
"type": "array",
|
|
376
|
+
"minItems": 1,
|
|
377
|
+
"maxItems": 50,
|
|
378
|
+
"description": "Pages to audit; each requires url and html.",
|
|
379
|
+
"items": {
|
|
380
|
+
"type": "object",
|
|
381
|
+
"properties": {
|
|
382
|
+
"url": {
|
|
383
|
+
"type": "string",
|
|
384
|
+
"description": "Absolute page URL."
|
|
385
|
+
},
|
|
386
|
+
"title": {
|
|
387
|
+
"type": "string",
|
|
388
|
+
"description": "Page title."
|
|
389
|
+
},
|
|
390
|
+
"text": {
|
|
391
|
+
"type": "string",
|
|
392
|
+
"description": "Visible page text."
|
|
393
|
+
},
|
|
394
|
+
"html": {
|
|
395
|
+
"type": "string",
|
|
396
|
+
"description": "Page HTML, when required."
|
|
397
|
+
}
|
|
398
|
+
},
|
|
399
|
+
"required": [
|
|
400
|
+
"url",
|
|
401
|
+
"html"
|
|
402
|
+
]
|
|
403
|
+
}
|
|
404
|
+
}
|
|
405
|
+
},
|
|
406
|
+
"required": [
|
|
407
|
+
"pages"
|
|
408
|
+
]
|
|
409
|
+
}
|
|
410
|
+
},
|
|
411
|
+
{
|
|
412
|
+
"name": "find_internal_link_opportunities",
|
|
413
|
+
"description": "Find missing contextually relevant internal links across supplied pages; costs $0.05 USDC.",
|
|
414
|
+
"annotations": {
|
|
415
|
+
"readOnlyHint": true,
|
|
416
|
+
"destructiveHint": false,
|
|
417
|
+
"idempotentHint": true,
|
|
418
|
+
"openWorldHint": true
|
|
419
|
+
},
|
|
420
|
+
"inputSchema": {
|
|
421
|
+
"type": "object",
|
|
422
|
+
"properties": {
|
|
423
|
+
"domain": {
|
|
424
|
+
"type": "string",
|
|
425
|
+
"description": "Site domain."
|
|
426
|
+
},
|
|
427
|
+
"pages": {
|
|
428
|
+
"type": "array",
|
|
429
|
+
"minItems": 2,
|
|
430
|
+
"maxItems": 50,
|
|
431
|
+
"items": {
|
|
432
|
+
"type": "object",
|
|
433
|
+
"properties": {
|
|
434
|
+
"url": {
|
|
435
|
+
"type": "string",
|
|
436
|
+
"description": "Absolute page URL."
|
|
437
|
+
},
|
|
438
|
+
"title": {
|
|
439
|
+
"type": "string",
|
|
440
|
+
"description": "Page title."
|
|
441
|
+
},
|
|
442
|
+
"text": {
|
|
443
|
+
"type": "string",
|
|
444
|
+
"description": "Visible page text."
|
|
445
|
+
},
|
|
446
|
+
"html": {
|
|
447
|
+
"type": "string",
|
|
448
|
+
"description": "Page HTML, when required."
|
|
449
|
+
}
|
|
450
|
+
},
|
|
451
|
+
"required": [
|
|
452
|
+
"url"
|
|
453
|
+
]
|
|
454
|
+
},
|
|
455
|
+
"description": "Two or more site pages with title and text for best results."
|
|
456
|
+
}
|
|
457
|
+
},
|
|
458
|
+
"required": [
|
|
459
|
+
"domain",
|
|
460
|
+
"pages"
|
|
461
|
+
]
|
|
462
|
+
}
|
|
463
|
+
}
|
|
464
|
+
]
|
|
465
|
+
}
|