@aiquants/html-to-markdown 0.1.4 → 0.1.6

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 (60) hide show
  1. package/README.md +100 -18
  2. package/dist/{core-CVMYjtlI.cjs → core-D2dlEt1l.cjs} +1 -1
  3. package/dist/{core-DOzMLPij.js → core-DU_246Q7.js} +52 -14
  4. package/dist/index.cjs +1 -1
  5. package/dist/index.js +8 -2
  6. package/dist/main.cjs +1 -1
  7. package/dist/main.js +1 -1
  8. package/dist/mcp-server-CpmnW1p8.js +283 -0
  9. package/dist/mcp-server-D4Mj1IQ9.cjs +1 -0
  10. package/dist/mcp-server-streamable-Bu7QAr3W.cjs +1 -0
  11. package/dist/mcp-server-streamable-CQD5zK30.js +7538 -0
  12. package/dist/mcp-streamable.cjs +2 -0
  13. package/dist/mcp-streamable.js +6 -0
  14. package/dist/mcp.cjs +2 -0
  15. package/dist/mcp.js +13 -0
  16. package/dist/src/core.d.ts +4 -4
  17. package/dist/src/index.d.ts +2 -0
  18. package/dist/src/mcp-server-streamable.d.ts +74 -0
  19. package/dist/src/mcp-server.d.ts +57 -0
  20. package/dist/src/mcp-streamable.d.ts +6 -0
  21. package/dist/src/mcp.d.ts +6 -0
  22. package/dist/src/types.d.ts +5 -0
  23. package/dist/src/version.d.ts +9 -0
  24. package/dist/tests/core-unified.test.d.ts +5 -0
  25. package/dist/tests/coverage-complete.test.d.ts +5 -0
  26. package/dist/tests/mcp-unified.test.d.ts +5 -0
  27. package/dist/tests/plugins-unified.test.d.ts +5 -0
  28. package/dist/tests/test-client.d.ts +4 -0
  29. package/dist/version-BRVBmpor.js +11318 -0
  30. package/dist/version-DTaUKNBS.cjs +1 -0
  31. package/mcp.json +14 -0
  32. package/package.json +27 -10
  33. package/dist/tests/100-percent-final.test.d.ts +0 -1
  34. package/dist/tests/absolute-final-coverage.test.d.ts +0 -1
  35. package/dist/tests/browser-100.test.d.ts +0 -1
  36. package/dist/tests/browser-coverage.test.d.ts +0 -1
  37. package/dist/tests/browser.test.d.ts +0 -1
  38. package/dist/tests/cli.test.d.ts +0 -1
  39. package/dist/tests/converter-coverage.test.d.ts +0 -1
  40. package/dist/tests/converter.test.d.ts +0 -1
  41. package/dist/tests/core.test.d.ts +0 -1
  42. package/dist/tests/coverage-edge-cases.test.d.ts +0 -1
  43. package/dist/tests/direct-coverage.test.d.ts +0 -1
  44. package/dist/tests/final-100-percent.test.d.ts +0 -1
  45. package/dist/tests/final-coverage.test.d.ts +0 -1
  46. package/dist/tests/i18n.test.d.ts +0 -1
  47. package/dist/tests/index.test.d.ts +0 -1
  48. package/dist/tests/line-70-coverage.test.d.ts +0 -1
  49. package/dist/tests/main.test.d.ts +0 -1
  50. package/dist/tests/plugins.test.d.ts +0 -1
  51. package/dist/tests/readme-usage.test.d.ts +0 -1
  52. package/dist/tests/rehype-absolute-links-coverage.test.d.ts +0 -1
  53. package/dist/tests/rehype-absolute-links.test.d.ts +0 -1
  54. package/dist/tests/rehype-named-anchors.test.d.ts +0 -1
  55. package/dist/tests/rehype-sanitize-html-coverage.test.d.ts +0 -1
  56. package/dist/tests/rehype-sanitize-html.test.d.ts +0 -1
  57. package/dist/tests/rehype-wikipedia-footnotes.test.d.ts +0 -1
  58. package/dist/tests/types.test.d.ts +0 -1
  59. package/dist/tests/ultimate-coverage.test.d.ts +0 -1
  60. /package/dist/tests/{100-percent-coverage.test.d.ts → entry-points-error.test.d.ts} +0 -0
@@ -19494,9 +19494,39 @@ function bail(error) {
19494
19494
  throw error;
19495
19495
  }
19496
19496
  }
19497
+ var commonjsGlobal = typeof globalThis !== "undefined" ? globalThis : typeof window !== "undefined" ? window : typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : {};
19497
19498
  function getDefaultExportFromCjs(x) {
19498
19499
  return x && x.__esModule && Object.prototype.hasOwnProperty.call(x, "default") ? x["default"] : x;
19499
19500
  }
19501
+ function getAugmentedNamespace(n) {
19502
+ if (Object.prototype.hasOwnProperty.call(n, "__esModule")) return n;
19503
+ var f = n.default;
19504
+ if (typeof f == "function") {
19505
+ var a2 = function a3() {
19506
+ var isInstance = false;
19507
+ try {
19508
+ isInstance = this instanceof a3;
19509
+ } catch {
19510
+ }
19511
+ if (isInstance) {
19512
+ return Reflect.construct(f, arguments, this.constructor);
19513
+ }
19514
+ return f.apply(this, arguments);
19515
+ };
19516
+ a2.prototype = f.prototype;
19517
+ } else a2 = {};
19518
+ Object.defineProperty(a2, "__esModule", { value: true });
19519
+ Object.keys(n).forEach(function(k) {
19520
+ var d = Object.getOwnPropertyDescriptor(n, k);
19521
+ Object.defineProperty(a2, k, d.get ? d : {
19522
+ enumerable: true,
19523
+ get: function() {
19524
+ return n[k];
19525
+ }
19526
+ });
19527
+ });
19528
+ return a2;
19529
+ }
19500
19530
  var extend$1;
19501
19531
  var hasRequiredExtend;
19502
19532
  function requireExtend() {
@@ -20662,11 +20692,7 @@ const convertHtmlToMarkdown = async (html2, baseUrl, locale) => {
20662
20692
  if (children.length === 0) {
20663
20693
  return { type: "html", value: `<span id="${String(id)}"></span>` };
20664
20694
  }
20665
- return [
20666
- { type: "html", value: `<span id="${String(id)}">` },
20667
- ...children,
20668
- { type: "html", value: "</span>" }
20669
- ];
20695
+ return [{ type: "html", value: `<span id="${String(id)}">` }, ...children, { type: "html", value: "</span>" }];
20670
20696
  }
20671
20697
  return state.all(node2);
20672
20698
  },
@@ -20760,23 +20786,35 @@ const convertHtmlToMarkdown = async (html2, baseUrl, locale) => {
20760
20786
  console.log(getMessage(locale, "convert_success"));
20761
20787
  return correctedMarkdown;
20762
20788
  };
20763
- const htmlToMarkdown = async (url, options = {}) => {
20764
- const { locale = "en-US" } = options;
20789
+ const htmlToMarkdown = async (urlOrHtml, options = {}) => {
20790
+ const { locale = "en-US", htmlContent } = options;
20765
20791
  try {
20766
- new URL(url);
20767
- const htmlContent = await getHtmlWithPlaywright(url, locale);
20768
- if (!htmlContent) {
20769
- console.error(`No HTML content found for URL: ${url}`);
20792
+ let htmlContentToProcess;
20793
+ let sourceUrl;
20794
+ if (htmlContent) {
20795
+ htmlContentToProcess = htmlContent;
20796
+ sourceUrl = urlOrHtml || "direct-html-input";
20797
+ } else {
20798
+ new URL(urlOrHtml);
20799
+ htmlContentToProcess = await getHtmlWithPlaywright(urlOrHtml, locale);
20800
+ sourceUrl = urlOrHtml;
20801
+ }
20802
+ if (!htmlContentToProcess) {
20803
+ console.error(`No HTML content found for source: ${sourceUrl}`);
20770
20804
  return { html: "", markdown: "" };
20771
20805
  }
20772
- const markdown = await convertHtmlToMarkdown(htmlContent, url, locale);
20773
- return { html: htmlContent, markdown };
20806
+ const markdown = await convertHtmlToMarkdown(htmlContentToProcess, sourceUrl, locale);
20807
+ return { html: htmlContentToProcess, markdown };
20774
20808
  } catch (error) {
20775
- console.error(`An error occurred during the conversion process for URL: ${url}`, error);
20809
+ const source = htmlContent ? "HTML string" : `URL: ${urlOrHtml}`;
20810
+ console.error(`An error occurred during the conversion process for ${source}`, error);
20776
20811
  return { html: "", markdown: "" };
20777
20812
  }
20778
20813
  };
20779
20814
  export {
20815
+ getAugmentedNamespace as a,
20816
+ getDefaultExportFromCjs as b,
20817
+ commonjsGlobal as c,
20780
20818
  getMessage as g,
20781
20819
  htmlToMarkdown as h
20782
20820
  };
package/dist/index.cjs CHANGED
@@ -1 +1 @@
1
- const e=new(require("happy-dom").Window);Object.assign(global,{document:e.document,window:e,self:e}),Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const o=require("./core-CVMYjtlI.cjs");exports.getMessage=o.getMessage,exports.htmlToMarkdown=o.htmlToMarkdown;
1
+ const e=new(require("happy-dom").Window);Object.assign(global,{document:e.document,window:e,self:e}),Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const r=require("./core-D2dlEt1l.cjs"),t=require("./mcp-server-D4Mj1IQ9.cjs"),c=require("./mcp-server-streamable-Bu7QAr3W.cjs");exports.getMessage=r.getMessage,exports.htmlToMarkdown=r.htmlToMarkdown,exports.createMcpServer=t.createMcpServer,exports.runMcpServer=t.runMcpServer,exports.createStreamableMcpServer=c.createStreamableMcpServer,exports.runStreamableMcpServer=c.runStreamableMcpServer;
package/dist/index.js CHANGED
@@ -5,8 +5,14 @@ Object.assign(global, {
5
5
  window,
6
6
  self: window
7
7
  });
8
- import { g, h } from "./core-DOzMLPij.js";
8
+ import { g, h } from "./core-DU_246Q7.js";
9
+ import { c, r } from "./mcp-server-CpmnW1p8.js";
10
+ import { c as c2, r as r2 } from "./mcp-server-streamable-CQD5zK30.js";
9
11
  export {
12
+ c as createMcpServer,
13
+ c2 as createStreamableMcpServer,
10
14
  g as getMessage,
11
- h as htmlToMarkdown
15
+ h as htmlToMarkdown,
16
+ r as runMcpServer,
17
+ r2 as runStreamableMcpServer
12
18
  };
package/dist/main.cjs CHANGED
@@ -1,2 +1,2 @@
1
1
  #!/usr/bin/env node
2
- Object.create,Object.defineProperty,Object.getOwnPropertyDescriptor,Object.getOwnPropertyNames,Object.getPrototypeOf,Object.prototype.hasOwnProperty;const e=new(require("happy-dom").Window);Object.assign(global,{document:e.document,window:e,self:e});const t=require("./core-CVMYjtlI.cjs");var r="undefined"!=typeof document?document.currentScript:null;(async()=>{(("undefined"==typeof document?require("url").pathToFileURL(__filename).href:r&&"SCRIPT"===r.tagName.toUpperCase()&&r.src||new URL("main.cjs",document.baseURI).href).endsWith(process.argv[1])||process.argv[1]&&process.argv[1].includes("vite-node"))&&(async()=>{const e=(await import("yargs-parser")).default,r=await import("node:fs"),o=await import("node:path"),c=e(process.argv.slice(2),{string:["locale","output"],alias:{output:["o"]},default:{locale:"en-US"}}),s=c._[0],n=c.locale,a=c.output;s||process.exit(1);try{new URL(s)}catch(i){process.exit(1)}try{const{markdown:e,html:c}=await t.htmlToMarkdown(s,{locale:n});let i;if(a){i=o.resolve(process.cwd(),a);const e=o.dirname(i);r.existsSync(e)||r.mkdirSync(e,{recursive:!0})}else{const e=`${s.replace(/https?:\/\//,"").replace(/[^a-zA-Z0-9]/g,"_")}_${Date.now()}.md`,t=o.join(process.cwd(),".outputs","raw");r.existsSync(t)||r.mkdirSync(t,{recursive:!0}),i=o.join(t,e)}r.writeFileSync(i,e);const p=o.parse(i),l=o.join(p.dir,`${p.name}.html`);r.writeFileSync(l,c)}catch(i){process.exit(1)}})()})();
2
+ Object.create,Object.defineProperty,Object.getOwnPropertyDescriptor,Object.getOwnPropertyNames,Object.getPrototypeOf,Object.prototype.hasOwnProperty;const e=new(require("happy-dom").Window);Object.assign(global,{document:e.document,window:e,self:e});const t=require("./core-D2dlEt1l.cjs");var r="undefined"!=typeof document?document.currentScript:null;(async()=>{(("undefined"==typeof document?require("url").pathToFileURL(__filename).href:r&&"SCRIPT"===r.tagName.toUpperCase()&&r.src||new URL("main.cjs",document.baseURI).href).endsWith(process.argv[1])||process.argv[1]&&process.argv[1].includes("vite-node"))&&(async()=>{const e=(await import("yargs-parser")).default,r=await import("node:fs"),o=await import("node:path"),c=e(process.argv.slice(2),{string:["locale","output"],alias:{output:["o"]},default:{locale:"en-US"}}),s=c._[0],n=c.locale,a=c.output;s||process.exit(1);try{new URL(s)}catch(i){process.exit(1)}try{const{markdown:e,html:c}=await t.htmlToMarkdown(s,{locale:n});let i;if(a){i=o.resolve(process.cwd(),a);const e=o.dirname(i);r.existsSync(e)||r.mkdirSync(e,{recursive:!0})}else{const e=`${s.replace(/https?:\/\//,"").replace(/[^a-zA-Z0-9]/g,"_")}_${Date.now()}.md`,t=o.join(process.cwd(),".outputs","raw");r.existsSync(t)||r.mkdirSync(t,{recursive:!0}),i=o.join(t,e)}r.writeFileSync(i,e);const p=o.parse(i),l=o.join(p.dir,`${p.name}.html`);r.writeFileSync(l,c)}catch(i){process.exit(1)}})()})();
package/dist/main.js CHANGED
@@ -6,7 +6,7 @@ Object.assign(global, {
6
6
  window,
7
7
  self: window
8
8
  });
9
- import { g as getMessage, h as htmlToMarkdown } from "./core-DOzMLPij.js";
9
+ import { g as getMessage, h as htmlToMarkdown } from "./core-DU_246Q7.js";
10
10
  const runCli = async () => {
11
11
  const yargsParser = (await import("yargs-parser")).default;
12
12
  const fs = await import("node:fs");
@@ -0,0 +1,283 @@
1
+ import { Window } from "happy-dom";
2
+ const window = new Window();
3
+ Object.assign(global, {
4
+ document: window.document,
5
+ window,
6
+ self: window
7
+ });
8
+ import { J as JSONRPCMessageSchema, g as getPackageVersion, S as Server, L as ListToolsRequestSchema, C as CallToolRequestSchema } from "./version-BRVBmpor.js";
9
+ import process from "node:process";
10
+ import { h as htmlToMarkdown } from "./core-DU_246Q7.js";
11
+ class ReadBuffer {
12
+ append(chunk) {
13
+ this._buffer = this._buffer ? Buffer.concat([this._buffer, chunk]) : chunk;
14
+ }
15
+ readMessage() {
16
+ if (!this._buffer) {
17
+ return null;
18
+ }
19
+ const index = this._buffer.indexOf("\n");
20
+ if (index === -1) {
21
+ return null;
22
+ }
23
+ const line = this._buffer.toString("utf8", 0, index).replace(/\r$/, "");
24
+ this._buffer = this._buffer.subarray(index + 1);
25
+ return deserializeMessage(line);
26
+ }
27
+ clear() {
28
+ this._buffer = void 0;
29
+ }
30
+ }
31
+ function deserializeMessage(line) {
32
+ return JSONRPCMessageSchema.parse(JSON.parse(line));
33
+ }
34
+ function serializeMessage(message) {
35
+ return JSON.stringify(message) + "\n";
36
+ }
37
+ class StdioServerTransport {
38
+ constructor(_stdin = process.stdin, _stdout = process.stdout) {
39
+ this._stdin = _stdin;
40
+ this._stdout = _stdout;
41
+ this._readBuffer = new ReadBuffer();
42
+ this._started = false;
43
+ this._ondata = (chunk) => {
44
+ this._readBuffer.append(chunk);
45
+ this.processReadBuffer();
46
+ };
47
+ this._onerror = (error) => {
48
+ var _a;
49
+ (_a = this.onerror) === null || _a === void 0 ? void 0 : _a.call(this, error);
50
+ };
51
+ }
52
+ /**
53
+ * Starts listening for messages on stdin.
54
+ */
55
+ async start() {
56
+ if (this._started) {
57
+ throw new Error("StdioServerTransport already started! If using Server class, note that connect() calls start() automatically.");
58
+ }
59
+ this._started = true;
60
+ this._stdin.on("data", this._ondata);
61
+ this._stdin.on("error", this._onerror);
62
+ }
63
+ processReadBuffer() {
64
+ var _a, _b;
65
+ while (true) {
66
+ try {
67
+ const message = this._readBuffer.readMessage();
68
+ if (message === null) {
69
+ break;
70
+ }
71
+ (_a = this.onmessage) === null || _a === void 0 ? void 0 : _a.call(this, message);
72
+ } catch (error) {
73
+ (_b = this.onerror) === null || _b === void 0 ? void 0 : _b.call(this, error);
74
+ }
75
+ }
76
+ }
77
+ async close() {
78
+ var _a;
79
+ this._stdin.off("data", this._ondata);
80
+ this._stdin.off("error", this._onerror);
81
+ const remainingDataListeners = this._stdin.listenerCount("data");
82
+ if (remainingDataListeners === 0) {
83
+ this._stdin.pause();
84
+ }
85
+ this._readBuffer.clear();
86
+ (_a = this.onclose) === null || _a === void 0 ? void 0 : _a.call(this);
87
+ }
88
+ send(message) {
89
+ return new Promise((resolve) => {
90
+ const json = serializeMessage(message);
91
+ if (this._stdout.write(json)) {
92
+ resolve();
93
+ } else {
94
+ this._stdout.once("drain", resolve);
95
+ }
96
+ });
97
+ }
98
+ }
99
+ function parseHtmlToMarkdownArgs(args) {
100
+ if (!args || typeof args !== "object") {
101
+ throw new Error("Arguments are required");
102
+ }
103
+ const { url, html_content, locale = "en-US", output_format = "markdown" } = args;
104
+ if (!url && !html_content) {
105
+ throw new Error("Either 'url' or 'html_content' is required");
106
+ }
107
+ if (url && typeof url !== "string") {
108
+ throw new Error("'url' must be a string");
109
+ }
110
+ if (html_content && typeof html_content !== "string") {
111
+ throw new Error("'html_content' must be a string");
112
+ }
113
+ if (locale && !["en-US", "ja-JP"].includes(locale)) {
114
+ throw new Error("'locale' must be 'en-US' or 'ja-JP'");
115
+ }
116
+ if (output_format && !["markdown", "html", "both"].includes(output_format)) {
117
+ throw new Error("'output_format' must be 'markdown', 'html', or 'both'");
118
+ }
119
+ return {
120
+ url,
121
+ html_content,
122
+ locale,
123
+ output_format
124
+ };
125
+ }
126
+ class HtmlToMarkdownMcpServer {
127
+ constructor() {
128
+ this.version = getPackageVersion();
129
+ this.server = new Server(
130
+ {
131
+ name: "@aiquants/html-to-markdown",
132
+ version: this.version,
133
+ description: "A tool to dynamically fetch a web page from a given URL and convert it to Markdown."
134
+ },
135
+ {
136
+ capabilities: {
137
+ tools: {}
138
+ }
139
+ }
140
+ );
141
+ this.setupToolHandlers();
142
+ }
143
+ /**
144
+ * Setup tool handlers for the MCP server.
145
+ * MCP サーバーのツールハンドラーを設定
146
+ */
147
+ setupToolHandlers() {
148
+ this.server.setRequestHandler(ListToolsRequestSchema, async () => {
149
+ return {
150
+ tools: [
151
+ {
152
+ name: "html_to_markdown",
153
+ description: "Convert HTML content from a URL or HTML string to Markdown format. Supports dynamic content loading and preserves table structures.",
154
+ inputSchema: {
155
+ type: "object",
156
+ properties: {
157
+ url: {
158
+ type: "string",
159
+ description: "The URL of the web page to convert to Markdown"
160
+ },
161
+ html_content: {
162
+ type: "string",
163
+ description: "HTML content as a string to convert to Markdown (alternative to URL)"
164
+ },
165
+ locale: {
166
+ type: "string",
167
+ description: "The locale to use for browser context (en-US or ja-JP)",
168
+ enum: ["en-US", "ja-JP"],
169
+ default: "en-US"
170
+ },
171
+ output_format: {
172
+ type: "string",
173
+ description: "Output format: 'markdown' (default), 'html', or 'both'",
174
+ enum: ["markdown", "html", "both"],
175
+ default: "markdown"
176
+ }
177
+ },
178
+ anyOf: [{ required: ["url"] }, { required: ["html_content"] }]
179
+ }
180
+ }
181
+ ]
182
+ };
183
+ });
184
+ this.server.setRequestHandler(CallToolRequestSchema, async (request) => {
185
+ switch (request.params.name) {
186
+ case "html_to_markdown": {
187
+ return await this.handleHtmlToMarkdown(request.params.arguments);
188
+ }
189
+ default:
190
+ throw new Error(`Unknown tool: ${request.params.name}`);
191
+ }
192
+ });
193
+ }
194
+ /**
195
+ * Handle HTML to Markdown conversion tool call.
196
+ * HTML から Markdown への変換ツール呼び出しを処理
197
+ */
198
+ async handleHtmlToMarkdown(args) {
199
+ try {
200
+ const validatedArgs = parseHtmlToMarkdownArgs(args);
201
+ const { url, html_content, locale = "en-US", output_format = "markdown" } = validatedArgs;
202
+ if (url) {
203
+ try {
204
+ new URL(url);
205
+ } catch {
206
+ throw new Error(`Invalid URL: ${url}`);
207
+ }
208
+ }
209
+ const result = await htmlToMarkdown(url || "direct-html-input", {
210
+ locale,
211
+ htmlContent: html_content
212
+ });
213
+ let content;
214
+ switch (output_format) {
215
+ case "markdown":
216
+ content = [
217
+ {
218
+ type: "text",
219
+ text: result.markdown
220
+ }
221
+ ];
222
+ break;
223
+ case "html":
224
+ content = [
225
+ {
226
+ type: "text",
227
+ text: result.html
228
+ }
229
+ ];
230
+ break;
231
+ case "both":
232
+ content = [
233
+ {
234
+ type: "text",
235
+ text: result.markdown
236
+ },
237
+ {
238
+ type: "text",
239
+ text: result.html
240
+ }
241
+ ];
242
+ break;
243
+ default:
244
+ throw new Error(`Invalid output format: ${output_format}`);
245
+ }
246
+ return {
247
+ content,
248
+ isError: false
249
+ };
250
+ } catch (error) {
251
+ const errorMessage = error instanceof Error ? error.message : String(error);
252
+ return {
253
+ content: [
254
+ {
255
+ type: "text",
256
+ text: `Error: ${errorMessage}`
257
+ }
258
+ ],
259
+ isError: true
260
+ };
261
+ }
262
+ }
263
+ /**
264
+ * Start the MCP server.
265
+ * MCP サーバーを開始
266
+ */
267
+ async start() {
268
+ const transport = new StdioServerTransport();
269
+ await this.server.connect(transport);
270
+ console.error("HTML to Markdown MCP server started");
271
+ }
272
+ }
273
+ const createMcpServer = () => {
274
+ return new HtmlToMarkdownMcpServer();
275
+ };
276
+ const runMcpServer = async () => {
277
+ const server = createMcpServer();
278
+ await server.start();
279
+ };
280
+ export {
281
+ createMcpServer as c,
282
+ runMcpServer as r
283
+ };
@@ -0,0 +1 @@
1
+ const t=new(require("happy-dom").Window);Object.assign(global,{document:t.document,window:t,self:t});const r=require("./version-DTaUKNBS.cjs"),e=require("node:process"),o=require("./core-D2dlEt1l.cjs");class n{append(t){this._buffer=this._buffer?Buffer.concat([this._buffer,t]):t}readMessage(){if(!this._buffer)return null;const t=this._buffer.indexOf("\n");if(-1===t)return null;const e=this._buffer.toString("utf8",0,t).replace(/\r$/,"");return this._buffer=this._buffer.subarray(t+1),function(t){return r.JSONRPCMessageSchema.parse(JSON.parse(t))}(e)}clear(){this._buffer=void 0}}class s{constructor(t=e.stdin,r=e.stdout){this._stdin=t,this._stdout=r,this._readBuffer=new n,this._started=!1,this._ondata=t=>{this._readBuffer.append(t),this.processReadBuffer()},this._onerror=t=>{var r;null===(r=this.onerror)||void 0===r||r.call(this,t)}}async start(){if(this._started)throw new Error("StdioServerTransport already started! If using Server class, note that connect() calls start() automatically.");this._started=!0,this._stdin.on("data",this._ondata),this._stdin.on("error",this._onerror)}processReadBuffer(){for(var t,r;;)try{const r=this._readBuffer.readMessage();if(null===r)break;null===(t=this.onmessage)||void 0===t||t.call(this,r)}catch(e){null===(r=this.onerror)||void 0===r||r.call(this,e)}}async close(){var t;this._stdin.off("data",this._ondata),this._stdin.off("error",this._onerror);0===this._stdin.listenerCount("data")&&this._stdin.pause(),this._readBuffer.clear(),null===(t=this.onclose)||void 0===t||t.call(this)}send(t){return new Promise(r=>{const e=function(t){return JSON.stringify(t)+"\n"}(t);this._stdout.write(e)?r():this._stdout.once("drain",r)})}}class a{constructor(){this.version=r.getPackageVersion(),this.server=new r.Server({name:"@aiquants/html-to-markdown",version:this.version,description:"A tool to dynamically fetch a web page from a given URL and convert it to Markdown."},{capabilities:{tools:{}}}),this.setupToolHandlers()}setupToolHandlers(){this.server.setRequestHandler(r.ListToolsRequestSchema,async()=>({tools:[{name:"html_to_markdown",description:"Convert HTML content from a URL or HTML string to Markdown format. Supports dynamic content loading and preserves table structures.",inputSchema:{type:"object",properties:{url:{type:"string",description:"The URL of the web page to convert to Markdown"},html_content:{type:"string",description:"HTML content as a string to convert to Markdown (alternative to URL)"},locale:{type:"string",description:"The locale to use for browser context (en-US or ja-JP)",enum:["en-US","ja-JP"],default:"en-US"},output_format:{type:"string",description:"Output format: 'markdown' (default), 'html', or 'both'",enum:["markdown","html","both"],default:"markdown"}},anyOf:[{required:["url"]},{required:["html_content"]}]}}]})),this.server.setRequestHandler(r.CallToolRequestSchema,async t=>{if("html_to_markdown"===t.params.name)return await this.handleHtmlToMarkdown(t.params.arguments);throw new Error(`Unknown tool: ${t.params.name}`)})}async handleHtmlToMarkdown(t){try{const r=function(t){if(!t||"object"!=typeof t)throw new Error("Arguments are required");const{url:r,html_content:e,locale:o="en-US",output_format:n="markdown"}=t;if(!r&&!e)throw new Error("Either 'url' or 'html_content' is required");if(r&&"string"!=typeof r)throw new Error("'url' must be a string");if(e&&"string"!=typeof e)throw new Error("'html_content' must be a string");if(o&&!["en-US","ja-JP"].includes(o))throw new Error("'locale' must be 'en-US' or 'ja-JP'");if(n&&!["markdown","html","both"].includes(n))throw new Error("'output_format' must be 'markdown', 'html', or 'both'");return{url:r,html_content:e,locale:o,output_format:n}}(t),{url:e,html_content:n,locale:s="en-US",output_format:a="markdown"}=r;if(e)try{new URL(e)}catch{throw new Error(`Invalid URL: ${e}`)}const i=await o.htmlToMarkdown(e||"direct-html-input",{locale:s,htmlContent:n});let c;switch(a){case"markdown":c=[{type:"text",text:i.markdown}];break;case"html":c=[{type:"text",text:i.html}];break;case"both":c=[{type:"text",text:i.markdown},{type:"text",text:i.html}];break;default:throw new Error(`Invalid output format: ${a}`)}return{content:c,isError:!1}}catch(r){return{content:[{type:"text",text:`Error: ${r instanceof Error?r.message:String(r)}`}],isError:!0}}}async start(){const t=new s;await this.server.connect(t)}}const i=()=>new a;exports.createMcpServer=i,exports.runMcpServer=async()=>{const t=i();await t.start()};