首页
/ Storybook Docs for Ember:为 Ember 组件自动生成分类文档、Props 表格与 MDX 长文文档

Storybook Docs for Ember:为 Ember 组件自动生成分类文档、Props 表格与 MDX 长文文档

2026-09-06 15:30:48作者:蔡怀权

本篇技术指南基于 Storybook 官方文档 Storybook Docs for Ember,系统讲解如何在 Ember 项目中接入 @storybook/addon-docs,并覆盖文档中全部四个实战环节:安装与 main.js 注册、DocsPage 自动生成文档、基于 ember-cli-storybook 的 Props 表格(docgen JSON 注入链路)以及 MDX 长文文档与 IFrame 高度配置。结合仓库源码可以看到,Ember 的 docgen JSON 通过 setJSONDoc 挂载到全局变量,再由 Ember 渲染层的 preview 配置消费;读完本篇你将掌握一套在 Ember 项目中完整落地 Storybook Docs 的可复制方案。

一、Storybook Docs 在 Ember 中的能力范围

Storybook Docs 是 Storybook 的文档 Addon,它能把 Storybook 中的 stories 转换成结构化的组件文档。针对 Ember,官方文档明确支持两类能力:

  • DocsPage(自动生成的文档页):每个 story 在 Storybook UI 的 Docs 标签页中获得自动生成的文档;
  • MDX(长文文档):用 Markdown 描述组件,并内嵌 stories、Props 表格等文档组件。

其中 DocsPage 属于"装上即得"的基础能力,而 Props 表格需要额外打通 docgen 数据链路(后文详述)。通用概念可参考 Docs 总览文档DocsPage 参考MDX 参考

说明:原文档顶部注明该页描述的是 Storybook 5.3.0 引入的新版配置方式;如需从旧格式迁移,可参考仓库根目录的 MIGRATION.md

二、安装:注册 @storybook/addon-docs

2.1 添加依赖

首先安装 Addon 包,并确保项目中所有 @storybook/* 包的版本保持一致:

yarn add -D @storybook/addon-docs

从当前仓库的 code/addons/docs/package.json 可以看到,@storybook/addon-docsstorybook 元信息中声明了 "displayName": "Docs",且 unsupportedFrameworks 仅排除了 react-native——Ember 属于其支持的框架范围。

2.2 在 .storybook/main.js 中注册

将 Addon 加入 addons 数组:

export default {
  addons: ['@storybook/addon-docs'],
};

三、DocsPage:自动生成的组件文档页

完成上面的安装后,所有 story 都会自动获得基础版 DocsPage 文档,无需额外代码即可在 Storybook UI 的 Docs 标签页中查看。DocsPage 会自动聚合该 story 的描述、Controls、故事画布等区块,是 Ember 项目落地组件文档的最低成本路径。

四、Props 表格:打通 docgen JSON 数据链路

要为组件生成 Props 表格(ArgsTable),比基础 DocsPage 多几步配置。核心思路是:用 ember-cli 构建过程生成一份 docgen JSON,再把它注入 preview 运行时

4.1 启用 ember-cli-storybook 的文档集成

Docs for Ember 依赖 @storybook/ember-cli-storybook 这个 ember Addon 从组件源文件中提取文档注释。如果项目已用 Storybook 跑 Ember,该 Addon 通常已安装,只需在 ember-cli-build.js 中打开开关:

let app = new EmberApp(defaults, {
  'ember-cli-storybook': {
    enableAddonDocsIntegration: true,
  },
});

4.2 构建产物:/storybook-docgen/index.json

开启后,运行 ember-cli 服务会在 /storybook-docgen/index.json 生成分类 JSON 文档文件。由于生成逻辑挂在 ember-cli 构建流程上,每次保存组件文件都会重新生成该文件,因此文档与源码注释始终保持同步。组件文档注释的写法(如 @class、参数说明等 yuidoc 风格标签)可参照 ember-cli-addon-docs-yuidoc 提供的文档示例。

4.3 用 setJSONDoc 把 JSON 注入 preview

.storybook/preview.js 中加载生成的 JSON 文件:

import { setJSONDoc } from '@storybook/addon-docs/ember';
import docJson from '../dist/storybook-docgen/index.json';

setJSONDoc(docJson);

从源码看这条链路非常简洁,且能解释"为什么叫 set":

也就是说,setJSONDoc 是 preview 构建期写入、渲染期读取的一个全局桥梁,这也是为什么 preview.js 必须在预览构建中被执行、且 import 的是构建后产物路径../dist/storybook-docgen/index.json)。

4.4 在 story 元数据中填写 component 字段

最后一步,在 story 元数据中填写 component 字段,其值必须是字符串,且要与源码注释中使用的 @class 名称一致:

export default {
  title: 'App Component',
  component: 'AppComponent',
};

这个字符串就是 docgen JSON 中的组件索引键:Docs 按 component 名称从 __EMBER_GENERATED_DOC_JSON__ 中查找对应条目并渲染表格,名称不匹配时表格会为空。

五、MDX:以 Markdown 写长文文档并内嵌文档组件

MDX 是用 Markdown 描述组件文档、并内嵌 story 与 Props 表格等文档组件的方式。在 Ember 中使用需注意以下三点。

5.1 补充 react 依赖

Docs Addon 存在对 react 的 peer 依赖(MDX 文档组件在渲染层使用 React 运行时)。若要写 MDX 文档,可能需要额外添加:

yarn add -D react

这一点与仓库事实相符:code/addons/docs/package.json@storybook/addon-docs 声明了 react / react-dom 的依赖区间(^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0),peerDependencies 中也包含 @types/react(可选)。

5.2 让 main.js 的 stories 匹配到 MDX 文件

更新 .storybook/main.js,确保 stories 的 glob 能收集到 MDX 文件:

export default {
  stories: ['../src/stories/**/*.stories.@(js|mdx)'],
};

5.3 一个完整的 Ember MDX 文档示例

import { Meta, Story, ArgsTable } from '@storybook/addon-docs';
import { hbs } from 'ember-cli-htmlbars';

<Meta title='App Component' component='AppComponent' />

# App Component

Some **markdown** description, or whatever you want.

<Story name='basic' height='400px'>{{
  template: hbs`<AppComponent @title={{title}} />`,
context: { title: "Title" },
}}</Story>

## ArgsTable

<ArgsTable of='AppComponent' />

两个来自原文档的实战注意事项:

  1. component 需要声明两次<Meta> 上一次、组件名又一次。原文档指出这是已知冗余,等待后续版本简化(对应 Storybook 侧的 issue #8673),在落地时按现状写即可,不要试图省略其中一处。
  2. Props 文档块依赖 docgen 配置:要使用 ArgsTable / Props 区块,必须先完成第四节的全部 docgen 链路(enableAddonDocsIntegration + setJSONDoc + component 字段),否则表格无法渲染。

六、IFrame 高度:全局、单 story 与 MDX 三级配置

Storybook Docs 在 Ember 中把 story 渲染在 iframe 内,默认高度为 60px。可在三个层面调整:

6.1 全局默认(.storybook/preview.js

export const parameters = { docs: { story: { iframeHeight: '400px' } } };

6.2 DocsPage:单 story 局部覆盖

在 story 上直接设置 parameters

export const basic = () => ...
basic.parameters = {
  docs: { story: { iframeHeight: '400px' } }
}

6.3 MDX:作为 Story 元素属性

<Story name='basic' height='400px'>{...}</Story>

6.4 源码中的取值优先级

code/addons/docs/src/blocks/blocks/Story.tsx 的实现可以看到,故事区块的高度解析存在一条明确的回退链:

props.height ?? storyParameters.height ?? storyParameters.iframeHeight ?? '100px'

MDX 的 height 属性 > story 参数中的 height > story 参数中的 iframeHeight > 兜底值,这与上面临"MDX 属性、单 story 参数、preview 全局参数"三级配置的描述一一对应:外层(更具体)的声明会覆盖全局默认。此外,仓库中 Ember 渲染层的 preview 配置 code/frameworks/ember/src/client/preview/config.ts 也内置了 story: { iframeHeight: '80px' } 的默认值,作为渲染端兜底。

6.5 仓库内的真实用法

仓库自带的 Ember 测试 Storybook 中就有实际用例:test-storybooks/ember-cli/stories/welcome-banner.stories.js 中通过 docs: { story: { iframeHeight: '200px' } } 调整了 story 的 iframe 高度,可作为参照实现。

七、相关文档与延伸阅读

原文档"More resources"部分列出的仓库内参考文档,转换为本仓库的全局路径如下:

结合本仓库源码还可以进一步深入:@storybook/addon-docs 的文档区块组件位于 code/addons/docs/src/blocks/ArgsTableStorySourceControls 等),Ember 渲染端实现位于 code/frameworks/ember/(含 src/client/preview/jsondoc.ts 的 docgen JSON 消费逻辑),可用于验证上文中每一处配置行为。

登录后查看全文
热门项目推荐
相关项目推荐