Flowgram 物料库建设思考与实践

背景

FlowGram 是一套基于节点编辑的流程搭建引擎,帮助开发者快速创建固定布局或自由连线布局模式的流程,并提供一套交互的最佳实践, 很适合有明确输入和输出的可视化工作流。

Flowgram 详细介绍见:flowgram.ai/guide/intro...

Flowgram 即便提供了高灵活度的定制能力,但是实际开发过程中依旧存在问题:

  • 高昂的学习成本: 开发者需要深入理解一系列复杂概念,如实体组件系统 (ECS)、抽象语法树 (AST) 和控制反转 (IoC) 等。
  • 开发效率瓶颈: 对于一些常见的业务场景,从零开始开发新物料的人力成本较高,而这些需求(如变量选择器、JsonSchema 编辑器等)在不同项目中又高度相似。

为了解决这些痛点,我们引入了物料库。 物料库作为 Flowgram 核心引擎之上的一个"外观层"(Facade),将底层的复杂性进行封装,以更直观、更易用的方式提供给开发者,从而极大地提升了开发体验和效率。

我们的物料库在设计上遵循两个核心原则:

  1. 代码简洁易读: 物料的代码应该专注于其核心功能,避免过度封装和复杂的业务逻辑,使其易于理解和维护。
  2. 鼓励通过 Copy-Paste 实现定制: 当官方物料无法满足特定的业务需求时,我们不推荐通过增加复杂的配置项来解决,而是鼓励开发者使用我们的命令行工具(CLI)将物料代码 copy-paste 到本地,进行二次开发。

物料库详见:flowgram.ai/guide/advan...

物料库建设上的一些实践

CLI 复制代码

背景

对于需要实现定制需求的用户,CLI 可以方便的把对应的物料从物料库中拷贝到用户自己的代码仓库里面,并自动处理依赖:

如下图所示,用户需要定制物料B 的逻辑,则他可以使用 CLI 将物料B复制到自己的仓库里,CLI 在复制时,会自动处理物料 B 对物料 C 的依赖:

Case Run Down

假设我想要定制 condition-row 组件:

  1. 运行 npx @flowgram.ai/form-materials ,选择 condition-row 组件:
  1. 代码会自动复制到用户代码仓库的 form-materials/components/condition-row文件夹:
  1. ConditionRow 代码其中对 form-materials 中的其他物料的依赖也会自动更新:
  1. 同时 CLI 会自动在当前项目中,安装相关的依赖项:

具体实现

CLI 复制的整体时序图如图所示:

组件物料的依赖注入

背景

在官方物料库中,组件物料和组件物料之间往往存在复杂的依赖关系,如图所示:

在这样一张复杂的依赖网络中,一些物料组件,如 VariableSelector、TypeSelector,往往处在依赖链的顶端,被大量其余物料直接或者间接依赖。

这些复杂的依赖链路会使这些处在依赖链顶端的物料定制难度加大。

以 VariableSelector 组件为例,他被 DynamicValueInput、BatchOutputs、ConditionRow 直接依赖,又被 InputsValues、ConditionRow 间接依赖。

  1. 用户想要定制 VariableSelector 一个样式,于是使用 CLI 将 VariableSelector 拷贝到本地,并加入样式定制代码:
  1. 用户在使用过程中,DynamicValueInput、BatchOutputs、ConditionRow 等物料直接依赖了VariableSelector,但是没有应用最新的样式。于是将 DynamicValueInput、BatchOutputs、ConditionRow 物料++也拷贝到本地,更改依赖++到用户定制后的 VariableSelector:
  1. 用户再次发现被 InputsValues、ConditionRow等物料还通过 DynamicValueInput 间接依赖了 VariableSelector,没有应用最新的样式,于是把 InputsValues 也拷贝到本地,并更新依赖:

解决思路

依赖反转原则(DIP)主要想告诉我们的是,如果想要设计一个灵活的系统,在源代码层次的依赖关系中就应该多引用抽象类型,而不是具体实现。 《架构整洁之道》

以 VariableSelector 为例,我们让所有物料对 VariableSelector 的依赖,改为对一个抽象的 VariableSelectorRenderKey 的依赖:

如图所示,基于该改造后:

  • 上层所有复杂的物料,不直接依赖 VariableSelector,而是依赖一个抽象的 VariableSelectorRenderKey

  • 物料库中的 VariableSelector实现被绑定到 VariableSelectorRenderKey 上

  • 当用户要定制VariableSelector物料时,将用户修改后的CustomVariableSelector,绑定到 VariableSelectorRenderKey 上即可

Case Run Down

物料库视角: 以 VariableSelector 为例,我希望 VariableSelector 是可依赖注入的,我可以在 VariableSelector 上配置一个 renderKey,接着使用 createInjectMaterial 高阶组件进行封装,封装为 InjectVariableSelector:

使用 createInjectMaterial 将物料封装为可依赖注入的物料

在物料库中,其他用到 VariableSelector的物料,都将引用改为 InjectVariableSelector:

引用 InjectVariableSelector,而不直接是 VariableSelector

用户视角: 在物料库将 VariableSelector 修改为可依赖注入后,我们首先通过 CLI 将 VariableSelector 拷贝到本地:

假设我的修改是把变量选择器的变量选择后的背景改为红色 那么系统中直接使用到定制后的变量选择器的地方会变成红色,但是物料库中依赖VariableSelector的地方,还是原来的样式,如图所示:

用户需要在use-editor-props 中,完成 VariableSelectorRenderKey 与用户定制 MyVariableSelector 之间的绑定:

经过修改后,系统中所有依赖 VariableSelector 的其它物料中,变量选择器的背景都变成了红色,如图所示:

实现

createInjectMaterial 的实现代码见 inject-material/index.tsx

时序图如下所示:

和 ShadeCN 的比对

ShadeCN 是一个广受欢迎的组件库,它和我们的物料库一样,也提供了 copy-paste 的方式让用户使用组件。然而,两者在设计上存在一些关键差异:

  • 架构差异: ShadeCN 倾向于提供原子化、功能单一的组件。而 flowgram 物料库中 物料相互依赖,因此额外提供了依赖注入等能力实现更灵活的定制,CLI 也增加自动处理依赖的能力
  • 生态集成: Flowgram 物料库是为 Flowgram 生态量身打造的,能够无缝地利用 Flowgram 核心引擎提供的状态管理、逻辑编排等能力,这是通用组件库无法比拟的。
  • 物料差异: ShadeCN 以组件物料为主,而 flowgram 物料库结合自己的节点引擎,提供了插件物料、副作用物料、校验器物料等多种物料
相关推荐
用户22152044278003 小时前
Promise实例方法和async、await语法糖
前端·javascript
普通码农3 小时前
uniapp开发微信小程序使用takeSnapshot截图保存分享
前端
snows_l4 小时前
MacOS 通过Homebrew 安装nvm
前端·macos
前端开发爱好者4 小时前
下一代全栈框架:Deno + Vite 的结合体!
前端·javascript·后端
CUGGZ4 小时前
前端部署,又有新花样?
前端·javascript
Zz_waiting.4 小时前
Javaweb 14.4 Vue3 视图渲染技术
前端·javascript·vue.js
前端开发爱好者4 小时前
一键 i18n 国际化神库!适配 Vue、React!
前端·javascript·vue.js
前端开发爱好者4 小时前
Vite 移动端调试利器!开发效率飙升 300%!
前端·javascript·vue.js
BillKu5 小时前
容器元素的滚动条回到顶部
前端·javascript·vue.js