Skip to main content
Glama

hono-apcore

Hono 适配器,用于 apcore AI-Perceivable 模块生态系统。将 Hono 应用转换为 MCP 工具和 OpenAI 兼容的函数定义——既可以通过显式声明工具,也可以通过扫描已有的路由。

特性

  • 两种方式 — 使用 defineTool() / defineToolset() 声明工具,或零代码更改扫描现有路由

  • 路由重放 — 扫描的路由成为通过 app.request() 回调的模块,因此中间件、验证器和错误处理程序仍然全部运行

  • 单端口mountMcp() 从同一个 Hono 应用提供 MCP 端点、工具浏览器和 /health

  • 注解推断GET → readonly + cacheable, PUT → idempotent, DELETE → destructive(RFC 9110 安全方法语义)

  • 多模式 — TypeBox、Zod 3、Zod 4 和纯 JSON Schema,通过优先级链自动检测

  • 上下文、ACL 和身份apcore() 中间件构建每个请求的 apcore Context,并带有 W3C 跟踪传播,因此 ACL 规则也管理你的路由

  • 运行时无关核心apcore-mcpapcore-cliapcore-a2a 是可选的对等依赖,按需加载,因此导入 hono-apcore 永远不会将 node:http 拖入边缘构建

  • CLIhono-apcore scan | serve | export 可针对普通 Hono 应用工作

  • YAML 绑定 — 以声明方式注册模块,无需修改源代码

Related MCP server: Graft

安装

npm install hono-apcore hono

可选的对等依赖,仅为你使用的功能安装:

npm install apcore-mcp @modelcontextprotocol/sdk   # MCP server + Tool Explorer
npm install @hono/node-server                      # mountMcp() on the Node runtime
npm install apcore-cli                             # CLI surface
npm install apcore-a2a                             # A2A agent surface
npm install @sinclair/typebox                      # TypeBox schemas (recommended)
npm install zod                                    # Zod schemas

要求: Node.js >= 18,Hono >= 4(已在 Hono 4.13 上测试)。

快速开始

1. 声明一些工具

// todo.tools.ts
import { Type } from '@sinclair/typebox';
import { defineToolset } from 'hono-apcore';

export const todoTools = defineToolset({
  namespace: 'todo',
  description: 'Todo list management',
  tags: ['todo'],
  tools: {
    list: {
      description: 'List all todos, optionally filtered by status',
      inputSchema: Type.Object({ done: Type.Optional(Type.Boolean()) }),
      annotations: { readonly: true, idempotent: true },
      handler: (inputs) => ({ todos: store.list(inputs.done as boolean | undefined) }),
    },
    add: {
      description: 'Add a new todo item',
      inputSchema: Type.Object({ title: Type.String() }),
      annotations: { readonly: false },
      handler: (inputs) => ({ todo: store.add(String(inputs.title)) }),
    },
  },
});

2. 将其接入应用

// app.ts
import { Hono } from 'hono';
import { apcore, createApcore } from 'hono-apcore';
import { todoTools } from './todo.tools.js';

export const ap = createApcore({
  tools: todoTools,
  mcp: { name: 'my-app', explorer: true, allowExecute: true },
});

export const app = new Hono();
app.use('*', apcore(ap));
app.get('/todos', (c) => c.json(store.list()));

3. 启动

// main.ts
import { serve } from '@hono/node-server';
import { app, ap } from './app.js';

await ap.init(app);              // register tools + scan routes
await ap.mountMcp(app);          // mount /mcp, /explorer, /health

serve({ fetch: app.fetch, port: 3000 });

你的应用现在响应:

  • REST 位于 http://localhost:3000/todos

  • MCP 位于 http://localhost:3000/mcp

  • 工具浏览器 位于 http://localhost:3000/explorer/

暴露能力的两种方式

defineTool() — 显式工具

这是 NestJS 的 @ApTool 装饰器的 Hono 对应物。Hono 没有可装饰的类或 DI 容器,因此工具是一个携带自身元数据和处理程序的普通对象。

import { defineTool } from 'hono-apcore';

const sendEmail = defineTool({
  namespace: 'email',
  name: 'send',                 // -> module id "email.send"
  description: 'Send an email',
  inputSchema: Type.Object({ to: Type.String(), body: Type.String() }),
  outputSchema: Type.Object({ messageId: Type.String() }),
  annotations: { readonly: false, destructive: false, requiresApproval: true },
  tags: ['email'],
  params: { to: 'Recipient address' },   // merged into the schema descriptions
  handler: async (inputs, context) => mailer.send(inputs, context),
});

字段

说明

id

原样使用。否则为 "<namespace>.<name>",其中 name 为蛇形命名

inputSchema / outputSchema

TypeBox、Zod 或纯 JSON Schema

annotations

readonlydestructiveidempotentrequiresApprovalopenWorldstreamingcacheable

params

每个参数的说明文本合并到输入模式中。JavaScript 无法像 Python 读取 docstring 那样在运行时读取函数的前导注释,因此这是显式的

handler

(inputs, context) => result。非对象结果会被包装为 { result }

路由扫描 — 零侵入工具

将扫描器指向应用,每个路由都会成为一个通过 app.request() 在进程内重放它的模块:

const ap = createApcore({
  routes: {
    excludePaths: ['/health', '/mcp*', '/explorer*'],
    modulePrefix: 'api',
  },
});

await ap.init(app);   // -> api.todos.list, api.todos.get, api.todos.create, …

模块 ID 来自路径和 HTTP 动词:

路由

模块 ID

推断的注解

GET /todos

todos.list

readonly, cacheable

GET /todos/:id

todos.get

readonly, cacheable

POST /todos

todos.create

PUT /todos/:id

todos.update

idempotent

DELETE /todos/:id

todos.delete

destructive

生成的输入模式为每个路径参数携带一个必需的字符串属性,外加一个自由形式的 query 对象(GET/DELETE)或 body 对象(POST/PUT/PATCH)。可以按路由覆盖其中任何部分:

routes: {
  overrides: {
    'GET /todos': {
      id: 'todo.all',
      description: 'Every todo, newest first',
      inputSchema: Type.Object({ done: Type.Optional(Type.Boolean()) }),
      annotations: { readonly: true, idempotent: true },
    },
    'DELETE /admin/wipe': { skip: true },
  },
}

由于执行通过 app.request() 返回,AI 调用与 HTTP 调用运行相同的代码路径——包括认证中间件、验证器、错误处理程序等。来自 apcore Context 的身份和 W3C 跟踪头会被转发到重放的请求上。

API 参考

createApcore(options)

返回一个 HonoApcore — 注册表、执行器和所有表面都挂载在它上面。

createApcore({
  extensionsDir?: string | null,   // scanned by Registry.discover()
  acl?: ACL,                       // enforced by the Executor on every call
  middleware?: Middleware[],       // apcore middleware installed on the Executor
  bindings?: string,               // YAML bindings file loaded during init()
  tools?: ApToolDefinition[],      // registered during init()
  routes?: RouteScanOptions,       // route-scanner configuration
  settings?: Partial<ApcoreSettings>,  // overrides for the APCORE_* settings
  mcp?: ApcoreMcpOptions,          // presence enables the MCP surface
  cli?: ApcoreCliOptions,          // presence enables the CLI surface
  a2a?: ApcoreA2aOptions,          // presence enables the A2A surface
})

方法

说明

init(app?, routeOptions?)

发现、注册工具和绑定,扫描路由,启动独立表面。幂等

ready()

等待进行中的 init()

registerTool(tool) / registerTools(tools)

在运行时注册工具定义

registerMethod(opts) / registerObject(opts)

注册普通服务对象的方法

scanRoutes(app, opts?)

扫描并注册应用的路由

routeOptions

此实例将使用的合并路由扫描选项

loadBindings(path?, resolver?)

加载 YAML 绑定文件

mountMcp(app, opts?)

/mcp、浏览器和 /health 挂载到应用中

toOpenaiTools(opts?)

OpenAI 兼容的函数定义

close()

关闭 MCP 和 A2A 表面

apcore(instance | options, middlewareOptions?)

Hono 中间件,将实例和每个请求的 apcore Context 放到 Hono 上下文上。

app.use('*', apcore(ap));

app.get('/orders', async (c) =>
  c.json(await getApcore(c).executor.call('orders.list', {}, getApcoreContext(c))),
);

变量映射被增强,因此 c.get('apcore')c.get('apcoreContext') 也有类型。在从不调用模块的路由上传递 { skipContext: true },或传递 { contextFactory } 以接入真实认证。

HonoContextFactory

从 Hono 上下文、Request 或裸 Headers 构建 apcore Context

身份解析顺序:x-user-idAuthorization: Bearer …(身份 id "bearer")→ 裸 x-roles 头(演示快捷方式)→ 匿名。traceparent 头提供跟踪 id;x-correlation-id(或 x-request-id)进入 context.data

new HonoContextFactory({
  resolveIdentity: (headers) => identityFromSession(headers),  // wins over the above
  data: (headers) => ({ tenant: headers.get('x-tenant') }),
});

MCP

ApcoreMcpService 以两种方式运行 MCP 服务器。

嵌入式 — 一个进程,一个端口:

await ap.mountMcp(app, { endpoint: '/mcp', explorer: true, allowExecute: true });

这需要 @hono/node-serverc.env 上暴露的原始 Node 请求和响应对象,因此仅限 Node;其他运行时上的挂载处理程序会以该说明回答 501endpoint 必须是 HTTP 服务器看到的路径——如果应用位于 basePath 下,请包含前缀。

独立 — 单独的端口,或用于 CLI 启动的服务器的 stdio:

createApcore({ mcp: { transport: 'streamable-http', host: '0.0.0.0', port: 8000 } });
// init() starts it, because `transport` was set explicitly

关键 MCP 选项:

字段

类型

说明

transport

'stdio' | 'streamable-http' | 'sse'

独立传输。设置它会使 init() 启动服务器

host / port

string / number

HTTP 传输的绑定地址

name / version

string

服务器身份

explorer / explorerPrefix / allowExecute

工具浏览器 Web UI

authenticator / requireAuth / exemptPaths

JWT 或自定义认证

tags / prefix

仅暴露匹配的模块

validateInputs

boolean

在每次调用时强制执行输入模式

observability

指标 + 使用中间件及其端点

outputFormat / outputFormatter / redactOutput / trace

结果序列化

approvalHandler / approvalStore / approvalNotify

破坏性工具的审批门

mcpMiddleware / mcpAcl

为 MCP 执行器提供的额外 apcore 中间件 / ACL

模式适配器

模式通过优先级链自动检测和转换:

适配器

优先级

输入

TypeBoxAdapter

100

@sinclair/typebox 模式

ZodAdapter

50

Zod 3(_def.typeName)和 Zod 4(_zod.def.type

JsonSchemaAdapter

30

纯 JSON Schema 对象

检测是结构性的——运行时不会导入 TypeBox 或 Zod——因此宿主应用安装哪个(或都不安装)都可以。使用 SchemaExtractor.registerAdapter() 注册你自己的适配器。

YAML 绑定

无需修改源代码即可注册模块:

bindings:
  - module_id: email.send
    target: EmailService.send
    description: Send an email
    input_schema:
      type: object
      properties:
        to: { type: string }
    tags: [email, mutate]
    annotations:
      readonly: false
import { resolverFromObjects } from 'hono-apcore';

await ap.loadBindings('./bindings.yaml', resolverFromObjects({ EmailService: mailer }));

反过来,writeBindingsFile() 将扫描的模块序列化输出——这正是 hono-apcore scan --format yaml 所做的。

CLI

hono-apcore scan   ./src/app.ts            # print the modules a scan would produce
hono-apcore scan   ./src/app.ts --format yaml --out bindings.yaml
hono-apcore serve  ./src/app.ts --transport http --port 8000 --explorer
hono-apcore export ./src/app.ts --out tools.json

入口是 path[:export];导出默认为 default,然后是 app。如果模块以任何名称导出 HonoApcore,其配置——路由过滤器、模块前缀、MCP 选项——会被尊重,因此 scan 报告应用自身注册的模块;CLI 标志会覆盖它。没有实例的入口仍然有效,因此 serve 可以针对从未听说过 apcore 的应用运行。TypeScript 入口需要加载器:

npx tsx node_modules/.bin/hono-apcore scan ./src/app.ts

配置(APCORE_*

每个 apcore 集成实现的标准设置,从环境读取并可通过 settings 覆盖:

Variable

Type

Default

Purpose

APCORE_ENABLED

bool

true

主开关——false 使 init() 成为空操作

APCORE_DEBUG

bool

false

详细日志/内省

APCORE_SCANNERS

list

["auto"]

启用的扫描器标识符

APCORE_INCLUDE_PATHS

list

[]

要包含的路由模式(空 = 全部)

APCORE_EXCLUDE_PATHS

list

[]

要排除的路由模式

APCORE_MODULE_PREFIX

str

""

附加到生成的模块 ID 的前缀

APCORE_AUTH_ENABLED

bool

false

MCP/A2A 端点需要身份验证

APCORE_AUTH_STRATEGY

str

"bearer"

bearer / session / custom

APCORE_TRANSPORT

str

"stdio"

MCP 传输:stdio / http / sse

APCORE_HOST

str

"0.0.0.0"

当传输不是 stdio 时的绑定地址

APCORE_PORT

int

8808

当传输不是 stdio 时的绑定端口

可选对等依赖不会被重新导出

与 NestJS 适配器不同,hono-apcore 重新导出 apcore-mcp / apcore-cli / apcore-a2a 接口。这样做会使它们被急切加载,而 apcore-mcp 会引入 node:http——这会破坏从不使用 MCP 接口的 Workers、Deno 或 Bun 应用构建。请从它们各自的包中导入这些符号:

import { JWTAuthenticator, getCurrentIdentity } from 'apcore-mcp';
import { createCli } from 'apcore-cli';
import { A2AClient } from 'apcore-a2a';

apcore-jsapcore-toolkit 硬依赖,因此它们的公共符号(ACLConfigregisterSysModulesTraceContextBaseScannerformatModules 等)直接从 hono-apcore 重新导出。

示例

示例

展示

examples/demo

完整应用:手写工具路由扫描、JWT、ACL、系统模块、Docker

examples/acl_demo

由 apcore ACL 管理的路由——orders.delete 仅限管理员

pnpm install && pnpm build
cd examples/demo && pnpm install && pnpm dev

详细文档

脚本

命令

描述

pnpm build

编译 TypeScript

pnpm dev

监视模式编译

pnpm test

运行测试套件(vitest)

pnpm test:coverage

带覆盖率的测试(90% 阈值)

pnpm typecheck

类型检查(不输出)

pnpm lint

检查源代码和测试

许可证

Apache-2.0

A
license - permissive license
Not graded
quality - not tested
B
maintenance

Maintenance

Maintainers
Response time
Release cycle
1Releases (12mo)
Commit activity

Resources

Unclaimed servers have limited discoverability.

Looking for Admin?

If you are the server author, to access and configure the admin panel.

Related MCP Servers

  • A
    license
    Not graded
    quality
    D
    maintenance
    Exposes Hono API endpoints as Model Context Protocol tools, allowing LLMs to interact with your API routes through a dedicated MCP endpoint. It provides helpers to describe routes and includes a codemode for dynamic API interaction via search and execute tools.
    32
    86
    MIT
  • A
    license
    Not graded
    quality
    C
    maintenance
    Enables building agent-ready APIs that expose tools as both HTTP and MCP endpoints from a single server definition, with automatic OpenAPI, discovery docs, and interactive API reference.
    5
    Apache 2.0
  • A
    license
    B
    quality
    C
    maintenance
    Transforms OpenAPI definitions into MCP tools for seamless LLM-API integration.
    8
    39
    1
    MIT
  • A
    license
    Not graded
    quality
    C
    maintenance
    Easily expose your Hono API endpoints as MCP tools with minimal configuration, supporting type-safe input handling and tool registration.
    32
    2
    MIT

View all related MCP servers

Related MCP Connectors

  • Point Gecko at an OpenAPI spec; get first-call-correct, auth-hidden agent tools.

  • Free public MCP for AI agents — 193 tools, 44 workflows. No API key.

  • MCP server for AI agents to plan, verify, and deploy Cloudflare-native apps.

View all MCP Connectors

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/aiperceivable/hono-apcore'

If you have feedback or need assistance with the MCP directory API, please join our Discord server