@baishuyun/ai-design 1.2.0 → 1.2.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1 +1 @@
1
- {"version":3,"file":"output-config-editor.d.ts","sourceRoot":"","sources":["../../../src/components/output-config-editor.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAa,wBAAwB,EAAE,WAAW,EAAE,MAAM,EAAiB,MAAM,kBAAkB,CAAC;AAkChH,MAAM,WAAW,uBAAuB;IACtC,KAAK,EAAE,KAAK,CAAC,wBAAwB,CAAC,CAAC;IACvC,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE,KAAK,CAAC,wBAAwB,CAAC,KAAK,IAAI,CAAC;IAE5D,YAAY,CAAC,EAAE,WAAW,EAAE,CAAC;IAC7B,YAAY,CAAC,EAAE,MAAM,EAAE,CAAC;IACxB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAkDD,wBAAgB,kBAAkB,CAAC,EAAE,KAAK,EAAE,QAAQ,EAAE,YAAY,EAAE,YAAY,EAAE,SAAS,EAAE,EAAE,uBAAuB,+BA8UrH"}
1
+ {"version":3,"file":"output-config-editor.d.ts","sourceRoot":"","sources":["../../../src/components/output-config-editor.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAa,wBAAwB,EAAE,WAAW,EAAE,MAAM,EAAiB,MAAM,kBAAkB,CAAC;AAkChH,MAAM,WAAW,uBAAuB;IACtC,KAAK,EAAE,KAAK,CAAC,wBAAwB,CAAC,CAAC;IACvC,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE,KAAK,CAAC,wBAAwB,CAAC,KAAK,IAAI,CAAC;IAE5D,YAAY,CAAC,EAAE,WAAW,EAAE,CAAC;IAC7B,YAAY,CAAC,EAAE,MAAM,EAAE,CAAC;IACxB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAwED,wBAAgB,kBAAkB,CAAC,EAAE,KAAK,EAAE,QAAQ,EAAE,YAAY,EAAE,YAAY,EAAE,SAAS,EAAE,EAAE,uBAAuB,+BA6VrH"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@baishuyun/ai-design",
3
- "version": "1.2.0",
3
+ "version": "1.2.2",
4
4
  "description": "AI 功能 UI 组件库 - 所有 AI 功能的 UI 表现唯一真相来源",
5
5
  "type": "module",
6
6
  "main": "src/index.ts",
@@ -60,8 +60,8 @@
60
60
  "tw-animate-css": "^1.4.0",
61
61
  "vaul": "^1.1.2",
62
62
  "zod": "^4.1.13",
63
- "@baishuyun/ai-feat-utils": "1.2.0",
64
- "@baishuyun/types": "2.2.0"
63
+ "@baishuyun/ai-feat-utils": "1.2.2",
64
+ "@baishuyun/types": "2.2.2"
65
65
  },
66
66
  "peerDependencies": {
67
67
  "react": "^19.0.0",
@@ -83,9 +83,9 @@
83
83
  "typescript": "^5.5.0",
84
84
  "vite": "^5.1.4",
85
85
  "vite-plugin-dts": "^4.5.4",
86
- "@baishuyun/tailwind-config": "2.2.0",
87
- "@baishuyun/types": "2.2.0",
88
- "@baishuyun/typescript-config": "1.2.0"
86
+ "@baishuyun/types": "2.2.2",
87
+ "@baishuyun/tailwind-config": "2.2.2",
88
+ "@baishuyun/typescript-config": "1.2.2"
89
89
  },
90
90
  "keywords": [],
91
91
  "author": "",
@@ -4,7 +4,8 @@ import { AgentTag } from '../agent-tag';
4
4
  import { IconBtn } from '../../icon-btn';
5
5
  import { Switch } from '../../ui/switch';
6
6
  import { EditIcon, CopyIcon, TrashIcon } from '../../bs-icons';
7
- import type { IAgentHelper, IAgentInfo } from '@baishuyun/types';
7
+ import type { IAgentHelper, IAgentInfo, IBsFormService, IEntry } from '@baishuyun/types';
8
+ import { useEffect, useMemo, useState } from 'react';
8
9
 
9
10
  const FORM_ACTION_LABELS: Record<string, string> = {
10
11
  submit: '提交数据',
@@ -19,26 +20,57 @@ const FLOW_NODE_ACTION_LABELS: Record<string, string> = {
19
20
  flow_node: '流程节点',
20
21
  };
21
22
 
22
- function buildTriggerDescription(helper: IAgentHelper): string {
23
+ function useTriggerDescription(helper: IAgentHelper, formService?: IBsFormService): string {
24
+ const [entryInfo, setEntryInfo] = useState<IEntry | undefined>(undefined);
25
+
26
+ const fetchEntryInfo = async (appId: string, entryId: string) => {
27
+ const entryInfo = await formService?.getEntry({ appId, entryId });
28
+ setEntryInfo(entryInfo);
29
+ }
30
+
31
+ useEffect(() => {
32
+ if (!helper.appId || !helper.formId) {
33
+ return;
34
+ }
35
+
36
+ fetchEntryInfo(helper.appId, helper.formId);
37
+ }, [helper.appId, helper.formId])
38
+
39
+ const formName = entryInfo ? entryInfo.name : helper.formId;
40
+ const fieldDict = useMemo(() => {
41
+ const ret: Record<string, string> = {};
42
+ for (const i of (entryInfo?.content.items ?? [])) {
43
+ const key = i.widget?.widgetName ?? "";
44
+ if (!key) {
45
+ continue;
46
+ }
47
+
48
+ ret[key] = i.label;
49
+ }
50
+ return ret;
51
+ }, [entryInfo?.content.items])
52
+
53
+ const widgetName = fieldDict[helper.triggerFieldWidgetName ?? ""] ?? helper.triggerFieldWidgetName;
54
+
23
55
  switch (helper.triggerType) {
24
56
  case 'form_action': {
25
57
  const actions =
26
58
  helper.formActionTriggerType
27
59
  ?.map((a) => FORM_ACTION_LABELS[a] || a)
28
60
  .join('/') || '';
29
- return actions ? `${helper.formId}\n${actions}` : helper.formId;
61
+ return actions ? `${formName}\n${actions}` : formName;
30
62
  }
31
63
  case 'form_flow_node': {
32
64
  const nodes =
33
65
  helper.flowNodeTriggerType
34
66
  ?.map((n) => FLOW_NODE_ACTION_LABELS[n] || n)
35
67
  .join('/') || '';
36
- return nodes ? `${helper.formId}\n${nodes}` : helper.formId;
68
+ return nodes ? `${formName}\n${nodes}` : formName
37
69
  }
38
70
  case 'form_field': {
39
71
  return helper.triggerFieldWidgetName
40
- ? `${helper.formId} / ${helper.triggerFieldWidgetName}`
41
- : helper.formId;
72
+ ? `${formName} / ${widgetName}`
73
+ : formName;
42
74
  }
43
75
  case 'universal':
44
76
  return '开箱即用,无需触发';
@@ -70,6 +102,8 @@ export interface AgentHelperCardProps {
70
102
  onEdit?: () => void;
71
103
  onCopy?: () => void;
72
104
  onDelete?: () => void;
105
+
106
+ formService?: IBsFormService;
73
107
  }
74
108
 
75
109
  export const AgentHelperCard = ({
@@ -82,8 +116,9 @@ export const AgentHelperCard = ({
82
116
  onEdit,
83
117
  onCopy,
84
118
  onDelete,
119
+ formService,
85
120
  }: AgentHelperCardProps) => {
86
- const description = buildTriggerDescription(helper);
121
+ const description = useTriggerDescription(helper, formService);
87
122
  const agent = buildAgentInfo(agentName, agentIcon);
88
123
 
89
124
  return (
@@ -1,6 +1,6 @@
1
1
  import { cn } from '../../../lib/utils';
2
2
  import { AgentHelperCard } from '../agent-helper-card';
3
- import type { IAgentHelper } from '@baishuyun/types';
3
+ import type { IAgentHelper, IBsFormService } from '@baishuyun/types';
4
4
 
5
5
  export interface AgentHelperCardListProps {
6
6
  items: Array<IAgentHelper>;
@@ -12,6 +12,7 @@ export interface AgentHelperCardListProps {
12
12
  onEdit?: (helperId: string) => void;
13
13
  onCopy?: (helperId: string) => void;
14
14
  onDelete?: (helperId: string) => void;
15
+ formService?: IBsFormService;
15
16
  }
16
17
 
17
18
  export const AgentHelperCardList = ({
@@ -24,6 +25,7 @@ export const AgentHelperCardList = ({
24
25
  onEdit,
25
26
  onCopy,
26
27
  onDelete,
28
+ formService,
27
29
  }: AgentHelperCardListProps) => {
28
30
  return (
29
31
  <div
@@ -34,6 +36,7 @@ export const AgentHelperCardList = ({
34
36
  >
35
37
  {items.map((helper) => (
36
38
  <AgentHelperCard
39
+ formService={formService}
37
40
  key={helper.id}
38
41
  helper={helper}
39
42
  agentName={getAgentName?.(helper.agentId)}
@@ -52,18 +52,18 @@ export const TriggerConfigList: Array<TriggerCardConfig> = [
52
52
  minIcon: <FlowNodeTypeIcon size={12} />,
53
53
  iconBgColor: 'rgba(255, 153, 33, 0.1)',
54
54
  },
55
- {
56
- triggerType: 'scheduler',
57
- title: '计划任务触发',
58
- description: '表单中数据发生变化时,触发自动化操作',
59
- icon: (
60
- <div className="text-[#F06648]">
61
- <ScheduleTypeIcon />
62
- </div>
63
- ),
64
- minIcon: <ScheduleTypeIcon size={12} />,
65
- iconBgColor: 'rgba(240, 102, 72, 0.1)',
66
- },
55
+ // {
56
+ // triggerType: 'scheduler',
57
+ // title: '计划任务触发',
58
+ // description: '表单中数据发生变化时,触发自动化操作',
59
+ // icon: (
60
+ // <div className="text-[#F06648]">
61
+ // <ScheduleTypeIcon />
62
+ // </div>
63
+ // ),
64
+ // minIcon: <ScheduleTypeIcon size={12} />,
65
+ // iconBgColor: 'rgba(240, 102, 72, 0.1)',
66
+ // },
67
67
  ];
68
68
 
69
69
  export interface ITriggerSelectProps {
@@ -90,6 +90,28 @@ function flattenSourceFields(fields: OutputFieldOption[]): OutputFieldOption[] {
90
90
  return result;
91
91
  }
92
92
 
93
+ function findFieldByName(fields: OutputFieldOption[], fieldName: string): OutputFieldOption | undefined {
94
+ for (const f of fields) {
95
+ if (f.fieldName === fieldName) return f;
96
+ if (f.children) {
97
+ const found = findFieldByName(f.children, fieldName);
98
+ if (found) return found;
99
+ }
100
+ }
101
+ return undefined;
102
+ }
103
+
104
+ function filterFieldsByType(fields: OutputFieldOption[], targetType: FieldType | ''): OutputFieldOption[] {
105
+ return fields.reduce<OutputFieldOption[]>((acc, f) => {
106
+ const selfMatches = f.type === targetType;
107
+ const filteredChildren = f.children ? filterFieldsByType(f.children, targetType) : [];
108
+ if (selfMatches || filteredChildren.length > 0) {
109
+ acc.push({ ...f, children: filteredChildren.length > 0 ? filteredChildren : f.children });
110
+ }
111
+ return acc;
112
+ }, []);
113
+ }
114
+
93
115
  export function OutputConfigEditor({ value, onChange, sourceFields, targetFields, className }: OutputConfigEditorProps) {
94
116
  const [dropdownTarget, setDropdownTarget] = useState<DropdownTarget>(null);
95
117
  const [searchText, setSearchText] = useState('');
@@ -122,11 +144,18 @@ export function OutputConfigEditor({ value, onChange, sourceFields, targetFields
122
144
 
123
145
  const handleSelectSourceField = useCallback((index: number, field: OutputFieldOption) => {
124
146
  const newValue = [...value];
125
- newValue[index] = { ...newValue[index], sourceField: { fieldName: field.fieldName, fieldDesc: field.fieldDesc } };
147
+ const newItem = { ...newValue[index], sourceField: { fieldName: field.fieldName, fieldDesc: field.fieldDesc } };
148
+ if (newItem.targetField.fieldName) {
149
+ const targetOption = findFieldByName(targetOptions, newItem.targetField.fieldName);
150
+ if (targetOption && targetOption.type !== field.type) {
151
+ newItem.targetField = { fieldName: '', fieldDesc: '' };
152
+ }
153
+ }
154
+ newValue[index] = newItem;
126
155
  onChange?.(newValue);
127
156
  setDropdownTarget(null);
128
157
  setSearchText('');
129
- }, [value, onChange]);
158
+ }, [value, onChange, targetOptions]);
130
159
 
131
160
  const handleSelectTargetField = useCallback((index: number, field: OutputFieldOption) => {
132
161
  const newValue = [...value];
@@ -166,7 +195,7 @@ export function OutputConfigEditor({ value, onChange, sourceFields, targetFields
166
195
  (f) => (matchSearch(f.fieldDesc) || matchSearch(f.fieldName)) && f.type !== 'subform'
167
196
  );
168
197
 
169
- const filteredTargetFields = filterFields(targetOptions);
198
+ const searchedTargetFields = filterFields(targetOptions);
170
199
 
171
200
  const fieldRowCls = cn(
172
201
  'bg-white border border-[#e0e0e0] rounded-[4px] h-[34px] px-[10px] py-[7px]',
@@ -206,7 +235,14 @@ export function OutputConfigEditor({ value, onChange, sourceFields, targetFields
206
235
  'flex flex-col gap-[10px]',
207
236
  className,
208
237
  )}>
209
- {value.map((item, index) => (
238
+ {value.map((item, index) => {
239
+ const selectedSourceType = item.sourceField.fieldName
240
+ ? flatSourceFields.find(f => f.fieldName === item.sourceField.fieldName)?.type
241
+ : undefined;
242
+ const rowTargetFields = selectedSourceType
243
+ ? filterFieldsByType(searchedTargetFields, selectedSourceType)
244
+ : searchedTargetFields;
245
+ return (
210
246
  <div key={index} className="flex gap-[10px] items-center">
211
247
  {/* Source field selector (JSON output field) */}
212
248
  <Popover open={isDropdownOpen(index, 'source')} onOpenChange={(open) => handleDropdownOpenChange(index, 'source', open)}>
@@ -328,7 +364,7 @@ export function OutputConfigEditor({ value, onChange, sourceFields, targetFields
328
364
  />
329
365
  </div>
330
366
  <div className="max-h-[210px] overflow-auto">
331
- {filteredTargetFields.map((field) => {
367
+ {rowTargetFields.map((field) => {
332
368
  const isParent = field.children && field.children.length > 0;
333
369
  const isCollapsed = collapsedParents.has(field.fieldName);
334
370
 
@@ -386,7 +422,7 @@ export function OutputConfigEditor({ value, onChange, sourceFields, targetFields
386
422
  </div>
387
423
  );
388
424
  })}
389
- {filteredTargetFields.length === 0 && (
425
+ {rowTargetFields.length === 0 && (
390
426
  <div className="px-[10px] py-[7px] text-[14px] text-[#999] leading-normal">
391
427
  无匹配结果
392
428
  </div>
@@ -406,7 +442,8 @@ export function OutputConfigEditor({ value, onChange, sourceFields, targetFields
406
442
  </span>
407
443
  </button>
408
444
  </div>
409
- ))}
445
+ );
446
+ })}
410
447
 
411
448
  <button
412
449
  type="button"