关于 build-integration
帮助开发者构建运行于 GitBook 内的 TypeScript 集成,涵盖脚手架、开发和发布流程。内容包括 ContentKit 界面、清单、事件处理、OAuth,以及 GitBook 的服务端运行模型。
主要功能
- 01使用 GitBook CLI 创建集成脚手架
- 02构建自定义 ContentKit 区块
- 03配置权限范围与设置
- 04处理事件和 HTTP 请求
- 05实现 OAuth 流程
- 06开发并发布集成
适用场景
- 01为 GitBook 编辑器添加自定义区块
- 02响应 GitBook 内容或同步事件
- 03将集成连接到外部服务
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ gitbookio/ gitbook-skills --skill build-integration安装后在 Claude Code 中输入/build-integration确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
references/contentkit.mdmanifest.mdruntime.md详细介绍
构建 GitBook 集成
一项用于在 GitBook 开发者平台上构建集成的技能:这类应用运行在 GitBook 内部。集成可以在编辑器中渲染自定义区块、显示配置界面、监听事件(内容更新、Git 同步完成、空间被查看)、通过 OAuth 对外部服务进行身份验证,并通过 HTTP 与任何服务通信。
这项技能涵盖集成的整个生命周期——搭建脚手架、编写代码、开发、发布。若要创建或调整集成可能安装到的文档站点,请参阅 configure-site;若要编写页面内容,请参阅 write-docs。
集成是什么(心智模型)
集成是一个由 GitBook 运行时执行的小型 TypeScript 应用——它不是注入页面的脚本,也不是运行在用户服务器上的代码。以下三点影响着其他所有事项:
- 渲染发生在 GitBook 后端。 组件的
render函数会在每次交互时于服务端运行,并返回 ContentKit 标记(类似 JSX 的 UI 描述)。你无法控制客户端 React 树,无法访问 DOM,UI 更新也会遵循 action → 新状态 → 重新渲染的循环。 - 你无法向站点注入 JavaScript。 你在 GitBook 自有集成中看到的
site:script:inject和site:script:cookies权限范围仅供内部使用。如果用户的需求相当于“向他们的文档添加一个 script 标签”,请尽早说明无法实现——受支持的方式是自定义区块、webframe 和事件。 - 本地开发使用的是代理,而不是供你访问的服务器。
gitbook dev会将已安装集成的流量路由到你的机器。你不会在浏览器中打开开发服务器的端口;而是在 app.gitbook.com 中与集成交互。
项目
gitbook new 会搭建如下结构:
my-integration/
├── gitbook-manifest.yaml # identity, scopes, blocks, configuration schema
├── .gitbook-dev.yaml # local dev config (generated by `gitbook dev`)
├── package.json
└── src/
└── index.tsx # entry file — default-exports createIntegration()
入口文件(即清单中 script: 指向的文件)会默认导出 createIntegration({ fetch, components, events }):
import { createIntegration, createComponent } from '@gitbook/runtime';
const helloBlock = createComponent({
componentId: 'hello-world', // must match a block id in the manifest
initialState: { message: 'Say hello!' },
action: async (element, action, context) => {
switch (action.action) {
case 'say':
return { state: { message: 'Hello world' } };
default:
return {};
}
},
render: async (element, context) => (
<block>
<button label={element.state.message} onPress={{ action: 'say' }} />
</block>
),
});
export default createIntegration({
components: [helloBlock],
events: {
space_content_updated: async (event, context) => {
// react to content changes
},
},
});
只有在两个位置都声明了自定义区块,它才会出现在编辑器的插入面板(⌘ + /)中:代码中的 createComponent,以及清单中的 blocks: 条目,且其 id 与 componentId 匹配。忘记其中一处是“我的区块没显示”最常见的原因。
简要介绍清单
gitbook-manifest.yaml 是集成的身份信息和权限授权文件。必填项:name(在所有 GitBook 中全局唯一——请选择类似 acme-changelog 的带命名空间名称,而不要用 test)、title、description、organization(组织 ID 或子域名)、visibility、scopes 和 script。只申请代码实际使用的权限范围——安装者会看到这些权限。
清单还会声明 blocks、面向安装者的 configurations(账户级和站点级属性模式,渲染为设置表单),以及 secrets(例如 CLIENT_ID: ${{ env.CLIENT_ID }},在发布时加载——使用 dotenv-cli,这样 gitbook publish 才能读取你的 .env)。
字段完整说明、权限范围列表和配置属性类型:references/manifest.md。若要编辑清单的基础配置以外的内容,请阅读该文件。
开发循环
这个循环的顺序不太直观——先发布,再本地开发:
- 准备工作。 Node 18+、从 https://app.gitbook.com/account/developer 获取的个人访问令牌,以及 CLI:
npm install @gitbook/cli -g,然后运行gitbook auth(或gitbook auth --token=<token>)。如果需要在对话中粘贴令牌,请将其导出到环境变量中,切勿将其回显或提交。 - 搭建脚手架。
gitbook new <dir>— 按提示填写名称、标题、组织和权限范围。 - 发布一次。 在项目根目录运行
gitbook publish。这会注册该集成(默认设为私有),并打印安装链接。 - 安装。 通过该链接将其安装到至少一个空间或站点中。安装到某处后,本地开发才能正常运行。
- 开发。
gitbook dev会启动代理:已安装集成的所有流量都会由本地代码提供,而不是已发布的版本。请在 GitBook 编辑器中与其交互,而不是访问服务器 URL。UI 更改需要刷新浏览器;关闭浏览器缓存可让开发循环更顺畅。日志会根据代码的运行位置显示在浏览器控制台或终端中——在认定日志功能失效之前,请检查两处。 - 重新发布。 每当需要更新托管版本时,运行
gitbook publish。运行gitbook unpublish <name>可将其移除。
CLI 命令参考(包括 gitbook whoami 和 gitbook openapi publish):references/manifest.md。
运行时:fetch、事件、环境、OAuth
详细信息和完整表格见 references/runtime.md——编写事件处理程序、OAuth 流程或任何涉及 context.environment 的代码时,请阅读该文档。要点如下:
fetch使用标准 Fetch API 的Request/Response对象处理发往集成公开端点的传入 HTTP 请求。传出 HTTP 请求也直接使用fetch。events将事件名称(installation_setup、space_installation_setup、space_view、ui_render、space_content_updated、space_visibility_updated、space_gitsync_started、space_gitsync_completed)映射到处理程序。部分事件需要匹配的权限范围。context.environment提供apiEndpoint、apiTokens、安装信息(空间、状态、安装者输入的每个安装对应的configuration值)、secrets和公开 URL(environment.integration.urls.publicEndpoint)。- OAuth 对接外部提供方时有固定模式:使用
button类型的配置属性,其callback_url路由到fetch处理程序中的createOAuthHandler({...}),客户端 ID/密钥来自secrets。不要自行编写重定向和令牌交换逻辑。 - 在集成中调用 GitBook API:使用
context.api(经过身份验证的@gitbook/api客户端),而不是根据原始令牌自行构造客户端。
ContentKit:构建 UI
ContentKit 是 render 可以返回的组件词汇:布局(block、vstack、hstack、divider)、展示(box、card、text、image、markdown)和交互元素(button、textinput、select、switch、checkbox、radio、codeblock、webframe、modal)。交互模型可以概括为:输入控件将其值绑定到 state 键;按钮分发操作;action reducer 返回新状态;GitBook 重新渲染。
编写超出简单按钮的组件之前,请阅读 references/contentkit.md——其中包含完整的属性表,以及一些不易猜到的用法模式:用于实时预览的动态状态绑定、webframe 的 postMessage 通信、带 returnValue 的模态框、使用 @editor.node.updateProps 持久化属性、通过 @link.unfurl 和 urlUnfurl 清单模式展开链接,以及 Markdown 代码块对块的序列化。
发布和分享
清单中的可见性决定了覆盖范围:
private(默认)——只有所属组织的成员可以安装。适用于内部工具;开发期间请保持此设置。unlisted——任何组织都可以安装,但只能通过共享的安装链接进行。适用于与特定客户或 Beta 测试人员分享。public——任何人都可以安装;提交到集成市场前必须设为此项(市场采用单独的审核流程——请参阅 GitBook 的“submit your app for review”文档)。
更改可见性后,重新运行 gitbook publish。建议设为 public 之前,请检查清单是否已准备就绪:icon、summary(Markdown,≤2048 个字符)、previewImages(1600×800)、categories、externalLinks。
工作方式
- 从头开始时,使用 CLI 搭建脚手架,而不是手动操作——
gitbook new会正确配置清单、TypeScript 配置和@gitbook/runtime版本。 - 组件出现异常时,追踪区块的 id 链(清单中的
blocks[].id↔componentId)。 - 不要将密钥放在清单文件中——始终使用
${{ env.X }}间接引用,绝不填写字面值。 - 当用户想要从 GitBook 外部 自动化内容或站点时(脚本调用 REST API、CI 流水线),集成可能不是合适的工具——使用个人令牌调用普通 API 更简单。只有当代码必须在 GitBook 内部 运行时,集成才有用:区块、配置 UI、事件响应、代表安装者进行 OAuth 授权。
参考资料
references/manifest.md——介绍gitbook-manifest.yaml中的所有字段、所有范围、配置属性类型、密钥、CLI 命令参考,以及安装/配置流程。references/runtime.md——介绍createIntegration/createComponent/createOAuthHandler的签名、事件目录、context.environment结构,以及 HTTP 请求的收发。references/contentkit.md——完整的组件参考,包含 props、内置操作和交互方案(动态绑定、webframe、模态框、展开预览、Markdown 序列化)。