mcpField
H
Henrri (unofficial)

Henrri (unofficial)

本地服务
github.com金融数据04 天前更新

关于 Henrri (unofficial)

Henrri (unofficial) 是一个 Rust MCP 服务,将 Henrri v1 API 提供给记账人员及其他 MCP 客户端使用,涵盖客户、报价、发票、付款和 Webhook。它支持只读配置,并对不可逆操作要求明确确认。

主要功能

  1. 01覆盖 Henrri v1 API 操作
  2. 02管理客户、报价、发票和付款
  3. 03合并式更新以保留未修改字段
  4. 04不可逆操作要求确认
  5. 05验证 Webhook 签名并阻止重放

适用场景

  1. 01查询逾期付款里程碑
  2. 02将已签署报价转换为发票
  3. 03以只读模式查看账务数据
  4. 04安全接收并检查 Webhook 事件

MCP 相关

该服务向 MCP 客户端提供 Henrri API 的结构化工具,涵盖读取、写入及 Webhook。可通过 stdio 或 HTTP 传输,并可限制为只读工具。

配置

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

mcp.json · 通用配置
{
"mcpServers": {
"edouard-claude-henrri": {
"command": "docker",
"args": [
"run",
"-i",
"--rm",
"-e",
"HENRRI_USERNAME",
"-e",
"HENRRI_PASSWORD",
"-e",
"HENRRI_CLIENT_ID",
"-e",
"HENRRI_CLIENT_SECRET",
"-e",
"HENRRI_ENVIRONMENT",
"-e",
"HENRRI_READ_ONLY",
"-e",
"HENRRI_TOOLSETS",
"ghcr.io/edouard-claude/henrri-mcp:0.1.0"
],
"env": {
"HENRRI_USERNAME": "<HENRRI_USERNAME>",
"HENRRI_PASSWORD": "<HENRRI_PASSWORD>",
"HENRRI_CLIENT_ID": "<HENRRI_CLIENT_ID>",
"HENRRI_CLIENT_SECRET": "<HENRRI_CLIENT_SECRET>",
"HENRRI_ENVIRONMENT": "<HENRRI_ENVIRONMENT>",
"HENRRI_READ_ONLY": "<HENRRI_READ_ONLY>",
"HENRRI_TOOLSETS": "<HENRRI_TOOLSETS>"
}
}
}
}
启动命令docker run -i --rm -e HENRRI_USERNAME -e HENRRI_PASSWORD -e HENRRI_CLIENT_ID -e HENRRI_CLIENT_SECRET -e HENRRI_ENVIRONMENT -e HENRRI_READ_ONLY -e HENRRI_TOOLSETS ghcr.io/edouard-claude/henrri-mcp:0.1.0
需要配置的环境变量
HENRRI_USERNAMEHenrri API user login (or set HENRRI_CLIENT_ID and HENRRI_CLIENT_SECRET)
HENRRI_PASSWORD密钥Henrri API user password
HENRRI_CLIENT_IDDeveloper client id, instead of a user
HENRRI_CLIENT_SECRET密钥Developer client secret
HENRRI_ENVIRONMENTproduction or sandbox
HENRRI_READ_ONLY1 to withhold every write tool (finalize, pay, delete…)
HENRRI_TOOLSETSComma-separated toolsets: account, customers, documents, catalog, payments, revenues, webhooks

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

安装包
ocighcr.io/edouard-claude/henrri-mcp:0.1.0

工具

还没有获取到工具列表

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

详细介绍

mcp-henrri

只需提问,即可获取 Henrri 开票信息。

一个 Rust 单文件二进制程序,可将完整的 Henrri v1 API—— 客户、报价单、发票、贷项通知单、付款计划、预付款、付款、Webhook—— 提供给任何 MCP 客户端。

Unofficial Rust MCP Henrri API Transports CI Release License

🇫🇷 Henrri 的非官方 MCP 服务:通过 Claude、Cursor 或任何 MCP 客户端,以自然语言管理客户、报价单、发票、贷项通知单、付款到期日、预付款和付款。

重要

这不是 Henrri 的官方产品。 这是一个独立的开源项目, 并非由 Henrri 制作、认可或支持。它逐项覆盖已发布的 Henrri v1 规范, 在 API 所允许的范围内忠实实现,并说明 API 与文档描述不一致之处。请参阅免责声明。


向助手提出 “为 Atelier Martin 开具发票,内容是 3 天开发工作,未税金额 600 欧元”、“还有谁欠我钱?”、“把已签署的报价单 D-26-11-3 转成发票”—— 就能直接在你的 Henrri 中完成操作,你的会计师也能看到结果。

> who still owes me money?

  list_payment_milestones   is_overdue = true · 7 milestones
                            ATELIER MARTIN    I-26-10-12   1 440,00 €   23 days late
                            LOVELACE          I-26-10-17     864,00 €    9 days late
                            …
                            overdue total     4 812,40 €

> invoice Atelier Martin for 3 days of development at 600 € excl. tax

  create_document           draft invoice 9632 for ATELIER MARTIN
  add_document_line         3 × Journée de développement · 600,00 € · VAT 20 %
  get_document_with_all     1 800,00 € excl. tax · 360,00 € VAT · 2 160,00 € incl. tax
                            finalize it? It locks the invoice for good and costs 8 credits.

为什么

Henrri 的 API 是简洁的 REST 接口,但直接交给大模型使用时,会以一些可预见的方式出错:PUT 会抹掉未随请求发送的所有字段;文档在调用一个不可撤销的操作之前都只是草稿;定稿会消耗额度;月度配额和速率限制器都会返回 429;模型也无法分辨文档的 ID 和编号。

  • **完整 API,毫无隐藏。**涵盖 v1 规范的全部 87 项操作:85 个路由,每个路由对应一个工具,另外两项认证路由由客户端本身处理。测试会将工具表与 spec/operations.tsv 比对,CI 每天都会将该文件与线上生产环境和沙盒规范进行核对。
  • **更新,就该真正更新。**每个 update_* 工具只接收要修改的内容,读取资源、合并并写回 Henrri 接受的内容——不会再因为客户的网站变更,就丢失他们的备注。
  • 对于不可撤销的操作,默认拒绝执行。finalize_document、validate_quotation、付款工具、cancel_deposit 以及所有删除操作,都必须提供 confirm: true 才会执行;拒绝执行时会说明可能造成的后果:文档、总额、客户和额度。设置 HENRRI_READ_ONLY=1 会禁用所有写入工具。
  • **让模型可以据此采取行动的错误信息。**失败会以工具结果的形式返回,并设置 isError: true,同时包含 Henrri 的 RFC 9457 问题文档:稳定的 errorCode(ALREADY_FINALIZED、LINES_MISSING、QUOTA_EXCEEDED 等)、detail、无效字段、供 Henrri 支持团队查询的 traceId,以及在解决方法不明显时提供的提示。
  • **一次处理好 API 的种种规则。**提前续期 10 分钟有效的令牌;遇到速率限制、503 和繁忙的定稿操作时进行重试;遇到额度限制时绝不重试;POST 请求可能已经执行后绝不再次发送;列表筛选条件以重复键的形式发送;将 last month 等时间段转换为 Henrri 使用的含首尾日期。
  • **经过验证的 Webhook。**通过 HTTP 时,服务会在 /webhooks 接收 Henrri 的推送,以恒定时间校验其 HMAC-SHA256 签名,拒绝重放请求,并让模型读取发生的事件。
  • **为模型阅读而编写。**89 个工具均提供带模式的结构化输出,每个工具都有注解;提供 4 个会在执行不可撤销操作前停下并询问的提示词;服务器说明会预先指出:使用 ID 而非编号、金额单位为欧元,以及草稿和定稿的区别。

安装

预编译二进制文件(macOS、Linux、Windows)

从最新版本下载适用于你平台的压缩包,对照其 .sha256 文件进行校验,然后将 mcp-henrri 放到 PATH 中:

# macOS on Apple silicon; swap the target for x86_64-apple-darwin,
# x86_64-unknown-linux-gnu or aarch64-unknown-linux-gnu
V=v0.1.0 T=aarch64-apple-darwin
curl -LO https://github.com/edouard-claude/henrri-mcp/releases/download/$V/mcp-henrri-$V-$T.tar.gz
tar xzf mcp-henrri-$V-$T.tar.gz
sudo mv mcp-henrri-$V-$T/mcp-henrri /usr/local/bin/

Windows:选择 x86_64-pc-windows-msvc.zip 压缩包。

从源代码构建(支持 Rust 1.88+ 的任意平台)
git clone https://github.com/edouard-claude/henrri-mcp
cd henrri-mcp
cargo build --release
# the binary is at target/release/mcp-henrri
使用 cargo install
cargo install --git https://github.com/edouard-claude/henrri-mcp
使用 Docker
docker run --rm -i \
  -e HENRRI_USERNAME -e HENRRI_PASSWORD \
  ghcr.io/edouard-claude/henrri-mcp:latest

镜像默认使用 stdio;添加 --http 0.0.0.0:8080(并设置 HENRRI_HTTP_TOKEN)即可提供 HTTP 服务。

获取 API 访问权限

Henrri 的开发者方案提供 API 访问权限。API 有两个环境,账户彼此独立:

环境API 根地址额度
生产环境https://api.henrri.io开具时扣除,设有月度配额
沙盒https://api-sandbox.henrri.io无限额度,数据为临时数据

认证方式有以下三种,按优先级从高到低排列:

  1. 开发者客户端——使用 HENRRI_CLIENT_ID 和 HENRRI_CLIENT_SECRET,通过 POST /v1/users/authenticate 交换令牌,并通过 POST /v1/users/refresh-token 续期。
  2. API 用户——使用 HENRRI_USERNAME 和 HENRRI_PASSWORD,通过 POST /v1/users/token 使用 OAuth2 password 授权(沙盒会提供这种账户,例如 [email protected])。
  3. 现成令牌——使用 HENRRI_ACCESS_TOKEN,原样使用且不会续期(有效期为 10 分钟)。

然后检查一切是否正常:

HENRRI_ENVIRONMENT=sandbox HENRRI_USERNAME=… HENRRI_PASSWORD=… mcp-henrri --check
environment  sandbox
base url     https://api-sandbox.henrri.io
credentials  API user (OAuth2 password grant)
toolsets     account, customers, documents, catalog, payments, revenues, webhooks
tools        89
token        ok
hello world  "Hello World"
user         [email protected] (16079), role admin
company      My company (947), plan discovery
credits      used 100 of unlimited, unlimited left

ready.

配置

所有内容均从环境变量读取,并在启动时读取一次。变量缺失或格式错误都会导致进程停止,并显示变量名称。

变量默认值
HENRRI_USERNAME / HENRRI_PASSWORDAPI 用户。Docker secrets 可使用 HENRRI_PASSWORD_FILE。
HENRRI_CLIENT_ID / HENRRI_CLIENT_SECRET或使用开发者客户端。也可使用 HENRRI_CLIENT_SECRET_FILE。
HENRRI_ACCESS_TOKEN或使用 bearer token,不会续期。
HENRRI_ENVIRONMENTproductionproduction 或 sandbox(staging)。
HENRRI_BASE_URL按环境而定覆盖 API 根地址。
HENRRI_TOOLSETS全部account,customers,documents,catalog,payments,revenues,webhooks
HENRRI_READ_ONLY0设为 1 时,不提供任何没有 readOnlyHint 的工具。
HENRRI_TIMEOUT_SECS30单次请求超时时间。
HENRRI_PDF_TIMEOUT_SECS120PDF 路由的超时时间,这些路由会按需渲染。
HENRRI_MAX_RETRIES3遇到速率限制、503 和忙碌状态的最终确认时的重试次数。
HENRRI_DOWNLOAD_DIR按用户缓存目录而定PDF 的保存位置(~/Library/Caches/mcp-henrri/downloads、~/.cache/…、%LOCALAPPDATA%\…)。目录将以 0700 权限创建;如果其他用户可写入该目录,则拒绝使用;不会回退到共享临时目录。
HENRRI_WEBHOOK_SECRETHenrri webhook 设置中的签名密钥。
HENRRI_HTTP_BIND在此地址提供 HTTP 服务,而非使用 stdio(与 --http 相同)。
HENRRI_HTTP_TOKENHTTP 传输所需的 Bearer token;非回环地址时必须设置。
HENRRI_LOGinfo日志过滤级别。日志写入 stderr,不会写入 stdout。

本地使用时,将 .env.example 复制为 .env;该文件已加入 git 忽略列表。

连接客户端

Claude Desktop

在 claude_desktop_config.json 中:

{
  "mcpServers": {
    "henrri": {
      "command": "/usr/local/bin/mcp-henrri",
      "env": {
        "HENRRI_USERNAME": "[email protected]",
        "HENRRI_PASSWORD": "…",
        "HENRRI_ENVIRONMENT": "production"
      }
    }
  }
}
Claude Code
claude mcp add henrri \
  -e [email protected] -e HENRRI_PASSWORD=… \
  -- /usr/local/bin/mcp-henrri
Cursor、VS Code 和任何 stdio 客户端

.cursor/mcp.json 或 .vscode/mcp.json:

{
  "servers": {
    "henrri": {
      "type": "stdio",
      "command": "/usr/local/bin/mcp-henrri",
      "env": { "HENRRI_USERNAME": "[email protected]", "HENRRI_PASSWORD": "…" }
    }
  }
}

提示:只需读取信息的记账员可以使用 HENRRI_READ_ONLY=1 运行;只需跟进付款的助手可以使用 HENRRI_TOOLSETS=customers,payments 运行。

工具

七个工具集中共有 89 个工具。mcp-henrri --list-tools 会列出当前配置开放的工具。R 表示读取,W 表示写入,D 表示具有破坏性或不可逆的操作,需要设置 confirm: true(两个付款工具和 validate_quotation 也需要)。

documents — 报价单、发票、贷项通知单、明细、PDF
工具路由
list_documentsRGET /v1/documents — 类型、状态、期间、搜索、min_id
list_documents_tableRGET /v1/documents/with-selected-fields
create_documentWPOST /v1/documents — 空白草稿
get_documentRGET /v1/documents/{id}
get_document_with_allRGET /v1/documents/{id}/with-all
get_document_all_includedRGET /v1/documents/{id}/all-included
update_documentWPUT /v1/documents/{id} — 局部更新,合并
delete_documentDDELETE /v1/documents/{id}
finalize_documentDPOST /v1/documents/{id}/finalize — 8 或 2 个积分
validate_quotationWPOST /v1/documents/{id}/validate — 2 个积分,需要 confirm
transform_quote_to_invoiceWPOST /v1/documents/{id}/transform-to-invoice
get_document_tax_detailsRGET /v1/documents/{id}/tax-details
get_document_displayRGET /v1/documents/{id}/display
get_payment_terms_displayRGET /v1/documents/{id}/paymenttermsdisplay
set_payment_terms_displayWPUT /v1/documents/{id}/paymenttermsdisplay — 局部更新
list_document_payment_milestonesRGET /v1/documents/{documentId}/paymentmilestones
get_document_pdfRGET /v1/documents/{id}/pdf — 保存到磁盘,可选 Factur-X
create_document_pdf_urlWPOST /v1/documents/{id}/pdf/url
download_document_pdf_fileRGET /v1/documents/{id}/pdf/files/{guid}
next_quote_batchWGET /v1/documents/next-quote-batch — 移动服务端游标
list_document_typesRGET /v1/documenttypes
list_document_linesRGET /v1/documents/{documentId}/lines
add_document_lineWPOST /v1/documents/{documentId}/lines — 将 kind 解析为类型 ID
get_document_lineRGET /v1/documents/{documentId}/lines/{id}
update_document_lineWPUT /v1/documents/{documentId}/lines/{id} — 局部更新,合并
delete_document_lineDDELETE /v1/documents/{documentId}/lines/{id}
move_document_lineWPOST /v1/documents/{documentId}/lines/{id}/move
list_document_line_typesRGET /v1/documentlinetypes
payments — 付款节点、定金、付款
工具路由
list_payment_milestonesRGET /v1/paymentmilestones — 已付款、逾期、单据
list_unpaid_milestones_tableRGET /v1/paymentmilestones/with-selected-fields
create_payment_milestoneWPOST /v1/paymentmilestones
get_payment_milestoneRGET /v1/paymentmilestones/{id}
update_payment_milestoneWPUT /v1/paymentmilestones/{id} — 局部更新
delete_payment_milestoneDDELETE /v1/paymentmilestones/{id}
pay_payment_milestoneWPOST /v1/paymentmilestones/{id}/pay — 需要 confirm
pay_payment_milestonesWPOST /v1/paymentmilestones/pay — 需要 confirm
get_milestone_paymentRGET /v1/paymentmilestones/{id}/payment
create_deposit_requestWPOST /v1/paymentmilestones/{id}/deposit-request
create_deposit_settlementWPOST /v1/paymentmilestones/{id}/deposit-settlement
cancel_depositDDELETE /v1/paymentmilestones/{id}/deposit
list_payment_modesRGET /v1/paymentmodes
list_paymentsRGET /v1/payments
get_paymentRGET /v1/payments/{id}
list_payment_settled_milestonesRGET /v1/payments/{id}/milestones
客户 — 客户与联系人
工具路由
list_customersRGET /v1/customers
list_customers_tableRGET /v1/customers/with-selected-fields
list_best_customersRGET /v1/customers/best-sales
list_last_used_customersRGET /v1/customers/last-used
create_customerWPOST /v1/customers — 先检查联系人规则和 SIRET/BCE
get_customerRGET /v1/customers/{id}
update_customerWPUT /v1/customers/{id} — 部分更新,合并
delete_customerDDELETE /v1/customers/{id}
get_customer_addressRGET /v1/customers/{id}/address
list_customer_payment_milestonesRGET /v1/customers/{id}/paymentmilestones
list_customer_contactsRGET /v1/customers/{id}/contacts
add_customer_contactWPOST /v1/customers/{id}/contacts
get_customer_contactRGET /v1/customers/{id}/contacts/{contactId}
update_customer_contactWPUT /v1/customers/{id}/contacts/{contactId} — 部分更新
delete_customer_contactDDELETE /v1/customers/{id}/contacts/{contactId}
目录 — 商品、类别、文本项、单位
工具路由
list_itemsRGET /v1/items
list_items_tableRGET /v1/items/with-selected-fields
list_most_used_itemsRGET /v1/items/most-used
list_best_selling_itemsRGET /v1/items/best-sales
create_itemWPOST /v1/items
get_itemRGET /v1/items/{id}
update_itemWPUT /v1/items/{id} — 部分更新,合并
delete_itemDDELETE /v1/items/{id}
list_item_categoriesRGET /v1/itemcategories
list_text_itemsRGET /v1/textitems
create_text_itemWPOST /v1/textitems
get_text_itemRGET /v1/textitems/{id}
update_text_itemWPUT /v1/textitems/{id} — 部分更新
delete_text_itemDDELETE /v1/textitems/{id}
list_unitsRGET /v1/units
create_unitWPOST /v1/units
get_unitRGET /v1/units/{id}
账户、收入与 Webhook
工具路由
pingRGET /v1/secures/hello-world
whoamiRGET /v1/users/me
get_userRGET /v1/users/{id}
get_user_addressRGET /v1/users/{id}/address
get_my_companyRGET /v1/users/companies
get_companyRGET /v1/companies/{id}
get_company_addressRGET /v1/companies/{id}/address
get_api_usageRX-Credits-* 和 X-RateLimit-* 标头
get_yearly_revenueRGET /v1/revenues/{year}
get_monthly_revenueRGET /v1/revenues/{year}/months
list_webhook_event_typesR规范中列出的 12 种 Webhook 事件和测试 ping
verify_webhook_signatureR{timestamp}.{rawBody} 的 HMAC-SHA256,采用恒定时间比较
list_received_webhook_eventsR在 /webhooks 收到的投递(HTTP 传输)

POST /v1/users/authenticate 和 POST /v1/users/refresh-token 不是工具:客户端会自行调用它们,OAuth2 令牌端点 POST /v1/users/token 也是如此。

资源和提示词

资源
henrri://me用户和公司。
henrri://reference文档类型、行类型、付款方式、项目类别、单位。
henrri://usage已用和剩余的额度、速率限制。
henrri://webhooks/eventsWebhook 事件目录。
henrri://webhooks/received收到的投递记录。
henrri://documents/{document_id}包含所有元素的文档。
henrri://documents/{document_id}/pdf文档的 PDF,以 blob 形式提供。
henrri://customers/{customer_id}包含付款节点的客户。
henrri://revenues/{year}某一年的总收入和月度收入。
提示词
draft_invoice从“谁”和“什么”开始,生成待审核的草稿;只有得到肯定答复后才定稿。
chase_unpaid按客户列出逾期款项,并提供可自行发送的提醒消息。只读。
revenue_report按月列出某一年的收入、最佳客户和项目。只读。
quote_to_invoice检查报价单、记录签名、转换、审核;得到肯定答复后再定稿。

Henrri 的实际行为

在构建此服务时通过沙盒发现了这些情况,并已妥善处理,模型不会遇到它们。tests/api_contract.rs 中的测试会验证每一项。

  • PUT 会删除未随请求发送的内容。 更新客户网站时,如果不附带评论,评论就会被删除。更新工具会先读取、合并,再写回。
  • 某些字段读取时返回 "",但提交 "" 会被拒绝。 vatNumber、siret 等字段都是如此。未变更的空字符串不会写入。
  • 携带联系人信息的客户 PUT 会被拒绝(PUT_WITH_CUSTOMER);携带嵌套项目、项目类型或计算总额的行 PUT 也会被拒绝。这些内容会被剔除。
  • 没有请求体且未提供 Content-Length 的 POST 会收到 IIS 411。 transform-to-invoice、deposit-request、pdf/url 等请求都会附带一个显式的空请求体。
  • 逗号分隔的列表筛选条件不会报错,而是返回空页(文档称会返回 400)。列表会以重复的键发送。
  • 创建付款节点时会忽略到期日,但更新时会采用该日期: create_payment_milestone 会通过第二次调用来设置日期。
  • 定稿请求体中的 confirmFirstOfMonth 会被拒绝,尽管 FIRST_ACCOUNTING_DOCUMENT_MONTH 错误要求提供该字段:它会作为查询参数发送。
  • 新单位的响应会返回 id: 0:create_unit 会通过单位名称查找该单位。
  • 公司级付款节点列表只显示已定稿的文档;已定稿文档指向客户的冻结副本(parentCustomerId):草稿的付款计划通过文档读取,客户的付款计划则通过该副本读取。
  • 城市会根据邮政编码变化。 Henrri 会重写城市名称(“Paris 01”);与邮政编码不匹配的城市会被清空。请同时修改两者。
  • refresh_token 在 /v1/users/token 上会被拒绝;API 用户会直接再次获得授权。
  • 有两种不同的 429。 每分钟速率限制器会重试;QUOTA_EXCEEDED(每月额度)不会重试。
  • PDF 渲染速度很慢,且在撰写本文时沙盒中的渲染存在问题(返回 500 或没有响应);PDF 路由使用单独的较长超时。

安全性

  • 不可逆调用采用失败关闭机制:没有 confirm: true 时,不会有任何内容离开进程,并且拒绝操作时会说明将会发生什么。服务说明和提示词会指示模型先向用户说明情况并取得肯定答复。
  • 设置 HENRRI_READ_ONLY=1 后,完全不会注册写入工具:只读状态由每个工具的 readOnlyHint 决定,而不是由可能发生偏差的列表决定。
  • 秘密信息绝不会进入日志或 Debug 输出;日志会写入 stderr。
  • PDF 仅会写入 HENRRI_DOWNLOAD_DIR,并使用经过净化的文件名。
  • 通过 HTTP 访问时,/mcp 需要 HENRRI_HTTP_TOKEN(使用恒定时间比较);没有令牌时,服务会拒绝在回环地址以外监听;在回环地址上,会对 Host 进行验证,以防止 DNS 重绑定。
  • 只有签名有效、时间戳在五分钟以内且每个投递 ID 仅首次出现的 Webhook 投递才会被接受。

通过 HTTP 运行

HENRRI_HTTP_TOKEN=$(openssl rand -hex 32) \
HENRRI_WEBHOOK_SECRET=… \
mcp-henrri --http 127.0.0.1:8080
# MCP at http://127.0.0.1:8080/mcp, webhooks at /webhooks, health at /healthz

Streamable HTTP 传输可服务多个会话,这些会话共用一个 Henrri 令牌和一个 Webhook 收件箱。在反向代理后,将绑定地址设为 0.0.0.0(此时必须提供令牌),并将 Henrri 的 Webhook 回调指向 https://<your-host>/webhooks。Henrri 对每次投递只发送一次,不会重试:接收方会立即响应 204,重复投递也不例外。

验证

cargo fmt --check
cargo clippy --all-targets -- -D warnings
cargo test                      # unit, contract (fake Henrri), stdio and HTTP protocol tests

使用真实沙盒进行验证,并在 .env 中填写沙盒凭据(此操作会创建一份报价草稿并将其删除;不会定稿):

set -a; source .env; set +a
HENRRI_SANDBOX_TESTS=1 cargo test --test sandbox

API 有变动吗?此命令会按 spec/operations.tsv 的格式打印实时操作列表(CI 每天都会针对生产环境和沙盒运行此命令):

scripts/spec-operations.sh | diff - spec/operations.tsv

发布

更新 Cargo.toml 和 server.json 中的 version,在 CHANGELOG.md 中添加一个章节,然后推送 vX.Y.Z 标签。发布工作流会检查三者是否一致,为五个目标平台构建二进制文件,将多架构镜像发布到 GHCR,并根据变更日志发布说明。

贡献

欢迎提交问题和拉取请求。请遵循代码所依循的规则:一条路由对应一个工具,并为真实 API 强制要求的每种行为编写测试。请参阅 CONTRIBUTING.md。

免责声明

Henrri 是其所有者的商标。本项目为非官方项目,与 Henrri 无关,也未获得 Henrri 的认可或支持。本项目基于 Henrri 的公开 v1 API 规范构建,并通过 Henrri 沙盒进行测试;API 变更时,行为也可能随之改变。在生产环境中定稿文档会产生税务后果并消耗 API 额度:您须对以自己名义签发的内容负责。本项目依据 MIT 许可证提供,不附带任何保证。

许可证

MIT © 2026 Edouard Claude

评论

支持 Markdown

第一次接触 MCP?

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

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