nanoparse-mcp 1.0.9 → 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.
package/CHANGELOG.md ADDED
@@ -0,0 +1,73 @@
1
+ # Changelog
2
+
3
+ All notable changes to nanoparse-mcp will be documented in this file.
4
+
5
+ ---
6
+
7
+ ## [2.0.0] - 2026-08-28
8
+
9
+ ### Changed
10
+
11
+ - Repo restructured as the public home for the **hosted** MCP endpoint
12
+ (`https://nanoparse.app/mcp`): docs + real examples, no client code.
13
+ - Retired v1 local stdio client moved to `archive/v1-local-client/`
14
+ (was `src/`), with a DEPRECATED banner. The client held a wallet private
15
+ key locally (`NANOPARSE_WALLET_KEY`) and is replaced by the hosted
16
+ endpoint's own payment flow.
17
+ - npm package `nanoparse-mcp` deprecated — use the hosted endpoint.
18
+ - README: real Litmus output example (arXiv parse), worked agent
19
+ conversation, cost comparison vs Firecrawl (verified Aug 2026), new
20
+ `examples/` directory (`example-output.json`, `agent-conversation.md`,
21
+ `costs.md`).
22
+ - Price: $0.01 → **$0.005** per parse (2026-10-06), with the README and
23
+ examples realigned.
24
+ - `package.json`: **removed `main`, `bin`, `files: ["dist/"]` and the build
25
+ scripts.** After the client source moved to `archive/v1-local-client/` they
26
+ pointed at `dist/index.js`, which no longer exists — so `npm run build` failed
27
+ and a publish would have shipped a package containing only LICENSE, README and
28
+ package.json. Runtime dependencies (`@modelcontextprotocol/sdk`, `viem`) went
29
+ with the client.
30
+
31
+ ### Published 2026-10-06
32
+
33
+ First publish of the 2.0.0 line. Versions ≤ 1.0.9 ship the retired local stdio
34
+ client and are deprecated on the registry.
35
+
36
+ ## [1.0.9] - 2026-08-23
37
+
38
+ ### Changed
39
+
40
+ - Price: $0.0175 → **$0.01** per parse (tool descriptions + README)
41
+ - README: removed dead card-pack section (`/payments` not live); docs links now point to live pages (`/quickstart`, `/compare`)
42
+ - Server version string synced with package version
43
+
44
+ ## [1.0.8] - 2026-08-23
45
+
46
+ ### Changed
47
+
48
+ - Price: $0.0175 → **$0.01** per parse in `nanoparse_fetch` tool description
49
+
50
+ ## [1.0.7] - 2026-08-17
51
+
52
+ ### Changed
53
+
54
+ - Local stdio client retired — hosted MCP endpoint (`https://nanoparse.app/mcp`) is the only supported integration
55
+ - README rewritten as customer guide to the hosted MCP
56
+
57
+ ## [1.0.2] - 2026-08-02
58
+
59
+ ### Fixed
60
+
61
+ - Added missing `#!/usr/bin/env node` shebang to `dist/index.js`. Plain `npx nanoparse-mcp` now works without requiring `node dist/index.js`. Added `postbuild` script to prepend shebang after `tsc` compilation and set execute permissions.
62
+
63
+ ## [1.0.1] - 2026-08-01
64
+
65
+ ### Changed
66
+
67
+ - Updated `nanoparse_fetch` tool description
68
+
69
+ ## [1.0.0] - 2026-07-26 — Initial release
70
+
71
+ - MCP server with stdio transport, single tool: `nanoparse_fetch(url, debug?)`
72
+ - x402 payment signing via viem (wallet key from `NANOPARSE_WALLET_KEY` env var)
73
+ - Thin client only — browser rendering and content scoring run on NanoParse's infrastructure
package/README.md CHANGED
@@ -1,9 +1,15 @@
1
1
  # NanoParse MCP
2
2
 
3
- **Give your AI agent clean, structured web content.** NanoParse MCP is a hosted Model Context Protocol server at `https://nanoparse.app/mcp` that turns any URL into clean Markdown your agent can actually use — with machine-readable trust signals attached.
3
+ [![npm version](https://img.shields.io/npm/v/nanoparse-mcp)](https://www.npmjs.com/package/nanoparse-mcp)
4
+ [![License: MIT](https://img.shields.io/badge/license-MIT-blue.svg)](LICENSE)
5
+ [![Website](https://img.shields.io/badge/web-nanoparse.app-22D3EE)](https://nanoparse.app)
6
+
7
+ **The easiest way for AI agents to read the web.** NanoParse MCP is a hosted Model Context Protocol server at `https://nanoparse.app/mcp` that turns any URL into clean Markdown your agent can actually use — with machine-readable trust signals attached.
4
8
 
5
9
  No install. No wallet key. No `.env`. Connect once and your agent can read the web.
6
10
 
11
+ **Why agents choose NanoParse over Firecrawl or Jina Reader:** no account, no subscription, no API key. Pay $0.005 per parse via x402 when the free tier runs out. Full JavaScript/SPA rendering, native GFM tables, and Litmus trust signals — built for agents, not humans.
12
+
7
13
  ## Quick start
8
14
 
9
15
  Add this to your MCP client config:
@@ -35,28 +41,69 @@ That's it. Your agent can now fetch pages from inside any MCP-compatible client
35
41
 
36
42
  `nanoparse_status` tells your agent exactly where it stands: free parses remaining, wallet and USDC balance, and whether the next call will succeed without payment. Agents call it before spending.
37
43
 
44
+ ## Real output
45
+
46
+ Every parse returns `markdown` + `metadata` + `litmus`. Example — parsing an arXiv paper (`examples/example-output.json`, complete and unmodified):
47
+
48
+ ```json
49
+ {
50
+ "litmus": {
51
+ "source": { "type": "academic", "authority": 0.85, "rationale": "academic source" },
52
+ "freshness": { "published": null, "stale_warning": "No publish date found — verify independently" },
53
+ "tldr": "Abstract page for arXiv paper 2401.14295: Demystifying Chains, Trees, and Graphs of Thoughts",
54
+ "key_figures": [ { "value": "2,247", "context": "Thu, 25 Jan 2024 16:34:00 UTC (2,247 KB)" } ],
55
+ "content_type": "academic_paper",
56
+ "reading_time": { "minutes": 4 },
57
+ "hedge_language": { "density": "low", "markers_found": 0 },
58
+ "syndication": { "detected": false },
59
+ "paywall": { "detected": false }
60
+ }
61
+ }
62
+ ```
63
+
64
+ The agent learns *before reading a word*: this is an academic source (0.85 authority), no publish date was found (verify independently), here's the one-sentence summary, the key numbers, and there's no paywall or syndication flag. See [`examples/agent-conversation.md`](examples/agent-conversation.md) for a full worked round-trip.
65
+
38
66
  ## Payments
39
67
 
40
- - **First 10 parses per device are free.** No account, no API key, no human required.
41
- - **After that: $0.01 per parse** (flat, no subscriptions) via **x402** — an open micropayment protocol. Your agent's wallet signs the payment automatically. To give your agent a Coinbase wallet, run `npx @coinbase/payments-mcp` and connect it alongside NanoParse.
68
+ - **First 10 parses per network (subnet) are free** — lifetime, shared across your whole network. No account, no API key, no human required.
69
+ - **After that: $0.005 per parse** (flat, no subscriptions) via **x402** — an open micropayment protocol. Your agent's wallet signs the payment automatically. To give your agent a Coinbase wallet, run `npx @coinbase/payments-mcp` and connect it alongside NanoParse.
42
70
 
43
71
  ## How payments work under the hood
44
72
 
45
- When an agent without free quota calls `nanoparse_fetch`, the endpoint responds with an **HTTP 402 — Payment Required** carrying x402 payment instructions. The agent's wallet signs a $0.01 USDC (Base) transfer, the facilitator settles it, and the parse proceeds. The hosted endpoint handles the entire challenge → settlement flow — the agent never needs a private key on your machine.
73
+ When an agent without free quota calls `nanoparse_fetch`, the endpoint responds with an **HTTP 402 — Payment Required** carrying x402 payment instructions. The agent's wallet signs a $0.005 USDC (Base) transfer, the facilitator settles it, and the parse proceeds. The hosted endpoint handles the entire challenge → settlement flow — the agent never needs a private key on your machine.
74
+
75
+ ## Pricing vs Firecrawl
76
+
77
+ | | NanoParse | Firecrawl Hobby |
78
+ |---|---|---|
79
+ | Billing | **$0.005 per parse, flat** | $16/mo subscription, credits expire monthly |
80
+ | 5,000 parses | **$50.00** | $16 base — but ~$145 with JSON/extraction modes (9× credit burn) |
81
+ | Account / API key | **None** | Required |
82
+ | Agent can pay directly (x402) | **Yes** | No |
83
+
84
+ Full math, including when Firecrawl's base rate wins at scale: [`examples/costs.md`](examples/costs.md).
46
85
 
47
86
  ## Example
48
87
 
49
88
  ```
50
- You: Fetch https://www.ft.com/content/... and summarize the argument.
89
+ You: Fetch https://arxiv.org/abs/2401.14295 and summarize the argument.
51
90
 
52
91
  Agent: [calls nanoparse_fetch(url)]
53
- → clean Markdown + Litmus signals
54
- → summarizes from primary content, cites freshness and authority
92
+ → clean Markdown + Litmus (academic, authority 0.85, 4-min read,
93
+ no date found — verify, no paywall)
94
+ → summarizes from primary content, cites authority and freshness
55
95
  ```
56
96
 
57
97
  ## Repository note
58
98
 
59
- The `nanoparse-mcp` npm package previously published here was the first-generation local client, which held a wallet private key and signed x402 payments on your machine. It is retired: the hosted MCP endpoint now handles the full payment flow itself, so the local client is no longer needed. **Use the hosted endpoint above** — it is the current, supported integration.
99
+ The `nanoparse-mcp` npm package and the local stdio client were the
100
+ first-generation integration, which held a wallet private key
101
+ (`NANOPARSE_WALLET_KEY`) and signed x402 payments on your machine. Both are
102
+ **retired**: the hosted endpoint above now handles the full payment flow
103
+ itself, so no local client or wallet key is needed. The retired client code
104
+ is preserved in [`archive/v1-local-client/`](archive/v1-local-client/) for
105
+ history, and the npm package is deprecated. **Use the hosted endpoint** — it
106
+ is the current, supported integration.
60
107
 
61
108
  ## Docs
62
109
 
@@ -0,0 +1,77 @@
1
+ # Worked example: an agent reading an academic paper
2
+
3
+ This is a real `nanoparse_fetch` round-trip against the hosted endpoint
4
+ (`https://nanoparse.app/mcp`), showing what the agent sees and how it reasons
5
+ over the Litmus signals. The full response JSON is in
6
+ [`example-output.json`](./example-output.json).
7
+
8
+ ## The request
9
+
10
+ ```
11
+ You: Fetch https://arxiv.org/abs/2401.14295 and tell me what this paper
12
+ claims, and whether I can trust it as a source.
13
+ ```
14
+
15
+ The agent calls `nanoparse_fetch(url: "https://arxiv.org/abs/2401.14295")`
16
+ and receives clean Markdown plus the Litmus object — before reading a single
17
+ word of the paper.
18
+
19
+ ## What Litmus told the agent, up front
20
+
21
+ ```json
22
+ {
23
+ "litmus": {
24
+ "source": {
25
+ "type": "academic",
26
+ "authority": 0.85,
27
+ "rationale": "academic source"
28
+ },
29
+ "freshness": {
30
+ "published": null,
31
+ "age": "unknown",
32
+ "stale_warning": "No publish date found — verify independently"
33
+ },
34
+ "tldr": "Abstract page for arXiv paper 2401.14295: Demystifying Chains, Trees, and Graphs of Thoughts",
35
+ "key_figures": [
36
+ { "value": "2,247", "context": "Thu, 25 Jan 2024 16:34:00 UTC (2,247 KB)" },
37
+ { "value": "2,290", "context": "Sat, 30 Mar 2024 16:36:33 UTC (2,290 KB)" }
38
+ ],
39
+ "content_type": "academic_paper",
40
+ "reading_time": { "minutes": 4 },
41
+ "hedge_language": { "density": "low", "markers_found": 0, "per_500_words": 0 },
42
+ "syndication": { "detected": false },
43
+ "paywall": { "detected": false }
44
+ }
45
+ }
46
+ ```
47
+
48
+ ## How the agent reasons about it
49
+
50
+ - **Authority 0.85, academic** — high-trust source class. Claims from this
51
+ paper can be weighed accordingly. (Litmus scores the *source class*, not
52
+ the truth of the content — the agent still reads and thinks.)
53
+ - **Freshness warning** — no publish date on the abstract page. The agent
54
+ checks the arXiv listing in the markdown and finds version dates
55
+ (Jan 2024 → Feb 2025), so it cites the paper as "2024, updated 2025"
56
+ instead of guessing.
57
+ - **Key figures** — file sizes are noise, so the agent ignores them; but it
58
+ now knows the paper exists in multiple revisions.
59
+ - **No syndication, no paywall, low hedge density, 4-minute read** — a
60
+ clean, direct academic source. No red flags.
61
+
62
+ ## The agent's answer
63
+
64
+ > The paper **"Demystifying Chains, Trees, and Graphs of Thoughts"**
65
+ > (arXiv 2401.14295) compares chain-of-thought, tree-of-thought, and
66
+ > graph-of-thought prompting across 12 datasets. It claims tree/graph
67
+ > reasoning does not consistently beat plain chain-of-thought, and that
68
+ > success depends on problem type and search strategy.
69
+ >
70
+ > Source note: academic (authority 0.85), first posted Jan 2024 with
71
+ > revisions through Feb 2025. No paywall or syndication flags. Solid
72
+ > source for a research summary; treat its negative claims about
73
+ > tree-of-thought as one study, not settled consensus.
74
+
75
+ That reasoning — *"can I trust this, how fresh is it, what kind of source
76
+ is it, is there anything to verify"* — is exactly what Litmus pre-computes
77
+ so the agent doesn't have to guess from raw text.
@@ -0,0 +1,46 @@
1
+ # Cost comparison: NanoParse vs Firecrawl
2
+
3
+ Pricing verified 2026-08-28. NanoParse: **$0.01 per parse, flat** — no
4
+ subscription, no account, no API key. Litmus signals, full JS/SPA rendering,
5
+ and GFM tables are included in every parse — there are no feature
6
+ multipliers.
7
+
8
+ Firecrawl (published plans, Aug 2026):
9
+
10
+ | Plan | Price | Credits/mo | Base cost/page |
11
+ |---|---|---|---|
12
+ | Free | $0 | 1,000 | — |
13
+ | Hobby | $16/mo | 5,000 | $0.0032 |
14
+ | Standard | $83/mo | 100,000 | $0.00083 |
15
+ | Growth | $333/mo | 500,000 | $0.00067 |
16
+ | Scale | $599/mo | 1,000,000 | $0.0006 |
17
+
18
+ Two things the base rate hides:
19
+
20
+ 1. **Credits do not roll over.** A Hobby subscription is $16 every month —
21
+ use 1,000 of 5,000 credits and you still paid $16. NanoParse bills only
22
+ what you use: $10 for exactly 1,000 parses.
23
+ 2. **Feature multipliers.** JSON extraction and enhanced mode each add
24
+ credits per page (up to 9 credits/page combined). At Hobby that makes a
25
+ fully-featured parse ~$0.029/page — ~3× NanoParse's flat rate. Litmus,
26
+ structured output, and rendering are included in NanoParse's $0.01 with
27
+ no multiplier.
28
+
29
+ ## What a month of 5,000 parses costs
30
+
31
+ | | NanoParse | Firecrawl Hobby |
32
+ |---|---|---|
33
+ | Subscription | None — pay per parse | $16/mo, billed every month |
34
+ | 5,000 plain scrapes | **$50.00** | $16 (base rate) |
35
+ | 5,000 with extraction/features | **$50.00** | ~$145 (9× credit burn) |
36
+ | Use only 1,000 of your quota | **$10.00** | $16 (credits expire) |
37
+ | Account / API key needed | No | Yes |
38
+ | Agent can pay directly (x402) | Yes | No |
39
+
40
+ ## When Firecrawl is genuinely cheaper
41
+
42
+ At scale with plain, credit-cheap scraping, Firecrawl's base rate is lower
43
+ per page — that's their volume bet. NanoParse's bet is different: no
44
+ subscription, no rollover loss, no multiplier, no account, and an agent can
45
+ pay for itself with x402. If you parse occasionally, or in bursts, or via
46
+ agents, NanoParse charges exactly for what you use.
@@ -0,0 +1,101 @@
1
+ {
2
+ "url": "https://arxiv.org/abs/2401.14295",
3
+ "parsed_at": "2026-08-28T00:00:00Z",
4
+ "note": "Real response from POST https://nanoparse.app/fetch (admin round, same public response shape). Markdown truncated to the first 3,000 chars for readability; metadata and litmus are complete and unmodified.",
5
+ "markdown_truncated": true,
6
+ "markdown": "# [2401.14295] Demystifying Chains, Trees, and Graphs of Thoughts\n\n--\n\n \n \n # Computer Science > Computation and Language\n \n\n \n **arXiv:2401.14295 (cs)\n \n\n- \n\n \n \n [Submitted on 25 Jan 2024 ([v1](https://arxiv.org/abs/2401.14295v1)), last revised 1 Apr 2026 (this version, v6)]\n # Title:Demystifying Chains, Trees, and Graphs of Thoughts\n Authors:[Maciej Besta](https://arxiv.org/search/cs?searchtype=author&query=Besta,+M), [Florim Memedi](https://arxiv.org/search/cs?searchtype=author&query=Memedi,+F), [Zhenyu Zhang](https://arxiv.org/search/cs?searchtype=author&query=Zhang,+Z), [Robert Gerstenberger](https://arxiv.org/search/cs?searchtype=author&query=Gerstenberger,+R), [Guangyuan Piao](https://arxiv.org/search/cs?searchtype=author&query=Piao,+G), [Nils Blach](https://arxiv.org/search/cs?searchtype=author&query=Blach,+N), [Piotr Nyczyk](https://arxiv.org/search/cs?searchtype=author&query=Nyczyk,+P), [Marcin Copik](https://arxiv.org/search/cs?searchtype=author&query=Copik,+M), [Grzegorz Kwa\u015bniewski](https://arxiv.org/search/cs?searchtype=author&query=Kwa%C5%9Bniewski,+G), [J\u00fcrgen M\u00fcller](https://arxiv.org/search/cs?searchtype=author&query=M%C3%BCller,+J), [Lukas Gianinazzi](https://arxiv.org/search/cs?searchtype=author&query=Gianinazzi,+L), [Ales Kubicek](https://arxiv.org/search/cs?searchtype=author&query=Kubicek,+A), [Hubert Niewiadomski](https://arxiv.org/search/cs?searchtype=author&query=Niewiadomski,+H), [Aidan O'Mahony](https://arxiv.org/search/cs?searchtype=author&query=O'Mahony,+A), [Onur Mutlu](https://arxiv.org/search/cs?searchtype=author&query=Mutlu,+O), [Torsten Hoefler](https://arxiv.org/search/cs?searchtype=author&query=Hoefler,+T) \n [View PDF](/pdf/2401.14295)\n [HTML (experimental)](https://arxiv.org/html/2401.14295v6)\n\n **\n Abstract:The field of natural language processing (NLP) has witnessed significant progress in recent years, with a notable focus on improving large language models' (LLM) performance through innovative prompting techniques. Among these, prompt engineering coupled with structures has emerged as a promising paradigm, with designs such as Chain-of-Thought, Tree of Thoughts, or Graph of Thoughts, in which the overall LLM reasoning is guided by a structure such as a graph. As illustrated with numerous examples, this paradigm significantly enhances the LLM's capability to solve numerous tasks, ranging from logical or mathematical reasoning to planning or creative writing. To facilitate the understanding of this growing field and pave the way for future developments, we devise a general blueprint for effective and efficient LLM reasoning schemes. For this, we conduct an in-depth analysis of the prompt execution pipeline, clarifying and clearly defining different concepts. We then build the first taxonomy of structure-enhanced LLM reasoning schemes. We focus on identifying fundamental classes of harnessed structures, and we analyze the representations of the",
7
+ "metadata": {
8
+ "title": "[2401.14295] Demystifying Chains, Trees, and Graphs of Thoughts",
9
+ "author": null,
10
+ "description": "Abstract page for arXiv paper 2401.14295: Demystifying Chains, Trees, and Graphs of Thoughts",
11
+ "published": null,
12
+ "image": "/static/browse/0.3.4/images/arxiv-logo-fb.png",
13
+ "site": "arXiv.org",
14
+ "domain": "arxiv.org",
15
+ "wordCount": 806
16
+ },
17
+ "litmus": {
18
+ "source": {
19
+ "type": "academic",
20
+ "authority": 0.85,
21
+ "rationale": "academic source"
22
+ },
23
+ "freshness": {
24
+ "published": null,
25
+ "age": "unknown",
26
+ "stale_warning": "No publish date found \u2014 verify independently",
27
+ "modified": null,
28
+ "has_correction": false,
29
+ "correction_note": null
30
+ },
31
+ "tldr": "Abstract page for arXiv paper 2401.14295: Demystifying Chains, Trees, and Graphs of Thoughts",
32
+ "key_figures": [
33
+ {
34
+ "value": "5%",
35
+ "context": "/search/cs?searchtype=author&query=Kwa%C5%9Bniewski,+G), [J\u00fcrgen M\u00fcller](https://arxiv.org/search/cs?s"
36
+ },
37
+ {
38
+ "value": "3%",
39
+ "context": "rg/search/cs?searchtype=author&query=M%C3%BCller,+J), [Lukas Gianinazzi](https://arxiv.org/search/cs?s"
40
+ },
41
+ {
42
+ "value": "2,247",
43
+ "context": "Thu, 25 Jan 2024 16:34:00 UTC (2,247 KB)** **[[v2]](/abs/2401.14295v2) Sat,"
44
+ },
45
+ {
46
+ "value": "2,290",
47
+ "context": "Sat, 30 Mar 2024 16:33:36 UTC (2,290 KB)** **[[v3]](/abs/2401.14295v3) Fri,"
48
+ },
49
+ {
50
+ "value": "2,297",
51
+ "context": ") Sat, 8 Feb 2025 09:02:41 UTC (2,297 KB)** **[[v5]](/abs/2401.14295v5) Fri,"
52
+ }
53
+ ],
54
+ "structural_trust_score": {
55
+ "level": "medium",
56
+ "trust_factors": [
57
+ "High-authority source",
58
+ "No publish date found \u2014 verify independently"
59
+ ]
60
+ },
61
+ "hedge_language": {
62
+ "density": "low",
63
+ "markers_found": 0,
64
+ "per_500_words": 0
65
+ },
66
+ "content_density": {
67
+ "thin_content": false,
68
+ "substantive_sentence_ratio": 0.7647058823529411
69
+ },
70
+ "syndication": {
71
+ "detected": false,
72
+ "note": null
73
+ },
74
+ "paywall": {
75
+ "detected": false,
76
+ "note": null
77
+ },
78
+ "content_type": "academic_paper",
79
+ "reading_time": {
80
+ "minutes": 4
81
+ },
82
+ "is_archived": {
83
+ "archive_org": true,
84
+ "archive_is": false
85
+ },
86
+ "outbound_authority": {
87
+ "score": 0.54,
88
+ "top_domains": [
89
+ "ui.adsabs.harvard.edu",
90
+ "scholar.google.com",
91
+ "api.semanticscholar.org",
92
+ "info.arxiv.org",
93
+ "core.ac.uk"
94
+ ]
95
+ },
96
+ "boilerplate_ratio": {
97
+ "ratio": 0.08,
98
+ "confidence": "high"
99
+ }
100
+ }
101
+ }
package/package.json CHANGED
@@ -1,20 +1,7 @@
1
1
  {
2
2
  "name": "nanoparse-mcp",
3
- "version": "1.0.9",
4
- "description": "MCP client for NanoParse — pay-per-parse web content extraction for AI agents",
5
- "type": "module",
6
- "main": "dist/index.js",
7
- "bin": {
8
- "nanoparse-mcp": "dist/index.js"
9
- },
10
- "files": [
11
- "dist/"
12
- ],
13
- "scripts": {
14
- "build": "tsc",
15
- "postbuild": "node -e \"var f='dist/index.js';var c=require('fs').readFileSync(f,'utf8');require('fs').writeFileSync(f,'#!/usr/bin/env node\\n'+c);require('fs').chmodSync(f,'755')\"",
16
- "prepublishOnly": "npm run build"
17
- },
3
+ "version": "2.0.0",
4
+ "description": "NanoParse MCP — hosted Model Context Protocol server for AI agents. Any URL becomes clean Markdown with attribution signals. $0.005 per page via x402, no account or API key.",
18
5
  "keywords": [
19
6
  "mcp",
20
7
  "model-context-protocol",
@@ -22,19 +9,28 @@
22
9
  "web-scraping",
23
10
  "markdown",
24
11
  "x402",
25
- "ai-agent"
12
+ "ai-agent",
13
+ "litmus"
26
14
  ],
15
+ "license": "MIT",
16
+ "homepage": "https://nanoparse.app",
27
17
  "repository": {
28
18
  "type": "git",
29
19
  "url": "https://github.com/nanoparse-dev/nanoparse-mcp"
30
20
  },
31
- "license": "MIT",
32
- "dependencies": {
33
- "@modelcontextprotocol/sdk": "^1.0.0",
34
- "viem": "^2.55.8"
21
+ "bugs": {
22
+ "url": "https://github.com/nanoparse-dev/nanoparse-mcp/issues"
23
+ },
24
+ "files": [
25
+ "README.md",
26
+ "LICENSE",
27
+ "CHANGELOG.md",
28
+ "examples/"
29
+ ],
30
+ "engines": {
31
+ "node": ">=18"
35
32
  },
36
- "devDependencies": {
37
- "@types/node": "^22.0.0",
38
- "typescript": "^5.5.0"
33
+ "publishConfig": {
34
+ "access": "public"
39
35
  }
40
36
  }
package/dist/fetch.d.ts DELETED
@@ -1,34 +0,0 @@
1
- interface NanoParseResponse {
2
- success: boolean;
3
- url: string;
4
- markdown: string;
5
- metadata: {
6
- title?: string;
7
- author?: string;
8
- description?: string;
9
- published?: string;
10
- image?: string;
11
- favicon?: string;
12
- site?: string;
13
- domain?: string;
14
- wordCount?: number;
15
- language?: string;
16
- };
17
- schemaOrgData?: Record<string, unknown>;
18
- freeCallsRemaining?: number;
19
- debug?: {
20
- contentSelector?: string;
21
- metadataSource?: string;
22
- cleaning?: {
23
- blocksRemoved: number;
24
- blocksKept: number;
25
- };
26
- timing?: {
27
- metadataFetchMs: number;
28
- browserRenderMs: number;
29
- };
30
- };
31
- }
32
- export declare function fetchPage(url: string, debug?: boolean): Promise<NanoParseResponse>;
33
- export {};
34
- //# sourceMappingURL=fetch.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"fetch.d.ts","sourceRoot":"","sources":["../src/fetch.ts"],"names":[],"mappings":"AAeA,UAAU,iBAAiB;IACzB,OAAO,EAAE,OAAO,CAAC;IACjB,GAAG,EAAE,MAAM,CAAC;IACZ,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE;QACR,KAAK,CAAC,EAAE,MAAM,CAAC;QACf,MAAM,CAAC,EAAE,MAAM,CAAC;QAChB,WAAW,CAAC,EAAE,MAAM,CAAC;QACrB,SAAS,CAAC,EAAE,MAAM,CAAC;QACnB,KAAK,CAAC,EAAE,MAAM,CAAC;QACf,OAAO,CAAC,EAAE,MAAM,CAAC;QACjB,IAAI,CAAC,EAAE,MAAM,CAAC;QACd,MAAM,CAAC,EAAE,MAAM,CAAC;QAChB,SAAS,CAAC,EAAE,MAAM,CAAC;QACnB,QAAQ,CAAC,EAAE,MAAM,CAAC;KACnB,CAAC;IACF,aAAa,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IACxC,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,KAAK,CAAC,EAAE;QACN,eAAe,CAAC,EAAE,MAAM,CAAC;QACzB,cAAc,CAAC,EAAE,MAAM,CAAC;QACxB,QAAQ,CAAC,EAAE;YAAE,aAAa,EAAE,MAAM,CAAC;YAAC,UAAU,EAAE,MAAM,CAAA;SAAE,CAAC;QACzD,MAAM,CAAC,EAAE;YAAE,eAAe,EAAE,MAAM,CAAC;YAAC,eAAe,EAAE,MAAM,CAAA;SAAE,CAAC;KAC/D,CAAC;CACH;AAED,wBAAsB,SAAS,CAC7B,GAAG,EAAE,MAAM,EACX,KAAK,UAAQ,GACZ,OAAO,CAAC,iBAAiB,CAAC,CA2C5B"}
package/dist/fetch.js DELETED
@@ -1,37 +0,0 @@
1
- import { signPayment } from "./payment.js";
2
- const FETCH_ENDPOINT = "https://nanoparse.app/fetch";
3
- export async function fetchPage(url, debug = false) {
4
- const body = { url };
5
- if (debug)
6
- body.debug = true;
7
- // First attempt — may return 402 if payment is required
8
- let res = await fetch(FETCH_ENDPOINT, {
9
- method: "POST",
10
- headers: { "Content-Type": "application/json" },
11
- body: JSON.stringify(body),
12
- });
13
- // Handle x402 payment flow
14
- if (res.status === 402) {
15
- const paymentTerms = await res.json();
16
- if (paymentTerms.error !== "payment_required") {
17
- throw new Error(`Unexpected 402 response: ${JSON.stringify(paymentTerms)}`);
18
- }
19
- const signature = await signPayment(paymentTerms);
20
- // Retry with payment signature
21
- res = await fetch(FETCH_ENDPOINT, {
22
- method: "POST",
23
- headers: {
24
- "Content-Type": "application/json",
25
- "Payment-Signature": signature,
26
- },
27
- body: JSON.stringify(body),
28
- });
29
- }
30
- if (!res.ok) {
31
- const errorText = await res.text().catch(() => "Unknown error");
32
- throw new Error(`NanoParse API returned ${res.status}: ${errorText}`);
33
- }
34
- const data = await res.json();
35
- return data;
36
- }
37
- //# sourceMappingURL=fetch.js.map
package/dist/fetch.js.map DELETED
@@ -1 +0,0 @@
1
- {"version":3,"file":"fetch.js","sourceRoot":"","sources":["../src/fetch.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,cAAc,CAAC;AAE3C,MAAM,cAAc,GAAG,6BAA6B,CAAC;AAuCrD,MAAM,CAAC,KAAK,UAAU,SAAS,CAC7B,GAAW,EACX,KAAK,GAAG,KAAK;IAEb,MAAM,IAAI,GAA4B,EAAE,GAAG,EAAE,CAAC;IAC9C,IAAI,KAAK;QAAE,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC;IAE7B,wDAAwD;IACxD,IAAI,GAAG,GAAG,MAAM,KAAK,CAAC,cAAc,EAAE;QACpC,MAAM,EAAE,MAAM;QACd,OAAO,EAAE,EAAE,cAAc,EAAE,kBAAkB,EAAE;QAC/C,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC;KAC3B,CAAC,CAAC;IAEH,2BAA2B;IAC3B,IAAI,GAAG,CAAC,MAAM,KAAK,GAAG,EAAE,CAAC;QACvB,MAAM,YAAY,GAAqB,MAAM,GAAG,CAAC,IAAI,EAAE,CAAC;QAExD,IAAI,YAAY,CAAC,KAAK,KAAK,kBAAkB,EAAE,CAAC;YAC9C,MAAM,IAAI,KAAK,CACb,4BAA4B,IAAI,CAAC,SAAS,CAAC,YAAY,CAAC,EAAE,CAC3D,CAAC;QACJ,CAAC;QAED,MAAM,SAAS,GAAG,MAAM,WAAW,CAAC,YAAY,CAAC,CAAC;QAElD,+BAA+B;QAC/B,GAAG,GAAG,MAAM,KAAK,CAAC,cAAc,EAAE;YAChC,MAAM,EAAE,MAAM;YACd,OAAO,EAAE;gBACP,cAAc,EAAE,kBAAkB;gBAClC,mBAAmB,EAAE,SAAS;aAC/B;YACD,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC;SAC3B,CAAC,CAAC;IACL,CAAC;IAED,IAAI,CAAC,GAAG,CAAC,EAAE,EAAE,CAAC;QACZ,MAAM,SAAS,GAAG,MAAM,GAAG,CAAC,IAAI,EAAE,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,eAAe,CAAC,CAAC;QAChE,MAAM,IAAI,KAAK,CACb,0BAA0B,GAAG,CAAC,MAAM,KAAK,SAAS,EAAE,CACrD,CAAC;IACJ,CAAC;IAED,MAAM,IAAI,GAAsB,MAAM,GAAG,CAAC,IAAI,EAAE,CAAC;IACjD,OAAO,IAAI,CAAC;AACd,CAAC"}
package/dist/index.d.ts DELETED
@@ -1,2 +0,0 @@
1
- export {};
2
- //# sourceMappingURL=index.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":""}
package/dist/index.js DELETED
@@ -1,80 +0,0 @@
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 { fetchPage } from "./fetch.js";
6
- const server = new Server({
7
- name: "nanoparse-mcp",
8
- version: "1.0.9",
9
- }, {
10
- capabilities: {
11
- tools: {},
12
- },
13
- });
14
- server.setRequestHandler(ListToolsRequestSchema, async () => ({
15
- tools: [
16
- {
17
- name: "nanoparse_fetch",
18
- description: "Fetch a web page and return clean, structured Markdown with metadata. " +
19
- "First 10 parses free per device. After that, pay $0.01 USDC on Base via x402. " +
20
- "No account or API key required.",
21
- inputSchema: {
22
- type: "object",
23
- properties: {
24
- url: {
25
- type: "string",
26
- description: "The URL to fetch and convert to Markdown",
27
- },
28
- debug: {
29
- type: "boolean",
30
- description: "If true, include extraction diagnostics in the response (contentSelector, metadataSource, cleaning stats, timing)",
31
- default: false,
32
- },
33
- },
34
- required: ["url"],
35
- },
36
- },
37
- ],
38
- }));
39
- server.setRequestHandler(CallToolRequestSchema, async (request) => {
40
- if (request.params.name !== "nanoparse_fetch") {
41
- throw new Error(`Unknown tool: ${request.params.name}`);
42
- }
43
- const args = request.params.arguments;
44
- if (!args.url || typeof args.url !== "string") {
45
- throw new Error('Missing required parameter: "url"');
46
- }
47
- try {
48
- const result = await fetchPage(args.url, args.debug ?? false);
49
- return {
50
- content: [
51
- {
52
- type: "text",
53
- text: result.markdown,
54
- },
55
- ],
56
- structuredContent: result,
57
- };
58
- }
59
- catch (err) {
60
- const message = err instanceof Error ? err.message : String(err);
61
- return {
62
- content: [
63
- {
64
- type: "text",
65
- text: `NanoParse error: ${message}`,
66
- },
67
- ],
68
- isError: true,
69
- };
70
- }
71
- });
72
- async function main() {
73
- const transport = new StdioServerTransport();
74
- await server.connect(transport);
75
- }
76
- main().catch((err) => {
77
- console.error("nanoparse-mcp server failed to start:", String(err));
78
- process.exit(1);
79
- });
80
- //# sourceMappingURL=index.js.map
package/dist/index.js.map DELETED
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,2CAA2C,CAAC;AACnE,OAAO,EAAE,oBAAoB,EAAE,MAAM,2CAA2C,CAAC;AACjF,OAAO,EACL,qBAAqB,EACrB,sBAAsB,GACvB,MAAM,oCAAoC,CAAC;AAC5C,OAAO,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAEvC,MAAM,MAAM,GAAG,IAAI,MAAM,CACvB;IACE,IAAI,EAAE,eAAe;IACrB,OAAO,EAAE,OAAO;CACjB,EACD;IACE,YAAY,EAAE;QACZ,KAAK,EAAE,EAAE;KACV;CACF,CACF,CAAC;AAEF,MAAM,CAAC,iBAAiB,CAAC,sBAAsB,EAAE,KAAK,IAAI,EAAE,CAAC,CAAC;IAC5D,KAAK,EAAE;QACL;YACE,IAAI,EAAE,iBAAiB;YACvB,WAAW,EACT,wEAAwE;gBACxE,gFAAgF;gBAChF,iCAAiC;YACnC,WAAW,EAAE;gBACX,IAAI,EAAE,QAAQ;gBACd,UAAU,EAAE;oBACV,GAAG,EAAE;wBACH,IAAI,EAAE,QAAQ;wBACd,WAAW,EAAE,0CAA0C;qBACxD;oBACD,KAAK,EAAE;wBACL,IAAI,EAAE,SAAS;wBACf,WAAW,EACT,mHAAmH;wBACrH,OAAO,EAAE,KAAK;qBACf;iBACF;gBACD,QAAQ,EAAE,CAAC,KAAK,CAAC;aAClB;SACF;KACF;CACF,CAAC,CAAC,CAAC;AAEJ,MAAM,CAAC,iBAAiB,CAAC,qBAAqB,EAAE,KAAK,EAAE,OAAO,EAAE,EAAE;IAChE,IAAI,OAAO,CAAC,MAAM,CAAC,IAAI,KAAK,iBAAiB,EAAE,CAAC;QAC9C,MAAM,IAAI,KAAK,CAAC,iBAAiB,OAAO,CAAC,MAAM,CAAC,IAAI,EAAE,CAAC,CAAC;IAC1D,CAAC;IAED,MAAM,IAAI,GAAG,OAAO,CAAC,MAAM,CAAC,SAG3B,CAAC;IAEF,IAAI,CAAC,IAAI,CAAC,GAAG,IAAI,OAAO,IAAI,CAAC,GAAG,KAAK,QAAQ,EAAE,CAAC;QAC9C,MAAM,IAAI,KAAK,CAAC,mCAAmC,CAAC,CAAC;IACvD,CAAC;IAED,IAAI,CAAC;QACH,MAAM,MAAM,GAAG,MAAM,SAAS,CAAC,IAAI,CAAC,GAAG,EAAE,IAAI,CAAC,KAAK,IAAI,KAAK,CAAC,CAAC;QAE9D,OAAO;YACL,OAAO,EAAE;gBACP;oBACE,IAAI,EAAE,MAAM;oBACZ,IAAI,EAAE,MAAM,CAAC,QAAQ;iBACtB;aACF;YACD,iBAAiB,EAAE,MAAM;SAC1B,CAAC;IACJ,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,MAAM,OAAO,GAAG,GAAG,YAAY,KAAK,CAAC,CAAC,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC;QACjE,OAAO;YACL,OAAO,EAAE;gBACP;oBACE,IAAI,EAAE,MAAM;oBACZ,IAAI,EAAE,oBAAoB,OAAO,EAAE;iBACpC;aACF;YACD,OAAO,EAAE,IAAI;SACd,CAAC;IACJ,CAAC;AACH,CAAC,CAAC,CAAC;AAEH,KAAK,UAAU,IAAI;IACjB,MAAM,SAAS,GAAG,IAAI,oBAAoB,EAAE,CAAC;IAC7C,MAAM,MAAM,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC;AAClC,CAAC;AAED,IAAI,EAAE,CAAC,KAAK,CAAC,CAAC,GAAG,EAAE,EAAE;IACnB,OAAO,CAAC,KAAK,CAAC,uCAAuC,EAAE,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC;IACpE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC,CAAC,CAAC"}
package/dist/payment.d.ts DELETED
@@ -1,30 +0,0 @@
1
- /**
2
- * Payment terms returned by NanoParse in a 402 response body.
3
- * These are the fields the client must sign before retrying.
4
- */
5
- interface X402PaymentTerms {
6
- error: "payment_required";
7
- scheme: "exact";
8
- network: string;
9
- asset: string;
10
- amount: string;
11
- payTo: string;
12
- free_calls_used: number;
13
- free_calls_limit: number;
14
- }
15
- /**
16
- * Sign x402 payment terms using the wallet key and return the
17
- * signature for the Payment-Signature header.
18
- *
19
- * The signature is created by signing a JSON-serialized
20
- * representation of the payment terms with the wallet's private key.
21
- * The x402 facilitator at x402.org verifies and settles the
22
- * transaction — the client never constructs raw blockchain
23
- * transactions directly.
24
- *
25
- * The wallet key is read from NANOPARSE_WALLET_KEY and is never
26
- * logged, printed, or included in error output.
27
- */
28
- export declare function signPayment(paymentTerms: X402PaymentTerms): Promise<string>;
29
- export {};
30
- //# sourceMappingURL=payment.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"payment.d.ts","sourceRoot":"","sources":["../src/payment.ts"],"names":[],"mappings":"AAkBA;;;GAGG;AACH,UAAU,gBAAgB;IACxB,KAAK,EAAE,kBAAkB,CAAC;IAC1B,MAAM,EAAE,OAAO,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;IACf,KAAK,EAAE,MAAM,CAAC;IACd,eAAe,EAAE,MAAM,CAAC;IACxB,gBAAgB,EAAE,MAAM,CAAC;CAC1B;AAED;;;;;;;;;;;;GAYG;AACH,wBAAsB,WAAW,CAC/B,YAAY,EAAE,gBAAgB,GAC7B,OAAO,CAAC,MAAM,CAAC,CA6BjB"}
package/dist/payment.js DELETED
@@ -1,51 +0,0 @@
1
- import { privateKeyToAccount } from "viem/accounts";
2
- import { createWalletClient, http } from "viem";
3
- import { base } from "viem/chains";
4
- function getWalletKey() {
5
- const key = process.env.NANOPARSE_WALLET_KEY;
6
- if (!key) {
7
- throw new Error("NANOPARSE_WALLET_KEY environment variable is not set. " +
8
- "Copy .env.example to .env and add your Base wallet private key.");
9
- }
10
- if (!key.startsWith("0x")) {
11
- return `0x${key}`;
12
- }
13
- return key;
14
- }
15
- /**
16
- * Sign x402 payment terms using the wallet key and return the
17
- * signature for the Payment-Signature header.
18
- *
19
- * The signature is created by signing a JSON-serialized
20
- * representation of the payment terms with the wallet's private key.
21
- * The x402 facilitator at x402.org verifies and settles the
22
- * transaction — the client never constructs raw blockchain
23
- * transactions directly.
24
- *
25
- * The wallet key is read from NANOPARSE_WALLET_KEY and is never
26
- * logged, printed, or included in error output.
27
- */
28
- export async function signPayment(paymentTerms) {
29
- const key = getWalletKey();
30
- const account = privateKeyToAccount(key);
31
- const client = createWalletClient({
32
- account,
33
- chain: base,
34
- transport: http(),
35
- });
36
- // Serialize the payment terms deterministically for signing.
37
- // The x402 facilitator expects a JSON payload with sorted keys.
38
- const payload = JSON.stringify({
39
- scheme: paymentTerms.scheme,
40
- network: paymentTerms.network,
41
- asset: paymentTerms.asset,
42
- amount: paymentTerms.amount,
43
- payTo: paymentTerms.payTo,
44
- }, Object.keys(paymentTerms).sort());
45
- const signature = await client.signMessage({
46
- account,
47
- message: payload,
48
- });
49
- return signature;
50
- }
51
- //# sourceMappingURL=payment.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"payment.js","sourceRoot":"","sources":["../src/payment.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,mBAAmB,EAAE,MAAM,eAAe,CAAC;AACpD,OAAO,EAAE,kBAAkB,EAAE,IAAI,EAAY,MAAM,MAAM,CAAC;AAC1D,OAAO,EAAE,IAAI,EAAE,MAAM,aAAa,CAAC;AAEnC,SAAS,YAAY;IACnB,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,CAAC,oBAAoB,CAAC;IAC7C,IAAI,CAAC,GAAG,EAAE,CAAC;QACT,MAAM,IAAI,KAAK,CACb,wDAAwD;YACtD,iEAAiE,CACpE,CAAC;IACJ,CAAC;IACD,IAAI,CAAC,GAAG,CAAC,UAAU,CAAC,IAAI,CAAC,EAAE,CAAC;QAC1B,OAAO,KAAK,GAAG,EAAS,CAAC;IAC3B,CAAC;IACD,OAAO,GAAU,CAAC;AACpB,CAAC;AAiBD;;;;;;;;;;;;GAYG;AACH,MAAM,CAAC,KAAK,UAAU,WAAW,CAC/B,YAA8B;IAE9B,MAAM,GAAG,GAAG,YAAY,EAAE,CAAC;IAC3B,MAAM,OAAO,GAAG,mBAAmB,CAAC,GAAG,CAAC,CAAC;IAEzC,MAAM,MAAM,GAAG,kBAAkB,CAAC;QAChC,OAAO;QACP,KAAK,EAAE,IAAI;QACX,SAAS,EAAE,IAAI,EAAE;KAClB,CAAC,CAAC;IAEH,6DAA6D;IAC7D,gEAAgE;IAChE,MAAM,OAAO,GAAG,IAAI,CAAC,SAAS,CAC5B;QACE,MAAM,EAAE,YAAY,CAAC,MAAM;QAC3B,OAAO,EAAE,YAAY,CAAC,OAAO;QAC7B,KAAK,EAAE,YAAY,CAAC,KAAK;QACzB,MAAM,EAAE,YAAY,CAAC,MAAM;QAC3B,KAAK,EAAE,YAAY,CAAC,KAAK;KAC1B,EACD,MAAM,CAAC,IAAI,CAAC,YAAY,CAAC,CAAC,IAAI,EAAE,CACjC,CAAC;IAEF,MAAM,SAAS,GAAG,MAAM,MAAM,CAAC,WAAW,CAAC;QACzC,OAAO;QACP,OAAO,EAAE,OAAO;KACjB,CAAC,CAAC;IAEH,OAAO,SAAS,CAAC;AACnB,CAAC"}