Markdown转换中间件

mcp-bridge是一款自托管中间件,能够自动为LLM提供优化的Markdown内容,同时为浏览器提供完整的HTML界面。

  • by Bernardoklopf
  • TypeScript
  • 本地部署
  • 6 星标
  • 更新于
在 GitHub 查看 Bernardoklopf/mcp-bridge

使用说明

mcp桥

自托管中间件,为LLM提供干净的标记,为浏览器提供漂亮的HTML。

当一个人访问你的网站时,他们会看到你的完整UI。当LLM访问时,它会自动收到令牌优化的降价。


问题

网站提供臃肿的HTML——导航栏、脚本、样式表、广告、cookie横幅、跟踪像素。一个典型的网页是50-100KB的HTML,但实际内容只有5-10KB。当LLM通过工具使用或网络获取来消费它时, 70%-80%的代币被浪费 关于不相关的标记。

┌─────────────────────────────────────────┐
│  nav  nav  nav  nav  nav  nav  nav  nav │  ← wasted tokens
├─────────────────────────────────────────┤
│  sidebar │                    │ ad      │  ← wasted tokens
│          │  ACTUAL CONTENT    │         │
│          │  (this is all the  │         │
│          │   LLM needs)       │         │
│          │                    │ ad      │  ← wasted tokens
├──────────┴────────────────────┴─────────┤
│  footer  footer  footer  footer  footer │  ← wasted tokens
│  <script src="analytics.js">            │  ← wasted tokens
│  <script src="tracking.js">             │  ← wasted tokens
└─────────────────────────────────────────┘

Cloudflare推出了“Markdown for Agents”(2026年2月),在CDN边缘解决了这个问题,但仅适用于Cloudflare付费客户。

mcp桥 赋予相同的能力 任何 web服务器,自托管,具有单行中间件。

解决方案

mcp-bridge检测LLM请求,并自动将HTML响应转换为干净、结构化的markdown。

之前 (原始HTML,约12KB,约3000个标记):

<!DOCTYPE html>
<html>
<head>
  <style>/* 200 lines of CSS */</style>
  <script src="analytics.js"></script>
</head>
<body>
  <nav><!-- 50 links --></nav>
  <div class="hero"><!-- animations --></div>
  <main>
    <h1>Pricing</h1>
    <p>Simple pricing for everyone.</p>
    <!-- actual content... -->
  </main>
  <footer><!-- legal links --></footer>
  <div class="cookie-banner"><!-- consent UI --></div>
  <script src="tracking.js"></script>
</body>
</html>

之后 (净降价,约900B,约230个代币-- 减少92%):

---
title: "Pricing - Acme Corp"
url: https://acme.com/pricing
description: "Simple, transparent pricing for teams of all sizes."
---

# Pricing

Simple, transparent pricing for teams of all sizes.

### Free — $0
- 1,000 API calls/month
- Community support

### Pro — $29/month
- 100,000 API calls/month
- Priority support
- Unlimited team members

运作原理

                    ┌─────────────────┐
                    │   Your Server   │
                    │  (Express/Next) │
                    └────────┬────────┘
                             │
                    ┌────────▼────────┐
  Request ─────────►   mcp-bridge    │
                    │   middleware    │
                    └────────┬────────┘
                             │
                    ┌────────▼────────┐
                    │    Detect:      │
                    │  Is this an LLM?│
                    └───┬─────────┬───┘
                        │         │
                   YES  │         │  NO
                        ▼         ▼
               ┌──────────┐  ┌──────────┐
               │ Extract   │  │ Pass     │
               │ content   │  │ through  │
               │ Convert   │  │ HTML     │
               │ to MD     │  │ as-is    │
               └──────────┘  └──────────┘

检测使用优先级链:

  1. Accept: text/markdown 标题(生态系统标准)
  2. 已知的AI用户代理匹配(GPTBot、ClaudeBot等)
  3. 自定义 X-LLM-Request: true 头球
  4. 自定义检测功能

快速开始

快速

npm install @mcp-bridge/express
import express from 'express';
import { mcpBridge } from '@mcp-bridge/express';

const app = express();

app.use(mcpBridge({
  exclude: ['/api/*', '/health'],
}));

// Your routes serve HTML as normal
app.get('/', (req, res) => {
  res.send('<html>...</html>');
});

app.listen(3000);

就是这样。浏览器请求得到HTML,LLM请求得到markdown。

Next.js

npm install @mcp-bridge/next
// middleware.ts
import { createMcpBridgeMiddleware } from '@mcp-bridge/next';

export const middleware = createMcpBridgeMiddleware({
  exclude: ['/api/*'],
});

export const config = {
  matcher: ['/((?!_next/static|_next/image|favicon.ico).*)'],
};

检测方法

mcp-bridge使用优先级链来识别LLM请求:

优先级 方法 信号 置信度
1 接受标题 Accept: text/markdown 高
2 用户代理 已知的AI机器人模式 高
3 自定义标题 X-LLM-Request: true 高
4 自定义功能 您的逻辑 中等

这 Accept: text/markdown header是新兴的生态系统标准,由Claude Code、OpenCode使用,并由Cloudflare的实现提供支持。

配置

interface McpBridgeConfig {
  detect?: {
    acceptHeader?: boolean;       // Check Accept: text/markdown (default: true)
    userAgent?: boolean;          // Check known AI user-agents (default: true)
    customHeader?: string;        // Custom header name (default: 'X-LLM-Request')
    ipRanges?: boolean;           // Check known AI IP ranges (default: false)
    custom?: (req) => boolean;    // Custom detection function
  };

  extract?: {
    annotations?: boolean;        // Respect data-llm-* attributes (default: true)
    fallback?: 'readability' | 'body'; // Extraction strategy (default: 'readability')
    maxLength?: number;           // Max output length in chars (default: 100000)
  };

  headers?: {
    contentUsage?: {              // IETF AIPREF Content-Usage header
      aiInput?: 'y' | 'n';       // Allow AI to use content as input
      trainAi?: 'y' | 'n';       // Allow content for AI training
      search?: 'y' | 'n';        // Allow content in search results
    };
    tokenCount?: boolean;         // Include X-Markdown-Tokens (default: true)
  };

  exclude?: string[];             // Glob patterns for paths to skip
  include?: string[];             // Only process these paths (if set)
  transform?: (md, metadata) => string; // Custom post-processing
}

开发人员注释

添加HTML属性以指导提取以获得最佳结果:

<!-- Mark the main content area -->
<main data-llm-content>
  <h1>Pricing</h1>
  <section>...</section>
</main>

<!-- Exclude elements from LLM output -->
<nav data-llm-ignore>...</nav>
<footer data-llm-ignore>...</footer>
<div class="cookie-banner" data-llm-ignore>...</div>

<!-- Add context hints for LLMs -->
<div data-llm-hint="This table compares pricing tiers">
  <table>...</table>
</div>

当 data-llm-content 仅提取这些元素内的内容。当不存在时,中间件使用Mozilla的Readability算法(与Firefox Reader View背后的算法相同)自动识别主要内容。

响应头

mcp-bridge在markdown响应上设置这些标头:

标题 示例 目的
Content-Type text/markdown; charset=utf-8 将响应标识为降价
Vary Accept, User-Agent 正确的缓存行为
X-Content-Source mcp-bridge/0.1.0 图书馆标识
X-Original-Content-Type text/html; charset=utf-8 起源提供了什么
Content-Usage ai-input=y, train-ai=n IETF AIPREF内容首选项
X-Markdown-Tokens 347 估计令牌计数

标准与兼容性

mcp-bridge与新兴的人工智能内容交付网络标准保持一致:

  • Accept: text/markdown --生态系统融合了LLM内容请求的信号。由Claude Code、OpenCode使用,并由Cloudflare支持。
  • IETF AIPREF — Content-Usage 用于表达AI内容偏好的标题。
  • 可读性 --Mozilla的内容提取算法,提取网络内容的行业标准。

建筑

mcp-bridge/
├── packages/
│   ├── core/        # Framework-agnostic engine (detection, extraction, conversion)
│   ├── express/     # Express middleware adapter
│   └── next/        # Next.js middleware adapter
└── examples/
    └── express-app/ # Working demo

这 @mcp-bridge/core 包是纯函数,没有框架依赖关系。它定义了以下规范算法:

  • 检测 --这是法学硕士的请求吗?
  • 提取 --这个HTML的主要内容是什么?
  • 转换 --将干净的HTML转换为markdown
  • 标头 --构建适当的响应标头

这使得使用等效库(例如。, readability-lxml + markdownify Python)。

已知AI代理

mcp-bridge能够识别以下用户代理字符串:

代理 组织
GPTBot OpenAI
ChatGPT-User OpenAI
OAI-SearchBot OpenAI
ClaudeBot 人类学
claude-web 人类学
anthropic-ai 人类学
Google-Extended 谷歌
PerplexityBot 困惑
Perplexity-User 困惑
meta-externalagent Meta
Applebot-Extended 苹果
Amazonbot 亚马逊
Bytespider 字节跳动
BingBot 微软

发展

# Install dependencies
pnpm install

# Build all packages
pnpm build

# Run tests
pnpm test

# Run the example server
cd examples/express-app && pnpm start

测试示例

# Browser request → HTML
curl http://localhost:3000/pricing

# LLM request via Accept header → Markdown
curl -H "Accept: text/markdown" http://localhost:3000/pricing

# LLM request via User-Agent → Markdown
curl -H "User-Agent: ClaudeBot/1.0" http://localhost:3000/pricing

# Excluded API path → JSON (unchanged)
curl -H "Accept: text/markdown" http://localhost:3000/api/data

贡献

欢迎捐款。关键领域:

  • 框架适配器 — 加入, Fastify, Koa, 等等.
  • 代理列表更新 --新的AI爬虫和机器人
  • 提取改进 --更好的内容启发式
  • 语言端口 --核心算法的Python、Go、Ruby实现

路线图

  • []Python端口(pip install mcp-bridge)
  • []前往港口
  • [ ] llms.txt 从网站内容自动生成
  • []用于结构化工具的MCP服务器端点
  • []Hono/Fastify适配器
  • []大页面的流媒体支持
  • []用于重复LLM请求的缓存层

许可证

麻省理工学院