Overview
The Web2MD REST API lets you convert any webpage or raw HTML to clean Markdown programmatically. Use it to build pipelines, automate content ingestion, or integrate Web2MD into your own tools.
The REST API requires a PRO plan. Generate your API key from the Web2MD dashboard.
Machine-readable specs
| Resource | URL | Description |
|---|
| OpenAPI 3.1 spec | /api/v1/openapi.json | Full API schema for code generation and tooling |
| AI plugin manifest | /.well-known/ai-plugin.json | Agent discovery (ChatGPT Plugins / AI assistants) |
Use the OpenAPI spec to auto-generate client SDKs or import into tools like Postman, Swagger UI, or AI agent frameworks.
Authentication
All requests must include your API key in the Authorization header:
Authorization: Bearer w2m_your_key_here
API keys are prefixed with w2m_ and are tied to your account.
Endpoint
POST https://web2md.org/api/v1/convert
Request body
| Field | Type | Required | Description |
|---|
url | string | One of url or html | The URL of the page to convert |
html | string | One of url or html | Raw HTML string to convert |
options | object | No | Conversion options (see below) |
Provide either url or html, not both. The request will fail with a 400 error if both are present or neither is provided.
Options
| Field | Type | Default | Description |
|---|
includeImages | boolean | true | Include image references in output |
includeLinks | boolean | true | Preserve hyperlinks in output |
includeMeta | boolean | true | Prepend page metadata as YAML front matter |
Response
A successful response returns:
{
"success": true,
"data": {
"markdown": "# Page Title\n\nConverted content...",
"metadata": {
"title": "Page Title",
"url": "https://example.com/article",
"extractedAt": "2026-03-22T10:30:00.000Z",
"wordCount": 1250,
"tokenCount": 1680,
"readingTime": 5,
"author": "Jane Doe",
"publishedDate": "2026-03-20",
"description": "A brief summary extracted from the page meta tags."
}
}
}
| Field | Type | Description |
|---|
title | string | Page title extracted from <title> |
url | string | Source URL (if provided) |
extractedAt | string | ISO 8601 timestamp of the conversion |
wordCount | integer | Total word count (English words + CJK characters) |
tokenCount | integer | Estimated LLM token count |
readingTime | integer | Estimated reading time in minutes |
author | string? | Author name from meta tags or JSON-LD |
publishedDate | string? | Publication date (YYYY-MM-DD) |
description | string? | Page description from Open Graph or meta tags |
Rate limits
API requests are rate-limited to 60 requests per minute per API key. If you exceed the limit, the API returns a 429 status code. Wait for the reset window before retrying.
Error responses
| Status | Meaning | Example |
|---|
400 | Bad request — missing or conflicting input | Both url and html provided, or neither |
401 | Unauthorized — invalid or missing API key | Missing Authorization header |
422 | Unprocessable — the URL could not be fetched | Target site returned an error or timed out |
429 | Rate limit exceeded | More than 60 requests in one minute |
500 | Internal server error | Unexpected failure on our end |
All error responses follow this shape:
{
"success": false,
"error": {
"code": "RATE_LIMIT_EXCEEDED",
"message": "Rate limit exceeded. Try again in 45 seconds."
}
}
Examples
Convert a URL with curl
curl -X POST https://web2md.org/api/v1/convert \
-H "Authorization: Bearer w2m_your_key_here" \
-H "Content-Type: application/json" \
-d '{
"url": "https://example.com/blog/post",
"options": {
"includeImages": true,
"includeLinks": true,
"includeMeta": false
}
}'
Convert raw HTML with curl
curl -X POST https://web2md.org/api/v1/convert \
-H "Authorization: Bearer w2m_your_key_here" \
-H "Content-Type: application/json" \
-d '{
"html": "<h1>Hello World</h1><p>This is a <strong>test</strong> paragraph.</p>"
}'
JavaScript (fetch)
const response = await fetch("https://web2md.org/api/v1/convert", {
method: "POST",
headers: {
"Authorization": "Bearer w2m_your_key_here",
"Content-Type": "application/json",
},
body: JSON.stringify({
url: "https://example.com/blog/post",
options: {
includeImages: true,
includeLinks: true,
},
}),
});
const result = await response.json();
if (result.success) {
console.log(result.data.markdown);
console.log(`Word count: ${result.data.metadata.wordCount}`);
} else {
console.error(result.error.message);
}
Store your API key in an environment variable rather than hardcoding it. For example, use process.env.WEB2MD_API_KEY in Node.js.