mcpField
F
Flexible Key Value Extracting Mcp Server

Flexible Key Value Extracting Mcp Server

本地服务
github.com/KunihiroS开发工具15 周前更新

关于 Flexible Key Value Extracting Mcp Server

Flexible Key Value Extracting MCP Server 使用 LLM 从嘈杂或非结构化文本中发现并提取键值对,适合需要整理原始文本的开发者和自动化流程。它通过多步类型处理与 Pydantic 校验输出,并支持 JSON、YAML 和 TOML;提取结果不保证完全准确。

主要功能

  1. 01自动发现键值字段
  2. 02处理噪声与非结构化文本
  3. 03支持日英中输入
  4. 04类型标注与规范化
  5. 05Pydantic 类型校验
  6. 06输出 JSON、YAML 或 TOML

适用场景

  1. 01将订单文本整理为结构化数据
  2. 02从多语言文本提取实体与字段
  3. 03为自动化流程生成类型安全输出

MCP 相关

该 MCP 服务提供 extract_json、extract_yaml 和 extract_toml 工具,供 MCP 客户端将输入文本转换为对应格式的键值数据。

配置

本地服务的配置在各客户端中通用,复制后粘贴到客户端的 MCP 配置文件即可。

mcp.json · 通用配置
{
"mcpServers": {
"kv-extractor": {
"command": "uvx",
"args": [
"kv-extractor-mcp-server"
],
"env": {
"OPENAI_API_KEY": "<OPENAI_API_KEY>"
}
}
}
}
启动命令uvx kv-extractor-mcp-server
需要配置的环境变量
OPENAI_API_KEY密钥

本地服务需要在你的电脑上安装运行环境(如 Node.js 18+)。各客户端的配置文件位置不同,请参考客户端文档。

安装包
pypikv-extractor-mcp-server

工具

还没有获取到工具列表

本地服务需要在你的电脑上运行后才能读取工具,维护者暂未提供工具列表。

详细介绍

灵活的键值提取 MCP 服务

版本:0.3.3

此 MCP 服务使用 LLM(GPT-4.1-mini)和 pydantic-ai 从任意、嘈杂或非结构化文本中提取键值对。
它确保类型安全,并支持多种输出格式(JSON、YAML、TOML)。此服务能够稳健处理各种输入,并始终尽可能尝试构建数据结构,但不保证提取结果完美。


🤔💡 为什么使用此 MCP 服务?

许多大模型(LLM)服务都提供结构化输出功能,而此 MCP 服务在键值提取方面具有独特优势,尤其适用于处理具有挑战性的真实文本:

  • 🔑🔍 自动发现键:它的一项核心优势是能够自主识别并提取相关键值对,无需预先定义键。典型的 LLM 结构化输出需要你指定要查找的键,而此服务能够自行发现键,因此非常适合处理结构未知、类型多样且难以预测的数据。
  • 💪🧱 处理复杂输入时更加稳健:它擅长处理任意、嘈杂或非结构化文本,而标准的 LLM 结构化输出可能难以应对。其多步骤处理流程专为筛选并理解不完美的数据而设计。
  • 🌐🗣️ 先进的多语言预处理:在由 LLM 处理之前,此服务会借助 spaCy 对日语、英语和中文(简体/繁体)执行命名实体识别(NER),为提取提供包含丰富上下文的候选短语,从而显著提高这些语言的提取准确率。
  • 🔄✍️ 迭代优化与类型标注:不同于单次提取,此服务采用了复杂的处理流程,包括基于 LLM 的类型标注、基于 LLM 的类型评估,以及基于规则并在必要时回退到 LLM 的规范化处理。这能确保数据类型更准确、更符合上下文。
  • ✅🛡️ 确保类型安全并遵循架构:最终使用 Pydantic 构建数据结构,确保输出不仅结构化,而且类型安全,并通过定义的架构验证,从而为下游应用提供可靠数据。
  • 📊⚙️ 输出一致且可预测:此服务经过设计,即使提取不完整或遇到问题,也始终返回格式正确的响应,这对于构建可靠的自动化系统至关重要。

发布说明

v0.3.3
  • 修复:由于 JSON-RPC 流之前向 stdout 写入了两行非 JSON 内容,MCP 宿主(例如 Codex CLI)无法加载此服务。现在所有诊断信息都会写入 stderr(或在启用 --log=on 时写入日志文件),并且会屏蔽 FastMCP / pydantic-ai 横幅。
  • 修复:在当前版本的 pydantic-ai 中,工具调用因 'AgentRunResult' object has no attribute 'data' 而失败。此服务现在面向 pydantic-ai 2.x API。
  • 修复:导入此服务(以及运行 --help)不再需要 OPENAI_API_KEY。如果缺少密钥,现在会明确报告工具调用错误,而不是在导入时崩溃。
  • 变更:移除了 Smithery 集成(徽章、安装说明、smithery.yaml 和由 Smithery 生成的 Dockerfile);此服务在 Smithery 上的条目现已无法访问(404)。
  • 变更:依赖项已指定版本上限(fastmcp>=4,<5、pydantic-ai>=2,<3、spacy>=3.8,<3.9,……),以便全新运行 uvx / pipx run 时能以可复现的方式解析依赖项。需要 Python 3.10 或更高版本。
v0.3.2
  • 修复:FastMCP 导致错误。
v0.3.1
  • 更新:改进类型评估提示词,以实现稳健纠正。
  • 更新:在 README.md 中补充此 MCP 服务的优势。
v0.2.0
  • 修复:zh-cn / zh-tw 的语言代码。
v0.1.0
  • 首次发布

工具

  • /extract_json:以 JSON 格式从输入文本中提取类型安全的键值对。
  • /extract_yaml:以 YAML 格式从输入文本中提取类型安全的键值对。
  • /extract_toml:以 TOML 格式从输入文本中提取类型安全的键值对。
    • 注意:由于 TOML 规范,无法直接表示对象(字典)数组或深层嵌套结构。详情请参阅下文的“关于 TOML 输出限制的说明”。

注意:

  • 支持的语言:日语、英语和中文(简体:zh-cn / 繁体:zh-tw)。
  • 提取依赖 pydantic-ai 和大模型,无法保证完美提取。
  • 输入句子越长,处理时间越久。请耐心等待。
  • 首次启动时,服务会下载 spaCy 模型,因此初次处理会花费更长时间。
预计处理时间示例
输入 Token 数输入字符数(约)实测处理时间(秒)模型配置
200~400~15gpt-4.1-mini

实际处理时间可能会因 API 响应、网络状况和模型负载而有很大差异。即使是短文本,也可能需要 15 秒或更长时间。

功能

  • 灵活提取:可处理任何输入,包括带有噪声或格式错误的数据。
  • 全面支持日语 / 英语 / 简体中文 / 繁体中文:通过自动语言检测,使用 spaCy NER 进行预处理(支持日语、英语、中文[简体:zh-cn / 繁体:zh-tw];其他语言会报错拒绝处理)。
  • 类型安全的输出:使用 Pydantic 验证输出。
  • 多种格式:以 JSON、YAML 或 TOML 格式返回结果。
  • 健壮的错误处理:即使处理失败,也始终返回格式正确的响应。
  • 高准确度:提取 / 注释和类型评估均使用 GPT-4.1-mini,并使用 Pydantic 完成最终结构化。

测试场景

该服务已使用各种输入进行了测试,包括:

  • 简单的键值对
  • 包含重要信息但内容嘈杂或无结构的文本
  • 不同的输出数据格式(JSON、YAML、TOML)

处理流程

下图展示了 server.py 中实现的键值对提取流水线的处理流程:

flowchart TD
    A[Input Text] --> B[Step 0: Preprocessing with spaCy Lang Detect then NER]
    B --> C[Step 1: Key-Value Extraction - LLM]
    C --> D[Step 2: Type Annotation - LLM]
    D --> E[Step 3: Type Evaluation - LLM]
    E --> F[Step 4: Type Normalization - Static Rules + LLM]
    F --> G[Step 5: Final Structuring with Pydantic]
    G --> H[Output in JSON/YAML/TOML]

使用 spaCy 进行预处理(多语言 NER)

此服务使用 spaCy 自动检测语言,并在将输入文本传递给大模型之前提取其中的命名实体。支持的语言包括日语(ja_core_news_md)、英语(en_core_web_sm)和中文(简体 / 繁体,zh_core_web_sm)。

  • 使用 langdetect 自动检测输入文本的语言。

  • 如果检测到的语言不是日语、英语或中文,服务会返回错误:Unsupported lang detected。

  • 根据需要自动下载并加载相应的 spaCy 模型。无需手动安装。

  • 提取的短语列表会按如下方式包含在大模型提示词中:

    [预处理候选短语(spaCy NER)] 以下是使用 spaCy 检测到的语言模型从输入文本中自动提取的短语列表。 这些短语代表检测到的实体,例如姓名、日期、组织、地点、数字等。 此列表仅供参考,可能包含无关或不正确的项目。大模型会根据自身判断并考虑完整的输入文本,灵活推断最合适的键值对。

步骤详情

本项目的键值对提取流水线由多个步骤组成。各步骤的详情如下:

步骤 0:使用 spaCy 进行预处理(语言检测 → 命名实体识别)
  • 用途:自动检测输入文本的语言,并使用相应的 spaCy 模型(例如,ja_core_news_md、en_core_web_sm、zh_core_web_sm)提取命名实体。
  • 输出:提取出的短语列表,该列表会作为提示信息包含在大模型提示词中,以提高键值对提取的准确性。
步骤 1:键值提取(大模型)
  • 用途:使用 GPT-4.1-mini 从输入文本和提取出的短语列表中提取键值对。
  • 详情:
    • 提示词中包含说明:同一键出现多次时,以列表形式返回对应的值。
    • 少样本示例经过设计,包含列表形式的输出。
  • 输出:示例:key: person, value: ["Tanaka", "Sato"]
步骤 2:类型标注(大模型)
  • 用途:使用 GPT-4.1-mini 推断步骤 1 中提取的各个键值对的数据类型(int、str、bool、list 等)。
  • 详情:
    • 类型标注提示词中包含对列表和多个值的支持说明。
  • 输出:示例:key: person, value: ["Tanaka", "Sato"] -> list[str]
步骤 3:类型评估(大模型)
  • 用途:使用 GPT-4.1-mini 评估并修正步骤 2 中的类型标注。
  • 详情:
    • 对于每个键值对,GPT-4.1-mini 会重新评估类型标注的有效性和上下文。
    • 如果检测到类型错误或歧义,GPT-4.1-mini 会自动修正或补充类型。
    • 示例:将提取为数字但应为字符串的值修正为字符串,或判断一个值是列表还是单个值。
  • 输出:经过类型评估的键值对列表。
步骤 4:类型规范化(静态规则 + 大模型回退)
  • 用途:将经过类型评估的数据转换为 Python 标准类型(int、float、bool、str、list、None 等)。
  • 详情:
    • 应用静态规范化规则(正则表达式或类型转换函数),将值转换为 Python 标准类型。
    • 示例:将逗号分隔的值转换为列表、将 "true"/"false" 转换为 bool,或将日期表达式转换为标准格式。
    • 如果静态规则无法转换某个值,则使用基于大模型的类型转换回退方案。
    • 无法转换的值会安全地处理为 None 或 str。
  • 输出:经过 Python 类型规范化的键值对列表。
步骤 5:使用 Pydantic 进行最终结构化
  • 用途:使用 Pydantic 模型(KVOut/KVPayload)验证并结构化经过类型规范化的数据。
  • 详情:
    • 将每个键值对映射到 Pydantic 模型,确保类型安全和数据完整性。
    • 根据架构验证单个值、列表、空值和复合类型。
    • 如果验证失败,则在尽可能保留数据的同时附加错误信息。
    • 最终输出将以指定格式(JSON、YAML 或 TOML)返回。
  • 输出:类型安全且经过验证的 dict,或指定格式(JSON/YAML/TOML)的输出。

此流水线旨在支持未来对列表格式的支持和 Pydantic 架构扩展。

关于 TOML 输出限制的说明

  • 在 TOML 中,简单数组(例如,items = ["A", "B"])可以原生表示,但 由于 TOML 规范的限制,无法直接表示对象(dict)数组或深度嵌套结构。
  • 因此,复杂列表或嵌套结构(例如,[{"name": "A"}, {"name": "B"}])会 以“JSON 字符串”的形式存储在 TOML 值中。
  • 这是为了避免 TOML 规范的限制导致信息丢失而做出的设计选择。
  • YAML 和 JSON 格式可以按原样表示嵌套结构。

输入/输出示例

输入:

Thank you for your order (Order Number: ORD-98765). Product: High-Performance Laptop, Price: 89,800 JPY (tax excluded), Delivery: May 15-17. Shipping address: 1-2-3 Shinjuku, Shinjuku-ku, Tokyo, Apartment 101. Phone: 090-1234-5678. Payment: Credit Card (VISA, last 4 digits: 1234). For changes, contact [email protected].

输出(JSON):

{
  "order_number": "ORD-98765",
  "product_name": "High-Performance Laptop",
  "price": 89800,
  "price_currency": "JPY",
  "tax_excluded": true,
  "delivery_start_date": "20240515",
  "delivery_end_date": "20240517",
  "shipping_address": "1-2-3 Shinjuku, Shinjuku-ku, Tokyo, Apartment 101",
  "phone_number": "090-1234-5678",
  "payment_method": "Credit Card",
  "card_type": "VISA",
  "card_last4": "1234",
  "customer_support_email": "[email protected]"
}

输出(YAML):

order_number: ORD-98765
product_name: High-Performance Laptop
price: 89800
price_currency: JPY
tax_excluded: true
delivery_start_date: '20240515'
delivery_end_date: '20240517'
shipping_address: 1-2-3 Shinjuku, Shinjuku-ku, Tokyo, Apartment 101
phone_number: 090-1234-5678
payment_method: Credit Card
card_type: VISA
card_last4: '1234'
customer_support_email: [email protected]

输出(TOML,简单情况):

order_number = "ORD-98765"
product_name = "High-Performance Laptop"
price = 89800
price_currency = "JPY"
tax_excluded = true
delivery_start_date = "20240515"
delivery_end_date = "20240517"
shipping_address = "1-2-3 Shinjuku, Shinjuku-ku, Tokyo, Apartment 101"
phone_number = "090-1234-5678"
payment_method = "Credit Card"
card_type = "VISA"
card_last4 = "1234"

输出(TOML,复杂情况):

items = '[{"name": "A", "qty": 2}, {"name": "B", "qty": 5}]'
addresses = '[{"city": "Tokyo", "zip": "160-0022"}, {"city": "Osaka", "zip": "530-0001"}]'

注:对象数组或嵌套结构会以 JSON 字符串的形式存储在 TOML 中。

工具

1. extract_json
  • 描述:从任意嘈杂文本中提取键值对,并以类型安全的 JSON(Python dict)形式返回。
  • 参数:
    • input_text(string):包含嘈杂或非结构化数据的输入字符串。
  • 返回值:{ "success": True, "result": ... } 或 { "success": False, "error": ... }
  • 示例:
    {
      "success": true,
      "result": { "foo": 1, "bar": "baz" }
    }
    
2. extract_yaml
  • 描述:从任意嘈杂文本中提取键值对,并以类型安全的 YAML(string)形式返回。
  • 参数:
    • input_text(string):包含嘈杂或非结构化数据的输入字符串。
  • 返回值:{ "success": True, "result": ... } 或 { "success": False, "error": ... }
  • 示例:
    {
      "success": true,
      "result": "foo: 1\nbar: baz"
    }
    
3. extract_toml
  • 描述:从任意嘈杂文本中提取键值对,并以类型安全的 TOML(string)形式返回。
  • 参数:
    • input_text(string):包含嘈杂或非结构化数据的输入字符串。
  • 返回值:{ "success": True, "result": ... } 或 { "success": False, "error": ... }
  • 示例:
    {
      "success": true,
      "result": "foo = 1\nbar = \"baz\""
    }
    

用法

要求
  • Python 3.10+
  • OpenAI 模型的 API 密钥(在 MCP 主机配置的 env 中设置)。即使没有密钥,服务也会启动并列出其工具,但在提供密钥之前,每次工具调用都会返回 {"success": false, "error": "OPENAI_API_KEY is not set. ..."}。
运行服务
python server.py

如果要手动运行服务。

MCP 主机配置

运行此 MCP 服务时,必须通过命令行参数明确指定日志输出模式,以及(如果启用日志)日志文件的绝对路径。

  • --log=off:禁用所有日志(不写入日志)
  • --log=on --logfile=/absolute/path/to/logfile.log:启用日志,并将日志写入指定的绝对路径
  • 启用日志时,必须提供这两个参数。如果缺少任一参数、路径不是绝对路径,或提供了无效值,服务将报错并退出。
示例:禁用日志
"kv-extractor-mcp-server": {
  "command": "pipx",
  "args": ["run", "kv-extractor-mcp-server", "--log=off"],
  "env": {
    "OPENAI_API_KEY": "{apikey}"
  }
}
示例:Codex CLI(~/.codex/config.toml,通过 uvx)
[mcp_servers.kv-extractor-mcp-server]
command = "uvx"
args = ["kv-extractor-mcp-server==0.3.3", "--log=off"]

[mcp_servers.kv-extractor-mcp-server.env]
OPENAI_API_KEY = "{apikey}"
示例:启用日志(必须指定日志文件的绝对路径)
"kv-extractor-mcp-server": {
  "command": "pipx",
  "args": ["run", "kv-extractor-mcp-server", "--log=on", "--logfile=/workspace/logs/kv-extractor-mcp-server.log"],
  "env": {
    "OPENAI_API_KEY": "{apikey}"
  }
}

注意:

  • 启用日志时,日志仅写入指定的绝对路径。使用相对路径或省略 --logfile 都会导致错误。
  • 禁用日志时,不会输出任何日志。
  • stdout 专用于 MCP JSON-RPC 流。诊断信息(启动消息以及启用 --log=on 时的日志流)会写入 stderr,因此不会干扰 MCP 主机的传输。
  • 如果缺少必需参数或参数无效,服务将无法启动,并会打印错误消息。
  • MCP 服务进程必须能够访问并写入日志文件。
  • 如果无法运行此服务,可能是由于缓存了较旧版本的 kv-extractor-mcp-server。请尝试通过以下设置,使用最新版本的 kv-extractor-mcp-server 运行(将 x.y.z 替换为最新版本)。
"kv-extractor-mcp-server": {
  "command": "pipx",
  "args": ["run", "kv-extractor-mcp-server==x.y.z", "--log=off"],
  "env": {
    "OPENAI_API_KEY": "{apikey}"
  }
}

许可证

GPL-3.0-or-later

作者

KunihiroS(及贡献者)

评论

支持 Markdown

第一次接触 MCP?

从协议是什么,到在客户端里装上第一个服务,这几条回答覆盖了大多数入门问题。

一个开放协议,规定了 AI 应用如何以统一方式连接外部工具与数据源。客户端负责与模型对话,MCP 服务负责提供工具、资源和提示模板,两者通过标准消息通信,同一个服务可以被不同客户端复用。