Skip to content

通过 React JS SDK 集成

react js sdk 与任何 github / npm 第三方库类似,提供了 Completion UI 组件和 useProvider hook,适用于将衡石 ChatBI 的能力以及图表集成在你自己的 react 项目中。

react 版本

支持的 react 版本为 18,我们提供的 sdk 内不包含 react 及 react-dom。

此外,sdk 内包含依赖了下列第三方库:

  • antd v4
  • core-js v3
  • zrender v5
  • lodash v4
  • marked v15
  • moment
  • react-i18next

若你的 react 项目也有使用同样的依赖库,可以联系售后进行沟通,我们可以提供排除重复依赖后的 sdk 包,以避免多余的资源加载。

提示

我们提供的 sdk 包已经是排除 react 后的压缩版本,你的项目在打包时,应避免再次将 sdk 文件进行压缩和混淆。

快速开始

  1. 安装与引入 由于 React JS SDK 不提供 npm 包,请与售后联系,或通过邮箱 support@hengshi.com 进行咨询。

示例项目结构

plaintext
<你的项目>/
├── src/
|   ├── hengshi/   <-- 例如将 SDK 放在您项目源码中的这里
│   ├── index.ejs
│   └── index.js
└── package.json
  1. 渲染一个 Completion 组件

示例 index.js

jsx
import React from "react";
import { createRoot } from "react-dom/client";

import Completion from "./hengshi";

function ReactApp() {
  const chat = { // 此对象数据结构来自衡石 ChatBI 后端
    "meta": "refineQuestion,answer,chart,chartConfig", // meta 属性可以控制组件渲染哪些内容
    "conversationId": 226,
    "uid": "00747081-9cc3-4c7c-b3de-735244498fd6",
    "prompt": "bug issue的模块分布情况",
    "answer": "bug issue在各模块中的分布较均匀,最多的模块有4个bug,其余大部分模块有2-3个bug。",
    "refineQuestion": "请提供bug issue在各模块中的分布情况",
    "charts": [
      {
        "appId": 134683,
        "datasetId": 1,
        "options": {
          "axes": [
            {
              "op": "{{41}}.{title}",
              "uid": "uid1",
              "kind": "formula"
            },
            {
              "op": "count({{33}}.{issue_id})",
              "uid": "uid2",
              "kind": "formula"
            }
          ],
          "limit": 100
        }
      }
    ]
  };

  return <Completion {...chat} />;
}

const root = createRoot(document.getElementById("root"));
root.render(<ReactApp />);

渲染后如图所示:

react-sdk-example

useProvider hook

useProvider 是我们提供一个 React Hook,等价于 vanilla js sdk 中的 new Copilot(...) 操作。hook 是为了更适配 react 项目。

useProvider hook 的返回值参考 copilot 实例。通过此 hook 你可以实现在 react 项目中创建衡石 ChatBI 对话、渲染图表等功能。

示例:

jsx
import React from "react";
import { createRoot } from "react-dom/client";

import Completion, { useProvider } from "./hengshi";

function ReactApp() {
  const [chat, setChat] = React.useState();
  const [prompt, setPrompt] = React.useState('用户输入的问题');
  const [dataSources, setDataSources] = React.useState([{"dataAppId":134683,"datasetId":1}]); // 对话数据源
  const provider = useProvider({
    baseUrl: 'http://localhost:8881', // 衡石服务地址
    pollingInterval: 1000, // 轮询间隔,单位毫秒
  });
  const onSend = () => {
    provider.context.onCreateChat({
      prompt, // 这里是用户的问题
      userConfig: {
        dataSources,
      },
    }, _chat => {
      setChat(_chat);
      provider.context.onWaitingChat(_chat.conversationId, _chat.uid, setChat);
    });
  };

  return (
    <div>
      <input onChange={e => setPrompt(e.target.value)} />
      <button onClick={onSend}>发送</button>
      {chat ? <Completion {...chat} /> : null}
    </div>
  );
}

const root = createRoot(document.getElementById("root"));
root.render(<ReactApp />);

Shadow DOM 说明

为了避免样式冲突,组件使用了 Shadow DOM 进行渲染,确保组件的样式不会影响或被外部应用影响。

SDK 目录结构

plaintext
hengshi/
├── index.css        # 样式表文件
├── index.js         # 主 SDK 入口
├── index.esm.js     # 主 SDK 入口
├── font/            # 字体资源
│   ├── fontello.eot
│   ├── fontello.ttf
│   ├── fontello.woff
│   └── fontello.woff2
└── locales/         # 语言包
    ├── en-US.json
    ├── zh-CN.json

组件 API 参考

正如前边示例中所示,Completion 组件接受 chat 数据作为参数,该对象是衡石对话回合的数据内容,可以通过 GET /api/conversations/${conversationId}/chats/${uid} 接口获取到,数据结构参考 chat

除了 chat 对象的所有属性之外,Completion 组件还接受以下参数:

参数类型说明
metaSTRING'refineQuestion', 'answer', 'chart', 'chartSwitcher', 'chartConfig' 等几个字符串的任意组合,以逗号(',')分割,可以用来自定义展示内容
disableEllipsisBOOL为 true 时,不会将答案和取数逻辑的 tag 折叠或省略显示
showWhenNoDataBOOL当没有数据时是否显示图表组件,默认为 false
chartThemeSTRING仪表盘主题 ID,参考主题颜色
stylesheetsSTRING 或 STRING ARRAY样式表链接 或者 样式表内容,用于自定义样式
localeSTRING多语言,默认 'zh-CN', 支持 'zh-CN'、'en-US'、'zh-TW'、'ja-JP'
onChangeChartTypeFUNCTION图表类型切换回调函数,传递此参数后,图表上方会出现切换图表类型的 icon 按钮
parserOBJECT配置项
parser.onSelectFUNCTION传递此参数后,图表右上角会出现一个 + 号 icon 按钮,点击按钮会触发此函数
parser.selectedTextSTRING字符串将作为 + 号 icon 按钮的 Tooltip 内容
onReadyFUNCTION初次渲染时的回调函数

常见问题

提示未登录,如何解决?

参考 登录认证 部分,在组件渲染之前需要先完成登录认证。

如何自定义样式?

由于使用了 Shadow DOM,您需要通过 stylesheets 传参进行样式修改, stylesheets 接收字符串或者字符串数组,同时支持样式表链接和样式表内容,例如:

jsx
const stylesheets = [ // 可以使用外部常量避免 react 组件重新渲染
  'https://cdn.example.com/custom.css',
  `.custom-class { color: red; }`,
];

function ReactApp() {
  return <Completion
    {...chat}
    stylesheets={stylesheets} />;
}

在 rspack 项目里怎么使用?

联系售后获取 sdk 包,解压后是 hengshi 文件夹,将 hengshi 目录放到你项目的 public 文件夹内(因为 sdk 有静态资源文件需要被 rspack devServer 提供服务),就可以启动你项目的开发模式了。

然后还需要修改 rspack config 文件:

  1. 在 rspack config minimizer 的 rspack.SwcJsMinimizerRspackPlugin 配置内增加 exclude: /hengshi/,避免 sdk js 文件被二次压缩(因为二次压缩是无意义的,浪费打包时间)。
  2. 在 rspack config plugins 里增加 rspack.CopyRspackPlugin,将 hengshi 目录拷贝到打包输出目录,例如:
js
export default defineConfig({
  // ...
  optimization: {
    minimizer: [
      // ...
      new rspack.SwcJsMinimizerRspackPlugin({
        exclude: /hengshi/,
      }),
    ],
  },
  plugins: [
    // ...
    new rspack.CopyRspackPlugin({
      patterns: [
        { from: 'public/hengshi', to: 'hengshi' },
      ],
    }),
  ],
});

示例:

在 vite 项目里怎么使用?

联系售后获取 sdk 包,解压后是 hengshi 文件夹,将 hengshi 目录放到你项目的 src 文件夹内,就可以启动你项目的开发模式了。

然后还需要修改 vite config 文件:

  1. 在 vite config 的 optimizeDeps 配置内增加 exclude: ['hengshi'],避免 sdk js 文件被 vite 优化(因为 vite 优化是无意义的,浪费打包时间)。
  2. 安装 vite-plugin-static-copy 插件,然后在 vite config 的 plugins 配置内增加
js
import { defineConfig } from 'vite'
import react from '@vitejs/plugin-react'
import { viteStaticCopy } from 'vite-plugin-static-copy'

// https://vite.dev/config/
export default defineConfig({
  optimizeDeps: {
    exclude: ['hengshi'],
  },
  plugins: [
    react(),
    viteStaticCopy({
      targets: [
        {
          src: 'src/hengshi',
          dest: 'assets',
        },
      ],
    }),
  ],
});

示例:

在 umi 项目里怎么使用?

联系售后获取 sdk 包,解压后是 hengshi 文件夹,将 hengshi 目录同时放到你项目的 publicsrc 文件夹内即可。

示例:

衡石分析平台使用手册