@fastspace/schema-form 0.0.15 → 2.0.0
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.
- package/dist/index.d.ts +1718 -361
- package/dist/schema-form-lib.js +10306 -8659
- package/dist/schema-form-lib.umd.cjs +13 -111
- package/package.json +27 -23
package/dist/index.d.ts
CHANGED
|
@@ -1,377 +1,1087 @@
|
|
|
1
|
-
|
|
1
|
+
/**
|
|
2
|
+
* Next-Gen Schema Form (V4)
|
|
3
|
+
*
|
|
4
|
+
* 基于 TanStack Form 的声明式表单引擎
|
|
5
|
+
*
|
|
6
|
+
* @packageDocumentation
|
|
7
|
+
*/
|
|
8
|
+
|
|
9
|
+
import { CheckboxProps } from '@mui/material';
|
|
2
10
|
import { default as default_2 } from 'react';
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
11
|
+
import { FC } from 'react';
|
|
12
|
+
import { FormApi } from '@tanstack/react-form';
|
|
13
|
+
import { FormHTMLAttributes } from 'react';
|
|
5
14
|
import { JSX } from 'react/jsx-runtime';
|
|
6
|
-
import {
|
|
15
|
+
import { JSXElementConstructor } from 'react';
|
|
16
|
+
import { NamedExoticComponent } from 'react';
|
|
17
|
+
import { RadioProps } from '@mui/material';
|
|
18
|
+
import { ReactElement } from 'react';
|
|
7
19
|
import { ReactNode } from 'react';
|
|
8
|
-
import {
|
|
20
|
+
import { ReactPortal } from 'react';
|
|
21
|
+
import { SwitchProps } from '@mui/material';
|
|
22
|
+
import { SxProps } from '@mui/material';
|
|
23
|
+
import { TextFieldProps } from '@mui/material';
|
|
24
|
+
import { Theme } from '@mui/material';
|
|
9
25
|
import * as v from 'valibot';
|
|
10
26
|
|
|
11
|
-
/** 自动完成(支持多选、远程搜索、分页) */
|
|
12
|
-
declare const AutocompleteWidget: WidgetComponent;
|
|
13
|
-
export { AutocompleteWidget }
|
|
14
|
-
export { AutocompleteWidget as SelectWidget }
|
|
15
|
-
|
|
16
27
|
/**
|
|
17
|
-
*
|
|
28
|
+
* 分析结果
|
|
18
29
|
*/
|
|
19
|
-
export declare
|
|
30
|
+
export declare type AnalysisResult = {
|
|
31
|
+
/** 反向依赖索引: Dep -> Rules */
|
|
32
|
+
dependencyMap: Map<string, SchemaRule[]>;
|
|
33
|
+
/** 拓扑排序序列 */
|
|
34
|
+
topologicalOrder: string[];
|
|
35
|
+
/** 所有检测到的循环 */
|
|
36
|
+
cycles: string[][];
|
|
37
|
+
/** 孤立字段 */
|
|
38
|
+
isolatedFields: string[];
|
|
39
|
+
/** 静态分析报告 */
|
|
40
|
+
report: StaticAnalysisReport;
|
|
41
|
+
};
|
|
20
42
|
|
|
21
|
-
|
|
22
|
-
export declare const CheckboxWidget: WidgetComponent;
|
|
43
|
+
declare type AnyFormApi = FormApi<any, any, any, any, any, any, any, any, any, any, any, any>;
|
|
23
44
|
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
45
|
+
declare type AnyFormApi_2 = FormApi<any, any, any, any, any, any, any, any, any, any, any, any>;
|
|
46
|
+
|
|
47
|
+
declare type AnyFormApi_3 = any;
|
|
48
|
+
|
|
49
|
+
declare type AnyFormApi_4 = any;
|
|
50
|
+
|
|
51
|
+
/**
|
|
52
|
+
* 异步选项配置(带依赖)
|
|
53
|
+
*/
|
|
54
|
+
export declare type AsyncOptionsConfig = {
|
|
55
|
+
/** 异步获取选项的函数 */
|
|
56
|
+
fetcher: (scope: EvalScope, signal?: AbortSignal) => Promise<any[]>;
|
|
57
|
+
/**
|
|
58
|
+
* 依赖的字段列表,当这些字段值变化时重新加载选项
|
|
59
|
+
* @example deps: ['province'] - 当 province 变化时重新加载
|
|
60
|
+
*/
|
|
61
|
+
deps: string[];
|
|
62
|
+
};
|
|
63
|
+
|
|
64
|
+
/**
|
|
65
|
+
* 异步任务调度器 (V4 Enhanced)
|
|
66
|
+
* 负责处理 Options 请求、异步计算等
|
|
67
|
+
*
|
|
68
|
+
* 特性:
|
|
69
|
+
* - Race Control: AbortController + VersionHash
|
|
70
|
+
* - Stable Hash: 基于内容的稳定哈希
|
|
71
|
+
* - 缓存管理: LRU 策略
|
|
72
|
+
* - 请求去重: 相同 hash 的请求复用
|
|
73
|
+
*/
|
|
74
|
+
export declare class AsyncScheduler {
|
|
75
|
+
private cache;
|
|
76
|
+
private activeRequests;
|
|
77
|
+
private pendingPromises;
|
|
78
|
+
private config;
|
|
79
|
+
constructor(config?: AsyncSchedulerConfig);
|
|
80
|
+
/**
|
|
81
|
+
* 执行异步任务
|
|
82
|
+
* @param target 目标字段 (用于取消互斥请求)
|
|
83
|
+
* @param hash 版本哈希 (deps hash)
|
|
84
|
+
* @param fetcher 异步函数
|
|
85
|
+
* @param scope 执行作用域
|
|
86
|
+
* @returns Promise<any>
|
|
87
|
+
*/
|
|
88
|
+
schedule(target: string, hash: string, fetcher: (scope: EvalScope, signal: AbortSignal) => Promise<any>, scope: EvalScope): Promise<any>;
|
|
89
|
+
/**
|
|
90
|
+
* 设置缓存 (带 LRU 策略)
|
|
91
|
+
*/
|
|
92
|
+
private setCache;
|
|
93
|
+
/**
|
|
94
|
+
* 生成稳定的依赖哈希
|
|
95
|
+
* 使用排序后的 JSON 确保相同内容生成相同 hash
|
|
96
|
+
*/
|
|
97
|
+
generateHash(deps: Record<string, any>): string;
|
|
98
|
+
/**
|
|
99
|
+
* 稳定的 JSON 序列化 (对象键排序)
|
|
100
|
+
*/
|
|
101
|
+
private stableStringify;
|
|
102
|
+
/**
|
|
103
|
+
* 取消指定目标的请求
|
|
104
|
+
*/
|
|
105
|
+
cancel(target: string): void;
|
|
106
|
+
/**
|
|
107
|
+
* 取消所有请求
|
|
108
|
+
*/
|
|
109
|
+
cancelAll(): void;
|
|
110
|
+
/**
|
|
111
|
+
* 清除缓存
|
|
112
|
+
*/
|
|
113
|
+
clearCache(target?: string): void;
|
|
114
|
+
/**
|
|
115
|
+
* 获取缓存统计
|
|
116
|
+
*/
|
|
117
|
+
getCacheStats(): {
|
|
118
|
+
size: number;
|
|
119
|
+
maxSize: number;
|
|
120
|
+
keys: string[];
|
|
46
121
|
};
|
|
122
|
+
/**
|
|
123
|
+
* 使缓存条目失效
|
|
124
|
+
*/
|
|
125
|
+
invalidate(target: string, hash?: string): void;
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
/**
|
|
129
|
+
* AsyncScheduler 配置
|
|
130
|
+
*/
|
|
131
|
+
export declare type AsyncSchedulerConfig = {
|
|
132
|
+
/** 缓存过期时间 (ms),默认 5 分钟 */
|
|
133
|
+
staleTime?: number;
|
|
134
|
+
/** 最大缓存条目数 */
|
|
135
|
+
maxCacheSize?: number;
|
|
136
|
+
/** 请求超时时间 (ms),默认 30 秒 */
|
|
137
|
+
timeout?: number;
|
|
138
|
+
/** 是否启用请求去重 (同 hash 的请求只发一次) */
|
|
139
|
+
deduplication?: boolean;
|
|
47
140
|
};
|
|
48
141
|
|
|
49
|
-
|
|
50
|
-
export declare type ComponentType = 'Text' | 'Number' | 'Password' | 'Textarea' | 'Select' | 'Autocomplete' | 'Checkbox' | 'Switch' | 'Radio' | 'Slider' | 'Rating' | 'Date' | 'Time' | 'DateTime' | 'Upload' | 'Hidden' | 'Custom' | 'Group' | 'FormList';
|
|
142
|
+
export declare const AutocompleteWidget: default_2.FC<AutocompleteWidgetProps>;
|
|
51
143
|
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
144
|
+
export declare type AutocompleteWidgetProps = {
|
|
145
|
+
form: any;
|
|
146
|
+
name: string;
|
|
147
|
+
validate?: any;
|
|
148
|
+
} & Omit<AutocompleteWidgetRenderProps, keyof WidgetProps>;
|
|
149
|
+
|
|
150
|
+
export declare const AutocompleteWidgetRender: default_2.NamedExoticComponent<AutocompleteWidgetRenderProps>;
|
|
151
|
+
|
|
152
|
+
export declare type AutocompleteWidgetRenderProps = WidgetProps & {
|
|
153
|
+
label?: string;
|
|
154
|
+
placeholder?: string;
|
|
155
|
+
helperText?: string;
|
|
156
|
+
multiple?: boolean;
|
|
157
|
+
freeSolo?: boolean;
|
|
158
|
+
loading?: boolean;
|
|
159
|
+
/** 远程搜索配置 */
|
|
160
|
+
remoteConfig?: RemoteConfig;
|
|
161
|
+
/** 指定选项显示文本的字段,默认 "label" */
|
|
162
|
+
optionLabelProp?: string;
|
|
163
|
+
/** 指定选项绑定值的字段,默认 "value" */
|
|
164
|
+
optionValueProp?: string;
|
|
165
|
+
/** 无数据时下拉面板提示文本 */
|
|
166
|
+
emptyText?: string;
|
|
167
|
+
/** 是否显示添加按钮(函数式控制或布尔值) */
|
|
168
|
+
showAddSuffix?: boolean | SuffixButtonRender;
|
|
169
|
+
/** 是否显示清空按钮 */
|
|
170
|
+
clearable?: boolean;
|
|
171
|
+
/** Suffix 按钮渲染函数 */
|
|
172
|
+
suffixButton?: SuffixButtonRender;
|
|
173
|
+
/** 添加选项成功回调 */
|
|
174
|
+
onAddOptionSuccess?: OnAddOptionSuccess;
|
|
175
|
+
/** 添加新选项后自动选中,默认 false */
|
|
176
|
+
autoSelectNewOption?: boolean;
|
|
177
|
+
/** 每次展开时刷新数据,默认 false (仅首次加载) */
|
|
178
|
+
refreshOnOpen?: boolean;
|
|
179
|
+
/** 搜索清空配置 */
|
|
180
|
+
searchClearConfig?: SearchClearConfig;
|
|
59
181
|
};
|
|
60
182
|
|
|
183
|
+
/** Suffix 按钮配置 (替代下拉箭头位置) */
|
|
184
|
+
declare type ButtonConfig = {
|
|
185
|
+
/**
|
|
186
|
+
* 按钮图标内容 (默认 AddIcon)
|
|
187
|
+
* 注意:MUI 会自动用 IconButton 包裹,所以这里只传图标/文本内容,不要传 Button 组件
|
|
188
|
+
* 例如:<AddIcon /> 或 <Typography>新增</Typography>
|
|
189
|
+
*/
|
|
190
|
+
icon?: default_2.ReactNode;
|
|
191
|
+
/** 点击回调 */
|
|
192
|
+
onClick: () => void;
|
|
193
|
+
/** 按钮提示 (tooltip) */
|
|
194
|
+
tooltip?: string;
|
|
195
|
+
/** 是否禁用 */
|
|
196
|
+
disabled?: boolean;
|
|
197
|
+
};
|
|
198
|
+
|
|
199
|
+
export declare const CheckboxWidget: default_2.FC<CheckboxWidgetProps>;
|
|
200
|
+
|
|
201
|
+
export declare type CheckboxWidgetProps = {
|
|
202
|
+
form: any;
|
|
203
|
+
name: string;
|
|
204
|
+
validate?: any;
|
|
205
|
+
} & Omit<CheckboxWidgetRenderProps, keyof WidgetProps>;
|
|
206
|
+
|
|
207
|
+
export declare const CheckboxWidgetRender: default_2.NamedExoticComponent<CheckboxWidgetRenderProps>;
|
|
208
|
+
|
|
209
|
+
declare type CheckboxWidgetRenderProps = WidgetProps & {
|
|
210
|
+
label?: string;
|
|
211
|
+
helperText?: string;
|
|
212
|
+
checkboxProps?: Partial<CheckboxProps>;
|
|
213
|
+
};
|
|
214
|
+
|
|
215
|
+
/** 紧凑型表单字段样式 (TextField 系列) */
|
|
216
|
+
export declare const compactFieldStyles: SxProps<Theme>;
|
|
217
|
+
|
|
61
218
|
/**
|
|
62
|
-
*
|
|
219
|
+
* 编译后的 Schema (Runtime 输入)
|
|
63
220
|
*/
|
|
64
|
-
export declare
|
|
221
|
+
export declare type CompiledSchema = {
|
|
222
|
+
meta: SchemaMeta;
|
|
223
|
+
fields: Record<string, FieldConfig>;
|
|
224
|
+
/** 布局树 */
|
|
225
|
+
layout: LayoutNode[];
|
|
226
|
+
/** 扁平化的规则列表,已排序 */
|
|
227
|
+
rules: SchemaRule[];
|
|
228
|
+
/** 反向依赖索引: DepField -> Rules[] */
|
|
229
|
+
dependencyMap: Map<string, SchemaRule[]>;
|
|
230
|
+
/** 拓扑排序序列 (字段名) */
|
|
231
|
+
topologicalOrder: string[];
|
|
232
|
+
/** 静态分析报告 */
|
|
233
|
+
staticAnalysisReport?: {
|
|
234
|
+
cycles: string[][];
|
|
235
|
+
isolatedFields: string[];
|
|
236
|
+
};
|
|
237
|
+
};
|
|
65
238
|
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
precision?: number;
|
|
74
|
-
/** 舍入模式(可选,默认为 'round' 四舍五入) */
|
|
75
|
-
roundMode?: 'round' | 'ceil' | 'floor';
|
|
239
|
+
export declare type CompilerOptions = {
|
|
240
|
+
/** 当前运行时版本 (用于兼容性检查) */
|
|
241
|
+
runtimeVersion?: string;
|
|
242
|
+
/** 是否启用严格模式 (循环依赖时抛出异常) */
|
|
243
|
+
strictMode?: boolean;
|
|
244
|
+
/** 是否跳过安全验证 (不推荐) */
|
|
245
|
+
skipSecurityValidation?: boolean;
|
|
76
246
|
};
|
|
77
247
|
|
|
248
|
+
/** 创建自定义配置的编译器 */
|
|
249
|
+
export declare function createCompiler(options: CompilerOptions): SchemaCompiler;
|
|
250
|
+
|
|
78
251
|
/**
|
|
79
|
-
*
|
|
252
|
+
* 创建绑定了 form 的 FieldAdapter
|
|
253
|
+
* 减少重复传递 form 参数
|
|
80
254
|
*/
|
|
81
|
-
export declare function
|
|
255
|
+
export declare function createFieldAdapter(form: AnyFormApi_4): (props: Omit<FieldAdapterProps, "form">) => JSX.Element;
|
|
82
256
|
|
|
83
|
-
/**
|
|
84
|
-
|
|
257
|
+
/**
|
|
258
|
+
* 快捷函数:为字段创建验证 schema
|
|
259
|
+
*
|
|
260
|
+
* @example
|
|
261
|
+
* ```tsx
|
|
262
|
+
* const schema = createFieldValidator(
|
|
263
|
+
* 'email',
|
|
264
|
+
* 'Text',
|
|
265
|
+
* [{ type: 'required' }, { type: 'email' }],
|
|
266
|
+
* { label: '邮箱' }
|
|
267
|
+
* );
|
|
268
|
+
* ```
|
|
269
|
+
*/
|
|
270
|
+
export declare function createFieldValidator(fieldName: string, component: string, rules: ValidationRule[], options?: Omit<RulesAdapterOptions, "fieldType">): v.BaseSchema<unknown, unknown, v.BaseIssue<unknown>>;
|
|
85
271
|
|
|
86
272
|
/**
|
|
87
|
-
*
|
|
273
|
+
* 创建验证预设注册表
|
|
274
|
+
*
|
|
275
|
+
* @param initialRules 初始规则集 (会与默认规则合并)
|
|
276
|
+
* @returns 注册表实例
|
|
277
|
+
*
|
|
278
|
+
* @example
|
|
279
|
+
* ```tsx
|
|
280
|
+
* const registry = createValidationRegistry({
|
|
281
|
+
* // 覆盖默认的 email 规则
|
|
282
|
+
* email: (config) => v.check(
|
|
283
|
+
* (val) => isEmpty(val) || /@(163|qq|gmail)\.com$/.test(String(val)),
|
|
284
|
+
* config?.message ?? '只支持 163、QQ、Gmail 邮箱'
|
|
285
|
+
* ),
|
|
286
|
+
* // 添加新规则
|
|
287
|
+
* idNumber: (config) => v.check(
|
|
288
|
+
* (val) => isEmpty(val) || /^\d{18}$/.test(String(val)),
|
|
289
|
+
* config?.message ?? '请输入18位身份证号'
|
|
290
|
+
* ),
|
|
291
|
+
* });
|
|
292
|
+
* ```
|
|
88
293
|
*/
|
|
89
|
-
export declare function
|
|
90
|
-
values: {
|
|
91
|
-
[x: string]: unknown;
|
|
92
|
-
};
|
|
93
|
-
errors: {};
|
|
94
|
-
} | {
|
|
95
|
-
values: {};
|
|
96
|
-
errors: Record<string, {
|
|
97
|
-
type: string;
|
|
98
|
-
message: string;
|
|
99
|
-
}>;
|
|
100
|
-
}>;
|
|
294
|
+
export declare function createValidationRegistry(initialRules?: Record<string, RuleFactory>): ValidationPresetRegistry;
|
|
101
295
|
|
|
102
|
-
/**
|
|
103
|
-
|
|
296
|
+
/**
|
|
297
|
+
* 自定义组件
|
|
298
|
+
*
|
|
299
|
+
* 允许用户完全自定义表单控件的渲染
|
|
300
|
+
*
|
|
301
|
+
* @example
|
|
302
|
+
* ```tsx
|
|
303
|
+
* // 使用 children 函数
|
|
304
|
+
* <CustomWidget
|
|
305
|
+
* form={form}
|
|
306
|
+
* name="custom"
|
|
307
|
+
* children={({ value, onChange }) => (
|
|
308
|
+
* <MyCustomInput value={value} onChange={onChange} />
|
|
309
|
+
* )}
|
|
310
|
+
* />
|
|
311
|
+
*
|
|
312
|
+
* // 使用 component
|
|
313
|
+
* <CustomWidget
|
|
314
|
+
* form={form}
|
|
315
|
+
* name="custom"
|
|
316
|
+
* component={MyCustomInput}
|
|
317
|
+
* componentProps={{ variant: 'outlined' }}
|
|
318
|
+
* />
|
|
319
|
+
* ```
|
|
320
|
+
*/
|
|
321
|
+
export declare const CustomWidget: default_2.FC<CustomWidgetProps>;
|
|
322
|
+
|
|
323
|
+
export declare type CustomWidgetProps = {
|
|
324
|
+
form: any;
|
|
325
|
+
name: string;
|
|
326
|
+
validate?: any;
|
|
327
|
+
} & Omit<CustomWidgetRenderProps, keyof WidgetProps>;
|
|
328
|
+
|
|
329
|
+
/**
|
|
330
|
+
* 自定义组件渲染
|
|
331
|
+
*
|
|
332
|
+
* 支持三种方式渲染自定义内容:
|
|
333
|
+
* 1. children 函数:接收完整的 props,返回 ReactNode
|
|
334
|
+
* 2. children ReactNode:直接渲染
|
|
335
|
+
* 3. component:自定义组件
|
|
336
|
+
*/
|
|
337
|
+
export declare const CustomWidgetRender: default_2.NamedExoticComponent<CustomWidgetRenderProps>;
|
|
338
|
+
|
|
339
|
+
export declare type CustomWidgetRenderProps = WidgetProps & {
|
|
340
|
+
label?: string;
|
|
341
|
+
helperText?: string;
|
|
342
|
+
/** 自定义渲染函数 */
|
|
343
|
+
children?: default_2.ReactNode | ((props: WidgetProps & Record<string, any>) => default_2.ReactNode);
|
|
344
|
+
/** 自定义组件 */
|
|
345
|
+
component?: default_2.ComponentType<WidgetProps & Record<string, any>>;
|
|
346
|
+
/** 传递给自定义组件的额外属性 */
|
|
347
|
+
componentProps?: Record<string, any>;
|
|
348
|
+
};
|
|
104
349
|
|
|
105
350
|
/** 日期格式 */
|
|
106
351
|
export declare const DATE_FORMAT = "YYYY-MM-DD";
|
|
107
352
|
|
|
108
353
|
export declare const DATETIME_FORMAT = "YYYY-MM-DD HH:mm";
|
|
109
354
|
|
|
110
|
-
|
|
111
|
-
|
|
355
|
+
export declare const DateTimeWidget: default_2.FC<DateTimeWidgetProps>;
|
|
356
|
+
|
|
357
|
+
export declare type DateTimeWidgetProps = {
|
|
358
|
+
form: any;
|
|
359
|
+
name: string;
|
|
360
|
+
validate?: any;
|
|
361
|
+
} & Omit<DateTimeWidgetRenderProps, keyof WidgetProps>;
|
|
362
|
+
|
|
363
|
+
export declare const DateTimeWidgetRender: default_2.NamedExoticComponent<DateTimeWidgetRenderProps>;
|
|
112
364
|
|
|
113
|
-
|
|
114
|
-
|
|
365
|
+
export declare type DateTimeWidgetRenderProps = WidgetProps & {
|
|
366
|
+
label?: string;
|
|
367
|
+
helperText?: string;
|
|
368
|
+
format?: string;
|
|
369
|
+
minDateTime?: string;
|
|
370
|
+
maxDateTime?: string;
|
|
371
|
+
ampm?: boolean;
|
|
372
|
+
};
|
|
373
|
+
|
|
374
|
+
export declare const DateWidget: default_2.FC<DateWidgetProps>;
|
|
375
|
+
|
|
376
|
+
export declare type DateWidgetProps = {
|
|
377
|
+
form: any;
|
|
378
|
+
name: string;
|
|
379
|
+
validate?: any;
|
|
380
|
+
} & Omit<DateWidgetRenderProps, keyof WidgetProps>;
|
|
381
|
+
|
|
382
|
+
export declare const DateWidgetRender: default_2.NamedExoticComponent<DateWidgetRenderProps>;
|
|
383
|
+
|
|
384
|
+
declare type DateWidgetRenderProps = WidgetProps & {
|
|
385
|
+
label?: string;
|
|
386
|
+
helperText?: string;
|
|
387
|
+
format?: string;
|
|
388
|
+
min?: string;
|
|
389
|
+
max?: string;
|
|
390
|
+
};
|
|
391
|
+
|
|
392
|
+
export declare const defaultRuleFactories: Record<string, RuleFactory>;
|
|
115
393
|
|
|
116
394
|
/**
|
|
117
395
|
* 默认 Widget 映射表
|
|
396
|
+
* 用于根据 component 类型自动选择对应的 Widget
|
|
397
|
+
*
|
|
398
|
+
* 使用 *Render 版本的组件 (纯渲染函数),接收 WidgetProps
|
|
118
399
|
*/
|
|
119
|
-
export declare const defaultWidgets: Record<string,
|
|
400
|
+
export declare const defaultWidgets: Record<string, WidgetRenderFn>;
|
|
120
401
|
|
|
121
402
|
/**
|
|
122
|
-
*
|
|
123
|
-
*
|
|
124
|
-
* @param values 当前表单值
|
|
125
|
-
* @returns 条件是否满足
|
|
403
|
+
* 依赖分析器 (V4 Enhanced)
|
|
404
|
+
* 负责检测循环依赖、孤立字段并生成拓扑排序
|
|
126
405
|
*/
|
|
127
|
-
export declare
|
|
406
|
+
export declare class DependencyAnalyzer {
|
|
407
|
+
/** 是否启用严格模式 (循环依赖时抛出异常) */
|
|
408
|
+
private strictMode;
|
|
409
|
+
constructor(options?: {
|
|
410
|
+
strictMode?: boolean;
|
|
411
|
+
});
|
|
412
|
+
/**
|
|
413
|
+
* 分析规则集合,返回拓扑排序和反向依赖索引
|
|
414
|
+
* @param rules 扁平化的规则列表
|
|
415
|
+
* @param allFieldNames 所有字段名 (用于检测孤立字段)
|
|
416
|
+
* @returns 分析结果
|
|
417
|
+
*/
|
|
418
|
+
analyze(rules: SchemaRule[], allFieldNames?: string[]): AnalysisResult;
|
|
419
|
+
/**
|
|
420
|
+
* 检测孤立字段
|
|
421
|
+
* 孤立字段:既不依赖其他字段,也不被其他字段依赖
|
|
422
|
+
*/
|
|
423
|
+
private findIsolatedFields;
|
|
424
|
+
/**
|
|
425
|
+
* Tarjan's algorithm for finding SCCs (Strongly Connected Components)
|
|
426
|
+
* Only components with size > 1 or self-loops are cycles.
|
|
427
|
+
*/
|
|
428
|
+
private findCycles;
|
|
429
|
+
/**
|
|
430
|
+
* Topological Sort (DFS based)
|
|
431
|
+
*/
|
|
432
|
+
private topologicalSort;
|
|
433
|
+
}
|
|
434
|
+
|
|
435
|
+
export declare const dependencyAnalyzer: DependencyAnalyzer;
|
|
128
436
|
|
|
129
437
|
/**
|
|
130
|
-
*
|
|
131
|
-
*
|
|
132
|
-
*
|
|
438
|
+
* 副作用系统 (Runtime Core - V4 Enhanced)
|
|
439
|
+
* 负责调度所有派生规则、条件判断和联动逻辑
|
|
440
|
+
*
|
|
441
|
+
* 核心特性:
|
|
442
|
+
* - Snapshot Batching: 基于状态快照计算,最后合并提交
|
|
443
|
+
* - Conflict Resolution: 高优先级覆盖低优先级
|
|
444
|
+
* - Error Boundary: 规则失败不阻断表单
|
|
445
|
+
* - Runtime Freezing: scope 对象浅冻结防止修改
|
|
133
446
|
*/
|
|
134
|
-
export declare
|
|
447
|
+
export declare class EffectSystem {
|
|
448
|
+
private schema;
|
|
449
|
+
private form;
|
|
450
|
+
private scheduler;
|
|
451
|
+
private config;
|
|
452
|
+
private pendingRules;
|
|
453
|
+
private isBatching;
|
|
454
|
+
private traces;
|
|
455
|
+
/** 字段 Meta 缓存 (避免频繁读取 Form State) */
|
|
456
|
+
private metaCache;
|
|
457
|
+
/** 字段订阅者 */
|
|
458
|
+
private listeners;
|
|
459
|
+
constructor(schema: CompiledSchema, form: AnyFormApi, scheduler: AsyncScheduler, config?: EffectSystemConfig);
|
|
460
|
+
/**
|
|
461
|
+
* 订阅字段 Meta 变更
|
|
462
|
+
*/
|
|
463
|
+
subscribe(fieldName: string, listener: () => void): () => void;
|
|
464
|
+
/**
|
|
465
|
+
* 初始化所有字段的 Meta 缓存
|
|
466
|
+
*/
|
|
467
|
+
private initializeMetaCache;
|
|
468
|
+
/**
|
|
469
|
+
* 获取字段的 Meta 状态
|
|
470
|
+
*/
|
|
471
|
+
getFieldMeta(fieldName: string): FieldMeta | undefined;
|
|
472
|
+
/**
|
|
473
|
+
* 获取所有 Meta 快照
|
|
474
|
+
*/
|
|
475
|
+
getAllMeta(): Record<string, FieldMeta>;
|
|
476
|
+
/**
|
|
477
|
+
* 获取追踪日志
|
|
478
|
+
*/
|
|
479
|
+
getTraces(): readonly EffectTrace[];
|
|
480
|
+
/**
|
|
481
|
+
* 清除追踪日志
|
|
482
|
+
*/
|
|
483
|
+
clearTraces(): void;
|
|
484
|
+
/**
|
|
485
|
+
* 清除所有订阅者
|
|
486
|
+
*/
|
|
487
|
+
clearListeners(): void;
|
|
488
|
+
/**
|
|
489
|
+
* 触发依赖更新
|
|
490
|
+
* 当 TanStack Form 字段值变化时调用此方法
|
|
491
|
+
* @param changedField 变化的字段名
|
|
492
|
+
*/
|
|
493
|
+
notifyFieldChange(changedField: string): void;
|
|
494
|
+
/**
|
|
495
|
+
* 调度批量更新 (Microtask)
|
|
496
|
+
*/
|
|
497
|
+
private scheduleBatchUpdate;
|
|
498
|
+
/**
|
|
499
|
+
* 递归冻结对象 (Deep Freeze)
|
|
500
|
+
* 确保 EvalScope 在运行时绝对不可变
|
|
501
|
+
*/
|
|
502
|
+
private deepFreeze;
|
|
503
|
+
/**
|
|
504
|
+
* 执行批量更新
|
|
505
|
+
*/
|
|
506
|
+
private flushUpdates;
|
|
507
|
+
/**
|
|
508
|
+
* 执行 derive 规则
|
|
509
|
+
*/
|
|
510
|
+
private executeDeriveRule;
|
|
511
|
+
/**
|
|
512
|
+
* 执行 gate 规则
|
|
513
|
+
*/
|
|
514
|
+
private executeGateRule;
|
|
515
|
+
/**
|
|
516
|
+
* 执行 options 规则 (异步)
|
|
517
|
+
*/
|
|
518
|
+
private executeOptionsRule;
|
|
519
|
+
/**
|
|
520
|
+
* 执行 effect 规则
|
|
521
|
+
*/
|
|
522
|
+
private executeEffectRule;
|
|
523
|
+
/**
|
|
524
|
+
* 提交变更到 Form
|
|
525
|
+
*/
|
|
526
|
+
private commitUpdates;
|
|
527
|
+
/**
|
|
528
|
+
* 通知字段订阅者
|
|
529
|
+
*/
|
|
530
|
+
private notifyListeners;
|
|
531
|
+
/**
|
|
532
|
+
* 通过路径获取值 (支持嵌套路径如 "a.b.c")
|
|
533
|
+
*/
|
|
534
|
+
private getValueByPath;
|
|
535
|
+
/**
|
|
536
|
+
* 简单的深拷贝
|
|
537
|
+
*/
|
|
538
|
+
private cloneDeep;
|
|
539
|
+
/**
|
|
540
|
+
* 深度比较两个值是否相等
|
|
541
|
+
*/
|
|
542
|
+
private isEqual;
|
|
543
|
+
/**
|
|
544
|
+
* 记录追踪日志
|
|
545
|
+
*/
|
|
546
|
+
private logTrace;
|
|
547
|
+
/**
|
|
548
|
+
* 初始化执行所有规则 (首次渲染)
|
|
549
|
+
*/
|
|
550
|
+
initialize(): void;
|
|
551
|
+
/**
|
|
552
|
+
* 更新外部上下文
|
|
553
|
+
*/
|
|
554
|
+
updateContext(context: Record<string, any>): void;
|
|
555
|
+
}
|
|
135
556
|
|
|
136
|
-
|
|
557
|
+
/**
|
|
558
|
+
* EffectSystem 配置
|
|
559
|
+
*/
|
|
560
|
+
export declare type EffectSystemConfig = {
|
|
561
|
+
/** 是否启用 DevTools 追踪 */
|
|
562
|
+
enableTracing?: boolean;
|
|
563
|
+
/** 追踪日志最大条数 */
|
|
564
|
+
maxTraceCount?: number;
|
|
565
|
+
/** 错误回调 */
|
|
566
|
+
onError?: (error: Error, context: {
|
|
567
|
+
rule: SchemaRule;
|
|
568
|
+
target: string;
|
|
569
|
+
}) => void;
|
|
570
|
+
/** 外部上下文 (注入到 EvalScope.context) */
|
|
571
|
+
externalContext?: Record<string, any>;
|
|
572
|
+
};
|
|
137
573
|
|
|
138
574
|
/**
|
|
139
|
-
*
|
|
140
|
-
* 负责根据 Schema 渲染单个表单字段
|
|
575
|
+
* 效果追踪日志
|
|
141
576
|
*/
|
|
142
|
-
declare
|
|
577
|
+
export declare type EffectTrace = {
|
|
578
|
+
ruleId: string;
|
|
579
|
+
target: string;
|
|
580
|
+
type: SchemaRule["type"];
|
|
581
|
+
deps?: string[];
|
|
582
|
+
duration: number;
|
|
583
|
+
result: any;
|
|
584
|
+
error?: Error;
|
|
585
|
+
timestamp: number;
|
|
586
|
+
};
|
|
143
587
|
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
/** 全局禁用 */
|
|
154
|
-
disabled?: boolean;
|
|
155
|
-
/** 全局只读 */
|
|
156
|
-
readOnly?: boolean;
|
|
157
|
-
/** Widget 映射 */
|
|
158
|
-
widgets: Record<string, WidgetComponent>;
|
|
159
|
-
/** 选项映射 */
|
|
160
|
-
optionsMap: Record<string, OptionItem[]>;
|
|
161
|
-
/** 是否使用 Grid 包装 */
|
|
162
|
-
useGrid?: boolean;
|
|
163
|
-
}
|
|
588
|
+
/**
|
|
589
|
+
* 运行时评估作用域
|
|
590
|
+
* 必须在运行时被 Object.freeze() 浅冻结
|
|
591
|
+
*/
|
|
592
|
+
export declare type EvalScope = Readonly<{
|
|
593
|
+
values: Record<string, any>;
|
|
594
|
+
meta: Record<string, any>;
|
|
595
|
+
context: Record<string, any>;
|
|
596
|
+
}>;
|
|
164
597
|
|
|
165
|
-
/**
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
598
|
+
/**
|
|
599
|
+
* 字段适配器 (V4 Enhanced)
|
|
600
|
+
*
|
|
601
|
+
* 特性:
|
|
602
|
+
* - Selector Subscription: 细粒度订阅减少重渲染
|
|
603
|
+
* - Runtime Meta 集成: 自动读取 visible/disabled/required
|
|
604
|
+
* - Validation 集成: 支持 Valibot schema 和预设规则数组
|
|
605
|
+
*/
|
|
606
|
+
export declare const FieldAdapter: default_2.NamedExoticComponent<FieldAdapterProps>;
|
|
607
|
+
|
|
608
|
+
export declare type FieldAdapterProps = {
|
|
609
|
+
form: AnyFormApi_4;
|
|
610
|
+
name: string;
|
|
611
|
+
/**
|
|
612
|
+
* 校验规则
|
|
613
|
+
* - Valibot schema: 直接使用 valibot 校验
|
|
614
|
+
* - PresetRule[]: 预设规则数组,格式为 [{type: 'required', message: '必填'}, {type: 'email'}]
|
|
615
|
+
*/
|
|
616
|
+
validate?: any | PresetRule[];
|
|
617
|
+
render: (props: WidgetProps) => default_2.ReactNode;
|
|
618
|
+
/** 额外的 props 透传 */
|
|
619
|
+
fieldProps?: Record<string, any>;
|
|
620
|
+
};
|
|
621
|
+
|
|
622
|
+
/**
|
|
623
|
+
* 字段配置 (Compiler 输出)
|
|
624
|
+
*/
|
|
625
|
+
export declare type FieldConfig = {
|
|
626
|
+
name: string;
|
|
627
|
+
component: string;
|
|
628
|
+
defaultValue?: any;
|
|
629
|
+
props?: Record<string, any>;
|
|
630
|
+
validate?: any;
|
|
631
|
+
};
|
|
632
|
+
|
|
633
|
+
/**
|
|
634
|
+
* 字段 Meta 状态
|
|
635
|
+
*/
|
|
636
|
+
export declare type FieldMeta = {
|
|
637
|
+
isVisible: boolean;
|
|
638
|
+
isDisabled: boolean;
|
|
639
|
+
isRequired: boolean;
|
|
640
|
+
options?: any[];
|
|
641
|
+
error?: string;
|
|
642
|
+
};
|
|
643
|
+
|
|
644
|
+
/** 字段类型 */
|
|
645
|
+
export declare type FieldType = "text" | "number" | "boolean" | "select" | "array" | "date" | "unknown";
|
|
646
|
+
|
|
647
|
+
/**
|
|
648
|
+
* FormList 动态列表组件
|
|
649
|
+
*
|
|
650
|
+
* 用于管理动态数组数据,支持添加、删除、复制行
|
|
651
|
+
*
|
|
652
|
+
* @example
|
|
653
|
+
* ```tsx
|
|
654
|
+
* // Schema 配置
|
|
655
|
+
* {
|
|
656
|
+
* name: 'users',
|
|
657
|
+
* component: 'FormList',
|
|
658
|
+
* ui: {
|
|
659
|
+
* label: '用户列表',
|
|
660
|
+
* minItems: 1,
|
|
661
|
+
* maxItems: 5,
|
|
662
|
+
* addText: '添加用户',
|
|
663
|
+
* copyable: true,
|
|
664
|
+
* },
|
|
665
|
+
* children: [
|
|
666
|
+
* { name: 'name', component: 'Text', ui: { label: '姓名' } },
|
|
667
|
+
* { name: 'age', component: 'Number', ui: { label: '年龄' } },
|
|
668
|
+
* ],
|
|
669
|
+
* }
|
|
670
|
+
* ```
|
|
671
|
+
*/
|
|
672
|
+
export declare const FormListWidget: default_2.NamedExoticComponent<FormListWidgetRenderProps>;
|
|
673
|
+
|
|
674
|
+
export declare type FormListWidgetProps = {
|
|
675
|
+
form: any;
|
|
676
|
+
name: string;
|
|
677
|
+
} & Omit<FormListWidgetRenderProps, keyof WidgetProps>;
|
|
678
|
+
|
|
679
|
+
/**
|
|
680
|
+
* FormList 动态列表组件
|
|
681
|
+
*
|
|
682
|
+
* 支持动态添加/删除/复制行
|
|
683
|
+
*/
|
|
684
|
+
export declare const FormListWidgetRender: default_2.NamedExoticComponent<FormListWidgetRenderProps>;
|
|
685
|
+
|
|
686
|
+
export declare type FormListWidgetRenderProps = WidgetProps & {
|
|
687
|
+
label?: string;
|
|
688
|
+
helperText?: string;
|
|
689
|
+
/** 布局子节点 (由 SchemaRenderer 传入) */
|
|
690
|
+
layoutChildren?: LayoutNode[];
|
|
203
691
|
/** 最小行数 */
|
|
204
692
|
minItems?: number;
|
|
205
693
|
/** 最大行数 */
|
|
206
694
|
maxItems?: number;
|
|
207
695
|
/** 添加按钮文案 */
|
|
208
696
|
addText?: string;
|
|
209
|
-
/** 是否可拖拽排序 */
|
|
210
|
-
sortable?: boolean;
|
|
211
697
|
/** 是否可复制 */
|
|
212
698
|
copyable?: boolean;
|
|
213
|
-
/**
|
|
214
|
-
|
|
215
|
-
/**
|
|
216
|
-
|
|
217
|
-
/**
|
|
218
|
-
|
|
219
|
-
/** 条件必填 */
|
|
220
|
-
requiredWhen?: ConditionExpression;
|
|
221
|
-
/** 只读 */
|
|
222
|
-
readonly?: boolean;
|
|
223
|
-
/** 禁用 */
|
|
224
|
-
disabled?: boolean;
|
|
225
|
-
/** 隐藏(不渲染) */
|
|
226
|
-
hidden?: boolean;
|
|
227
|
-
/** 自动计算配置 */
|
|
228
|
-
compute?: ComputeConfig;
|
|
229
|
-
/** 提交前转换 */
|
|
230
|
-
transform?: (value: unknown, values: T) => unknown;
|
|
231
|
-
/** 不参与提交 */
|
|
232
|
-
noSubmit?: boolean;
|
|
233
|
-
/** 依赖字段(用于触发重新计算/校验) */
|
|
234
|
-
dependencies?: string[];
|
|
235
|
-
/** 组件透传属性 (快捷方式,等同于 ui.props) */
|
|
236
|
-
fieldProps?: Record<string, unknown>;
|
|
237
|
-
};
|
|
238
|
-
|
|
239
|
-
/**
|
|
240
|
-
* 字段状态计算引擎
|
|
241
|
-
*
|
|
242
|
-
* 计算每个字段的运行时状态:
|
|
243
|
-
* - visible: 是否显示
|
|
244
|
-
* - disabled: 是否禁用
|
|
245
|
-
* - required: 是否必填
|
|
246
|
-
* - readonly: 是否只读
|
|
247
|
-
*/
|
|
248
|
-
/** 单个字段的运行时状态 */
|
|
249
|
-
export declare type FieldState = {
|
|
250
|
-
/** 是否可见 */
|
|
251
|
-
visible: boolean;
|
|
252
|
-
/** 是否禁用 */
|
|
253
|
-
disabled: boolean;
|
|
254
|
-
/** 是否必填 */
|
|
255
|
-
required: boolean;
|
|
256
|
-
/** 是否只读 */
|
|
257
|
-
readonly: boolean;
|
|
699
|
+
/** 空状态提示 */
|
|
700
|
+
emptyText?: string;
|
|
701
|
+
/** 显示行号 */
|
|
702
|
+
showIndex?: boolean;
|
|
703
|
+
/** 每行的默认值 */
|
|
704
|
+
itemDefaultValue?: Record<string, any>;
|
|
258
705
|
};
|
|
259
706
|
|
|
260
|
-
/**
|
|
261
|
-
|
|
707
|
+
/**
|
|
708
|
+
* 表单运行时 (Facade - V4)
|
|
709
|
+
*
|
|
710
|
+
* 统一管理 EffectSystem 和 AsyncScheduler,提供简洁的 API。
|
|
711
|
+
*/
|
|
712
|
+
export declare class FormRuntime {
|
|
713
|
+
readonly effectSystem: EffectSystem;
|
|
714
|
+
readonly asyncScheduler: AsyncScheduler;
|
|
715
|
+
readonly schema: CompiledSchema;
|
|
716
|
+
private form;
|
|
717
|
+
private initialized;
|
|
718
|
+
constructor(schema: CompiledSchema, form: AnyFormApi_2, config?: RuntimeConfig);
|
|
719
|
+
/**
|
|
720
|
+
* 获取 TanStack Form 实例 (仅用于调试或高级用法)
|
|
721
|
+
*/
|
|
722
|
+
getForm(): AnyFormApi_2;
|
|
723
|
+
/**
|
|
724
|
+
* 初始化运行时 (执行所有规则)
|
|
725
|
+
*/
|
|
726
|
+
initialize(): void;
|
|
727
|
+
/**
|
|
728
|
+
* 通知字段变更
|
|
729
|
+
*/
|
|
730
|
+
notifyChange(field: string): void;
|
|
731
|
+
/**
|
|
732
|
+
* 批量通知字段变更
|
|
733
|
+
*/
|
|
734
|
+
notifyChanges(fields: string[]): void;
|
|
735
|
+
/**
|
|
736
|
+
* 订阅字段 Meta 变更
|
|
737
|
+
*/
|
|
738
|
+
subscribe(fieldName: string, listener: () => void): () => void;
|
|
739
|
+
/**
|
|
740
|
+
* 获取字段 Meta
|
|
741
|
+
*/
|
|
742
|
+
getFieldMeta(fieldName: string): FieldMeta | undefined;
|
|
743
|
+
/**
|
|
744
|
+
* 获取所有字段 Meta
|
|
745
|
+
*/
|
|
746
|
+
getAllMeta(): Record<string, FieldMeta>;
|
|
747
|
+
/**
|
|
748
|
+
* 更新外部上下文
|
|
749
|
+
*/
|
|
750
|
+
updateContext(context: Record<string, any>): void;
|
|
751
|
+
/**
|
|
752
|
+
* 获取调度器
|
|
753
|
+
*/
|
|
754
|
+
get scheduler(): AsyncScheduler;
|
|
755
|
+
/**
|
|
756
|
+
* 获取追踪日志
|
|
757
|
+
*/
|
|
758
|
+
getTraces(): readonly EffectTrace[];
|
|
759
|
+
/**
|
|
760
|
+
* 清除追踪日志
|
|
761
|
+
*/
|
|
762
|
+
clearTraces(): void;
|
|
763
|
+
/**
|
|
764
|
+
* 使缓存失效并重新计算
|
|
765
|
+
*/
|
|
766
|
+
invalidateAndRefresh(field?: string): void;
|
|
767
|
+
/**
|
|
768
|
+
* 销毁运行时
|
|
769
|
+
*/
|
|
770
|
+
destroy(): void;
|
|
771
|
+
}
|
|
262
772
|
|
|
263
773
|
/**
|
|
264
|
-
*
|
|
265
|
-
* 支持动态添加/删除/复制行
|
|
774
|
+
* 获取所有已注册的 Widget 类型
|
|
266
775
|
*/
|
|
267
|
-
export declare
|
|
776
|
+
export declare function getRegisteredWidgetTypes(): string[];
|
|
268
777
|
|
|
269
778
|
/**
|
|
270
|
-
*
|
|
271
|
-
* 用于判断哪些字段需要重新计算
|
|
779
|
+
* 获取 Widget 组件
|
|
272
780
|
*/
|
|
273
|
-
export declare function
|
|
781
|
+
export declare function getWidget(type: string): WidgetRenderFn | undefined;
|
|
782
|
+
|
|
783
|
+
/** 全局默认验证预设注册表 */
|
|
784
|
+
export declare const globalValidationRegistry: ValidationPresetRegistry;
|
|
274
785
|
|
|
275
786
|
/**
|
|
276
|
-
*
|
|
277
|
-
*
|
|
787
|
+
* 分组组件
|
|
788
|
+
*
|
|
789
|
+
* 用于将多个表单字段组织在一起
|
|
790
|
+
*
|
|
791
|
+
* @example
|
|
792
|
+
* ```tsx
|
|
793
|
+
* // Schema 配置
|
|
794
|
+
* {
|
|
795
|
+
* name: 'personalInfo',
|
|
796
|
+
* component: 'Group',
|
|
797
|
+
* ui: {
|
|
798
|
+
* label: '个人信息',
|
|
799
|
+
* variant: 'card',
|
|
800
|
+
* },
|
|
801
|
+
* children: [
|
|
802
|
+
* { name: 'name', component: 'Text', ui: { label: '姓名' } },
|
|
803
|
+
* { name: 'age', component: 'Number', ui: { label: '年龄' } },
|
|
804
|
+
* ],
|
|
805
|
+
* }
|
|
806
|
+
* ```
|
|
278
807
|
*/
|
|
279
|
-
export declare
|
|
808
|
+
export declare const GroupWidget: default_2.FC<GroupWidgetProps>;
|
|
809
|
+
|
|
810
|
+
export declare type GroupWidgetProps = {} & GroupWidgetRenderProps;
|
|
280
811
|
|
|
281
812
|
/**
|
|
282
|
-
*
|
|
283
|
-
*
|
|
813
|
+
* 分组组件渲染
|
|
814
|
+
*
|
|
815
|
+
* 将多个字段组合在一起,支持不同的显示样式
|
|
284
816
|
*/
|
|
285
|
-
export declare const
|
|
817
|
+
export declare const GroupWidgetRender: default_2.NamedExoticComponent<GroupWidgetRenderProps>;
|
|
286
818
|
|
|
287
|
-
export declare
|
|
288
|
-
|
|
819
|
+
export declare type GroupWidgetRenderProps = WidgetProps & {
|
|
820
|
+
label?: string;
|
|
821
|
+
helperText?: string;
|
|
822
|
+
/** 布局子节点 (由 SchemaRenderer 传入) */
|
|
823
|
+
layoutChildren?: LayoutNode[];
|
|
824
|
+
/** 显示样式: card 卡片 | divider 分割线 | none 无边框 */
|
|
825
|
+
variant?: "card" | "divider" | "none";
|
|
826
|
+
/** 是否折叠 (TODO: 未实现) */
|
|
827
|
+
collapsible?: boolean;
|
|
828
|
+
/** Grid 间距 */
|
|
289
829
|
spacing?: number;
|
|
290
|
-
|
|
291
|
-
|
|
830
|
+
};
|
|
831
|
+
|
|
832
|
+
export declare const HiddenWidget: default_2.FC<HiddenWidgetProps>;
|
|
833
|
+
|
|
834
|
+
export declare type HiddenWidgetProps = {
|
|
835
|
+
form: any;
|
|
836
|
+
name: string;
|
|
837
|
+
validate?: any;
|
|
838
|
+
};
|
|
839
|
+
|
|
840
|
+
/**
|
|
841
|
+
* 隐藏字段渲染组件
|
|
842
|
+
*
|
|
843
|
+
* 渲染一个隐藏的 input 元素,用于存储不可见的表单数据
|
|
844
|
+
*/
|
|
845
|
+
export declare const HiddenWidgetRender: default_2.NamedExoticComponent<WidgetProps>;
|
|
846
|
+
|
|
847
|
+
export declare type HiddenWidgetRenderProps = WidgetProps;
|
|
848
|
+
|
|
849
|
+
/**
|
|
850
|
+
* 从字段配置推断字段类型
|
|
851
|
+
*/
|
|
852
|
+
export declare function inferFieldType(component: string): FieldType;
|
|
853
|
+
|
|
854
|
+
/**
|
|
855
|
+
* 检测是否为预设规则数组
|
|
856
|
+
* @param value 待检测的值
|
|
857
|
+
* @returns 是否为预设规则数组
|
|
858
|
+
*/
|
|
859
|
+
export declare function isPresetRulesArray(value: unknown): value is PresetRule[];
|
|
860
|
+
|
|
861
|
+
export declare const LayoutContext: default_2.Context<LayoutContextType | null>;
|
|
862
|
+
|
|
863
|
+
export declare interface LayoutContextType {
|
|
864
|
+
renderField: (fieldPath: string, layoutChildren?: LayoutNode[]) => default_2.ReactNode;
|
|
292
865
|
}
|
|
293
866
|
|
|
294
867
|
/**
|
|
295
|
-
*
|
|
296
|
-
* 将多个字段组合在一行内显示
|
|
868
|
+
* 布局节点
|
|
297
869
|
*/
|
|
298
|
-
export declare
|
|
870
|
+
export declare type LayoutNode = {
|
|
871
|
+
type: 'field' | 'container';
|
|
872
|
+
/** 如果是 field,对应 fieldPath */
|
|
873
|
+
field?: string;
|
|
874
|
+
/** 如果是 container,对应组件名 (Grid, Stack, Card...) */
|
|
875
|
+
component?: string;
|
|
876
|
+
props?: Record<string, any>;
|
|
877
|
+
children?: LayoutNode[];
|
|
878
|
+
};
|
|
299
879
|
|
|
300
|
-
|
|
301
|
-
export declare const HiddenWidget: WidgetComponent;
|
|
880
|
+
export declare const LayoutRenderer: default_2.FC<LayoutRendererProps>;
|
|
302
881
|
|
|
303
|
-
export declare
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
882
|
+
export declare interface LayoutRendererProps {
|
|
883
|
+
layout: LayoutNode[];
|
|
884
|
+
renderField: (fieldPath: string, layoutChildren?: LayoutNode[]) => default_2.ReactNode;
|
|
885
|
+
}
|
|
886
|
+
|
|
887
|
+
export declare type LinterOptions = {
|
|
888
|
+
/** 是否检查未使用的字段 */
|
|
889
|
+
checkUnusedFields?: boolean;
|
|
890
|
+
/** 是否检查表达式语法 */
|
|
891
|
+
checkExpressions?: boolean;
|
|
892
|
+
/** 是否检查组件类型 */
|
|
893
|
+
checkComponentTypes?: boolean;
|
|
894
|
+
/** 已知的组件类型列表 */
|
|
895
|
+
knownComponents?: string[];
|
|
896
|
+
};
|
|
897
|
+
|
|
898
|
+
export declare type LintMessage = {
|
|
899
|
+
severity: LintSeverity;
|
|
900
|
+
field?: string;
|
|
901
|
+
rule?: string;
|
|
902
|
+
message: string;
|
|
903
|
+
suggestion?: string;
|
|
904
|
+
};
|
|
905
|
+
|
|
906
|
+
export declare type LintResult = {
|
|
907
|
+
valid: boolean;
|
|
908
|
+
messages: LintMessage[];
|
|
909
|
+
errors: LintMessage[];
|
|
910
|
+
warnings: LintMessage[];
|
|
312
911
|
};
|
|
313
912
|
|
|
314
913
|
/**
|
|
315
|
-
*
|
|
914
|
+
* 快捷校验函数
|
|
316
915
|
*/
|
|
317
|
-
export declare function
|
|
916
|
+
export declare function lintSchema(schema: SchemaInput, options?: LinterOptions): LintResult;
|
|
917
|
+
|
|
918
|
+
export declare type LintSeverity = "error" | "warning" | "info";
|
|
919
|
+
|
|
920
|
+
export declare const NumberWidget: default_2.FC<NumberWidgetProps>;
|
|
921
|
+
|
|
922
|
+
export declare type NumberWidgetProps = {
|
|
923
|
+
form: any;
|
|
924
|
+
name: string;
|
|
925
|
+
validate?: any;
|
|
926
|
+
} & Omit<NumberWidgetRenderProps, keyof WidgetProps>;
|
|
318
927
|
|
|
319
|
-
|
|
320
|
-
|
|
928
|
+
export declare const NumberWidgetRender: default_2.NamedExoticComponent<NumberWidgetRenderProps>;
|
|
929
|
+
|
|
930
|
+
declare type NumberWidgetRenderProps = WidgetProps & {
|
|
931
|
+
label?: string;
|
|
932
|
+
placeholder?: string;
|
|
933
|
+
helperText?: string;
|
|
934
|
+
min?: number;
|
|
935
|
+
max?: number;
|
|
936
|
+
step?: number;
|
|
937
|
+
inputProps?: Record<string, any>;
|
|
938
|
+
slotProps?: TextFieldProps["slotProps"];
|
|
939
|
+
};
|
|
940
|
+
|
|
941
|
+
/** 添加选项成功回调 */
|
|
942
|
+
declare type OnAddOptionSuccess = (newOption: OptionItem, context: {
|
|
943
|
+
/** 是否为远程模式 */
|
|
944
|
+
isRemote: boolean;
|
|
945
|
+
/** 刷新远程数据 (仅远程模式) */
|
|
946
|
+
refreshRemote?: () => void;
|
|
947
|
+
/** 追加本地选项 (仅本地模式) */
|
|
948
|
+
appendLocalOption?: (option: OptionItem) => void;
|
|
949
|
+
}) => void;
|
|
321
950
|
|
|
322
951
|
export declare type OptionItem = {
|
|
323
952
|
label: string;
|
|
324
953
|
value: string | number | boolean | null;
|
|
325
954
|
disabled?: boolean;
|
|
326
|
-
/** 唯一标识 (解决 label 重复问题) */
|
|
327
955
|
key?: string | number;
|
|
328
956
|
/** 列表展示文本 (允许与选中后回显的 label 不一致) */
|
|
329
|
-
listLabel?:
|
|
957
|
+
listLabel?: default_2.ReactNode;
|
|
330
958
|
[key: string]: unknown;
|
|
331
959
|
};
|
|
332
960
|
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
961
|
+
/**
|
|
962
|
+
* 快捷函数:覆盖全局注册表中的预设规则
|
|
963
|
+
*/
|
|
964
|
+
export declare function overridePresetRule(name: string, factory: RuleFactory): void;
|
|
965
|
+
|
|
966
|
+
/**
|
|
967
|
+
* 解析 colSpan 为 Grid size props
|
|
968
|
+
*/
|
|
969
|
+
export declare function parseColSpan(colSpan?: number | Record<string, number>): Record<string, number>;
|
|
970
|
+
|
|
971
|
+
/**
|
|
972
|
+
* 预设规则配置
|
|
973
|
+
* @example
|
|
974
|
+
* ```tsx
|
|
975
|
+
* // 简写
|
|
976
|
+
* { type: 'required' }
|
|
977
|
+
* { type: 'email', message: '请输入有效邮箱' }
|
|
978
|
+
*
|
|
979
|
+
* // 带参数
|
|
980
|
+
* { type: 'minLength', value: 3, message: '至少3个字符' }
|
|
981
|
+
* { type: 'pattern', value: /^\d+$/, message: '只能输入数字' }
|
|
982
|
+
* ```
|
|
983
|
+
*/
|
|
984
|
+
export declare type PresetRule = {
|
|
985
|
+
type: PresetRuleName;
|
|
986
|
+
value?: any;
|
|
987
|
+
message?: string;
|
|
344
988
|
};
|
|
345
989
|
|
|
990
|
+
/** 预设规则名称 */
|
|
991
|
+
export declare type PresetRuleName = "required" | "email" | "phone" | "url" | "minLength" | "maxLength" | "min" | "max" | "pattern" | "idCard" | "integer" | "positive" | "negative" | "alphanumeric" | "chinese" | string;
|
|
992
|
+
|
|
346
993
|
/**
|
|
347
|
-
*
|
|
994
|
+
* 将预设规则数组转换为 valibot schema
|
|
995
|
+
*
|
|
996
|
+
* @example
|
|
997
|
+
* ```tsx
|
|
998
|
+
* // 基础用法
|
|
999
|
+
* const schema = presetToSchema([
|
|
1000
|
+
* { type: 'required', message: '必填项' },
|
|
1001
|
+
* { type: 'email', message: '请输入有效邮箱' },
|
|
1002
|
+
* ]);
|
|
1003
|
+
*
|
|
1004
|
+
* // 带参数的规则
|
|
1005
|
+
* const schema = presetToSchema([
|
|
1006
|
+
* { type: 'required' },
|
|
1007
|
+
* { type: 'minLength', value: 3, message: '至少3个字符' },
|
|
1008
|
+
* { type: 'maxLength', value: 20 },
|
|
1009
|
+
* ], { label: '用户名' });
|
|
1010
|
+
* ```
|
|
348
1011
|
*/
|
|
349
|
-
export declare function
|
|
350
|
-
|
|
1012
|
+
export declare function presetToSchema(rules: PresetRule[], options?: {
|
|
1013
|
+
label?: string;
|
|
1014
|
+
baseType?: "string" | "number" | "any";
|
|
1015
|
+
}): v.BaseSchema<unknown, unknown, v.BaseIssue<unknown>>;
|
|
1016
|
+
|
|
1017
|
+
export declare const RadioWidget: default_2.FC<RadioWidgetProps>;
|
|
1018
|
+
|
|
1019
|
+
export declare type RadioWidgetProps = {
|
|
1020
|
+
form: any;
|
|
1021
|
+
name: string;
|
|
1022
|
+
validate?: any;
|
|
1023
|
+
} & Omit<RadioWidgetRenderProps, keyof WidgetProps>;
|
|
1024
|
+
|
|
1025
|
+
export declare const RadioWidgetRender: default_2.NamedExoticComponent<RadioWidgetRenderProps>;
|
|
1026
|
+
|
|
1027
|
+
declare type RadioWidgetRenderProps = WidgetProps & {
|
|
1028
|
+
label?: string;
|
|
1029
|
+
helperText?: string;
|
|
1030
|
+
/** 选项横向排列,默认 false(纵向) */
|
|
1031
|
+
row?: boolean;
|
|
1032
|
+
/** label 和组件在同一行,默认 false(label 在上) */
|
|
1033
|
+
inline?: boolean;
|
|
1034
|
+
radioProps?: Partial<RadioProps>;
|
|
351
1035
|
};
|
|
352
1036
|
|
|
353
|
-
|
|
354
|
-
export declare const PasswordWidget: WidgetComponent;
|
|
1037
|
+
export declare const RatingWidget: default_2.FC<RatingWidgetProps>;
|
|
355
1038
|
|
|
356
|
-
|
|
357
|
-
|
|
1039
|
+
export declare type RatingWidgetProps = {
|
|
1040
|
+
form: any;
|
|
1041
|
+
name: string;
|
|
1042
|
+
validate?: any;
|
|
1043
|
+
} & Omit<RatingWidgetRenderProps, keyof WidgetProps>;
|
|
358
1044
|
|
|
359
|
-
|
|
360
|
-
export declare const RatingWidget: WidgetComponent;
|
|
1045
|
+
export declare const RatingWidgetRender: default_2.NamedExoticComponent<RatingWidgetRenderProps>;
|
|
361
1046
|
|
|
362
|
-
|
|
363
|
-
|
|
1047
|
+
export declare type RatingWidgetRenderProps = WidgetProps & {
|
|
1048
|
+
label?: string;
|
|
1049
|
+
helperText?: string;
|
|
1050
|
+
max?: number;
|
|
1051
|
+
precision?: number;
|
|
1052
|
+
size?: "small" | "medium" | "large";
|
|
1053
|
+
readOnly?: boolean;
|
|
1054
|
+
/** 内联模式:label 和 rating 在同一行 */
|
|
1055
|
+
inline?: boolean;
|
|
1056
|
+
};
|
|
1057
|
+
|
|
1058
|
+
/**
|
|
1059
|
+
* 快捷函数:注册新的预设规则到全局注册表
|
|
1060
|
+
*/
|
|
1061
|
+
export declare function registerPresetRule(name: string, factory: RuleFactory): void;
|
|
1062
|
+
|
|
1063
|
+
/**
|
|
1064
|
+
* 注册自定义 Widget
|
|
1065
|
+
*/
|
|
1066
|
+
export declare function registerWidget(type: string, widget: WidgetRenderFn): void;
|
|
1067
|
+
|
|
1068
|
+
/**
|
|
1069
|
+
* 批量注册 Widget
|
|
1070
|
+
*/
|
|
1071
|
+
export declare function registerWidgets(widgets: Record<string, WidgetRenderFn>): void;
|
|
1072
|
+
|
|
1073
|
+
export declare type RemoteConfig = {
|
|
364
1074
|
/** 获取数据的函数 */
|
|
365
1075
|
fetchOptions: (keyword: string, page: number, pageSize: number) => Promise<{
|
|
366
1076
|
data: OptionItem[];
|
|
367
1077
|
total: number;
|
|
368
1078
|
hasMore: boolean;
|
|
369
1079
|
}>;
|
|
370
|
-
/**
|
|
1080
|
+
/** 每页条数,默认 20 */
|
|
371
1081
|
pageSize?: number;
|
|
372
|
-
/** 搜索防抖时间 (ms) */
|
|
1082
|
+
/** 搜索防抖时间 (ms),默认 500 */
|
|
373
1083
|
debounceTimeout?: number;
|
|
374
|
-
/**
|
|
1084
|
+
/** 最小搜索字符数,默认 0 */
|
|
375
1085
|
minSearchLength?: number;
|
|
376
1086
|
/** 加载状态回调 */
|
|
377
1087
|
onLoadingChange?: (loading: boolean) => void;
|
|
@@ -379,167 +1089,814 @@ declare type RemoteConfig = {
|
|
|
379
1089
|
fetchById?: (value: string | number) => Promise<OptionItem | null>;
|
|
380
1090
|
};
|
|
381
1091
|
|
|
382
|
-
/**
|
|
383
|
-
|
|
384
|
-
|
|
1092
|
+
/**
|
|
1093
|
+
* 渲染带必填标识的标签
|
|
1094
|
+
*
|
|
1095
|
+
* @param label - 标签文本
|
|
1096
|
+
* @param required - 是否必填
|
|
1097
|
+
* @returns 带星号标识的标签
|
|
1098
|
+
*/
|
|
1099
|
+
export declare const renderLabel: (label: ReactNode, required?: boolean) => string | number | bigint | boolean | Iterable<ReactNode> | Promise<string | number | bigint | boolean | ReactPortal | ReactElement<unknown, string | JSXElementConstructor<any>> | Iterable<ReactNode> | null | undefined> | JSX.Element | null | undefined;
|
|
1100
|
+
|
|
1101
|
+
/** 规则配置参数 */
|
|
1102
|
+
export declare type RuleConfig = {
|
|
1103
|
+
/** 规则参数值 (如 minLength 的长度) */
|
|
1104
|
+
value?: any;
|
|
1105
|
+
/** 自定义错误消息 */
|
|
1106
|
+
message?: string;
|
|
1107
|
+
/** 字段标签 (用于默认消息) */
|
|
1108
|
+
label?: string;
|
|
1109
|
+
};
|
|
1110
|
+
|
|
1111
|
+
/** 规则工厂函数 - 接收配置,返回 valibot check */
|
|
1112
|
+
export declare type RuleFactory = (config?: RuleConfig) => v.PipeItem<any, any, v.BaseIssue<unknown>>;
|
|
1113
|
+
|
|
1114
|
+
/** 规则适配器选项 */
|
|
1115
|
+
export declare type RulesAdapterOptions = {
|
|
1116
|
+
/** 字段标签(用于默认错误消息) */
|
|
1117
|
+
label?: string;
|
|
1118
|
+
/** 字段类型 */
|
|
1119
|
+
fieldType?: FieldType;
|
|
1120
|
+
/** 当前表单值(用于 custom 规则) */
|
|
1121
|
+
values?: Record<string, unknown>;
|
|
1122
|
+
};
|
|
1123
|
+
|
|
1124
|
+
/**
|
|
1125
|
+
* 将声明式验证规则转换为 Valibot schema
|
|
1126
|
+
*
|
|
1127
|
+
* @example
|
|
1128
|
+
* ```tsx
|
|
1129
|
+
* const schema = rulesToValibot([
|
|
1130
|
+
* { type: 'required', message: '必填' },
|
|
1131
|
+
* { type: 'minLength', value: 3, message: '至少3个字符' },
|
|
1132
|
+
* { type: 'email' },
|
|
1133
|
+
* ], { label: '邮箱', fieldType: 'text' });
|
|
1134
|
+
* ```
|
|
1135
|
+
*/
|
|
1136
|
+
export declare function rulesToValibot(rules: ValidationRule[], options?: RulesAdapterOptions): v.BaseSchema<unknown, unknown, v.BaseIssue<unknown>>;
|
|
1137
|
+
|
|
1138
|
+
/**
|
|
1139
|
+
* 运行时配置
|
|
1140
|
+
*/
|
|
1141
|
+
export declare type RuntimeConfig = {
|
|
1142
|
+
/** EffectSystem 配置 */
|
|
1143
|
+
effect?: EffectSystemConfig;
|
|
1144
|
+
/** AsyncScheduler 配置 */
|
|
1145
|
+
async?: AsyncSchedulerConfig;
|
|
1146
|
+
/** 是否自动初始化 (执行所有规则) */
|
|
1147
|
+
autoInitialize?: boolean;
|
|
1148
|
+
};
|
|
1149
|
+
|
|
1150
|
+
/**
|
|
1151
|
+
* 安全的表达式求值器
|
|
1152
|
+
* 基于 AST 解释执行,禁止 eval/new Function
|
|
1153
|
+
*/
|
|
1154
|
+
export declare class SafeEvaluator {
|
|
1155
|
+
private allowedGlobals;
|
|
1156
|
+
constructor();
|
|
1157
|
+
/**
|
|
1158
|
+
* 编译表达式为可执行函数
|
|
1159
|
+
* @param expr 表达式字符串
|
|
1160
|
+
* @returns 执行函数
|
|
1161
|
+
* @throws Error 如果表达式无效或包含危险代码
|
|
1162
|
+
*/
|
|
1163
|
+
compile(expr: string): (scope: EvalScope) => any;
|
|
1164
|
+
/**
|
|
1165
|
+
* 尝试编译表达式,不抛出异常
|
|
1166
|
+
* @param expr 表达式字符串
|
|
1167
|
+
* @returns 编译结果或 null
|
|
1168
|
+
*/
|
|
1169
|
+
tryCompile(expr: string): ((scope: EvalScope) => any) | null;
|
|
1170
|
+
/**
|
|
1171
|
+
* 递归评估 AST 节点
|
|
1172
|
+
*/
|
|
1173
|
+
private evaluate;
|
|
1174
|
+
/**
|
|
1175
|
+
* 从表达式中提取变量依赖
|
|
1176
|
+
* @param expr 表达式字符串
|
|
1177
|
+
* @returns 依赖的变量名数组 (去重)
|
|
1178
|
+
*/
|
|
1179
|
+
extractDependencies(expr: string): string[];
|
|
1180
|
+
/**
|
|
1181
|
+
* 验证表达式是否安全
|
|
1182
|
+
* @param expr 表达式字符串
|
|
1183
|
+
* @returns 验证结果
|
|
1184
|
+
*/
|
|
1185
|
+
validate(expr: string): {
|
|
1186
|
+
valid: boolean;
|
|
1187
|
+
error?: string;
|
|
1188
|
+
};
|
|
1189
|
+
/**
|
|
1190
|
+
* 递归验证 AST 节点的安全性
|
|
1191
|
+
*/
|
|
1192
|
+
private validateNode;
|
|
1193
|
+
private visitIdentifiers;
|
|
1194
|
+
}
|
|
1195
|
+
|
|
1196
|
+
export declare const safeEvaluator: SafeEvaluator;
|
|
1197
|
+
|
|
1198
|
+
/**
|
|
1199
|
+
* Schema 编译器 (V4)
|
|
1200
|
+
*/
|
|
1201
|
+
export declare class SchemaCompiler {
|
|
1202
|
+
private options;
|
|
1203
|
+
private dependencyAnalyzer;
|
|
1204
|
+
constructor(options?: CompilerOptions);
|
|
1205
|
+
compile(input: SchemaInput): CompiledSchema;
|
|
1206
|
+
/**
|
|
1207
|
+
* 版本兼容性检查
|
|
1208
|
+
*/
|
|
1209
|
+
private checkVersion;
|
|
1210
|
+
private processFields;
|
|
1211
|
+
private extractOptionsRule;
|
|
1212
|
+
private extractRule;
|
|
1213
|
+
}
|
|
1214
|
+
|
|
1215
|
+
/** 默认编译器实例 */
|
|
1216
|
+
export declare const schemaCompiler: SchemaCompiler;
|
|
1217
|
+
|
|
1218
|
+
export declare type SchemaField = {
|
|
1219
|
+
name: string;
|
|
1220
|
+
component: string;
|
|
1221
|
+
defaultValue?: any;
|
|
1222
|
+
visibleWhen?: string | ((scope: EvalScope) => boolean);
|
|
1223
|
+
disabledWhen?: string | ((scope: EvalScope) => boolean);
|
|
1224
|
+
requiredWhen?: string | ((scope: EvalScope) => boolean);
|
|
1225
|
+
compute?: string | ((scope: EvalScope) => any);
|
|
1226
|
+
/** 校验规则 (Valibot Schema or Adapter) */
|
|
1227
|
+
validate?: any;
|
|
1228
|
+
/**
|
|
1229
|
+
* 选项配置
|
|
1230
|
+
* - 数组:静态选项
|
|
1231
|
+
* - 函数:异步选项(无依赖追踪)
|
|
1232
|
+
* - 对象:异步选项 + 手动指定依赖(推荐用于级联选择)
|
|
1233
|
+
* @example
|
|
1234
|
+
* // 静态选项
|
|
1235
|
+
* options: [{ label: '选项1', value: '1' }]
|
|
1236
|
+
*
|
|
1237
|
+
* // 异步选项(无依赖,仅初始化时加载)
|
|
1238
|
+
* options: async (scope, signal) => fetchOptions()
|
|
1239
|
+
*
|
|
1240
|
+
* // 异步选项 + 依赖(推荐:依赖变化时重新加载)
|
|
1241
|
+
* options: {
|
|
1242
|
+
* fetcher: async (scope, signal) => fetchCities(scope.values.province),
|
|
1243
|
+
* deps: ['province']
|
|
1244
|
+
* }
|
|
1245
|
+
*/
|
|
1246
|
+
options?: any[] | ((scope: EvalScope, signal?: AbortSignal) => Promise<any[]>) | AsyncOptionsConfig;
|
|
1247
|
+
children?: SchemaField[];
|
|
1248
|
+
/** 栅格布局配置 (MUI Grid size) */
|
|
1249
|
+
colSpan?: number | Record<string, number>;
|
|
1250
|
+
/** 独占一行(组件占满整行,内部宽度由 colSpan 控制) */
|
|
1251
|
+
independent?: boolean;
|
|
1252
|
+
ui?: Record<string, any>;
|
|
1253
|
+
};
|
|
1254
|
+
|
|
1255
|
+
export declare const SchemaForm: <T extends Record<string, any> = Record<string, any>>(props: SchemaFormProps<T> & {
|
|
1256
|
+
ref?: default_2.ForwardedRef<SchemaFormInstance<T>>;
|
|
385
1257
|
}) => default_2.ReactElement;
|
|
386
1258
|
|
|
387
|
-
|
|
1259
|
+
/**
|
|
1260
|
+
* SchemaForm 实例方法 (通过 ref 暴露)
|
|
1261
|
+
*/
|
|
1262
|
+
export declare interface SchemaFormInstance<T = any> {
|
|
388
1263
|
/** 提交表单 */
|
|
389
|
-
submit: () =>
|
|
390
|
-
/**
|
|
391
|
-
|
|
1264
|
+
submit: () => void;
|
|
1265
|
+
/** 重置表单 */
|
|
1266
|
+
reset: () => void;
|
|
1267
|
+
/** 获取所有值 */
|
|
1268
|
+
getValues: () => T;
|
|
1269
|
+
/** 设置字段值 */
|
|
1270
|
+
setValue: (name: keyof T, value: any) => void;
|
|
392
1271
|
/** 批量设置值 */
|
|
393
1272
|
setValues: (values: Partial<T>) => void;
|
|
394
|
-
|
|
1273
|
+
/** 获取 TanStack Form 实例 */
|
|
1274
|
+
getForm: () => any;
|
|
1275
|
+
/** 获取 Runtime 实例 */
|
|
1276
|
+
getRuntime: () => FormRuntime;
|
|
1277
|
+
/** 获取编译后的 Schema */
|
|
1278
|
+
getCompiledSchema: () => CompiledSchema;
|
|
1279
|
+
/** 触发字段校验 */
|
|
1280
|
+
validate: (name?: string) => Promise<boolean>;
|
|
1281
|
+
/** 清除错误 */
|
|
1282
|
+
clearErrors: (name?: string) => void;
|
|
1283
|
+
}
|
|
395
1284
|
|
|
396
|
-
|
|
1285
|
+
/**
|
|
1286
|
+
* SchemaForm Props
|
|
1287
|
+
*/
|
|
1288
|
+
export declare type SchemaFormProps<T extends Record<string, any> = Record<string, any>> = {
|
|
397
1289
|
/** Schema 定义 */
|
|
398
|
-
schema: SchemaInput
|
|
1290
|
+
schema: SchemaInput;
|
|
399
1291
|
/** 默认值 */
|
|
400
1292
|
defaultValues?: Partial<T>;
|
|
401
1293
|
/** 提交回调 */
|
|
402
|
-
onSubmit?: (values: T) => void | Promise<void
|
|
1294
|
+
onSubmit?: (values: T) => void | Promise<void>;
|
|
403
1295
|
/** 值变化回调 */
|
|
404
1296
|
onValuesChange?: (values: T) => void;
|
|
405
|
-
/**
|
|
406
|
-
|
|
1297
|
+
/** 提交失败回调 */
|
|
1298
|
+
onSubmitFailed?: (errors: any) => void;
|
|
1299
|
+
/** 自定义 Widget 映射 */
|
|
1300
|
+
widgets?: WidgetRegistry;
|
|
1301
|
+
/** 全局禁用 */
|
|
1302
|
+
disabled?: boolean;
|
|
407
1303
|
/** 全局只读 */
|
|
408
1304
|
readOnly?: boolean;
|
|
1305
|
+
/** 栅格间距 */
|
|
1306
|
+
spacing?: number;
|
|
1307
|
+
/** form 标签的额外属性 */
|
|
1308
|
+
formProps?: Omit<FormHTMLAttributes<HTMLFormElement>, "onSubmit">;
|
|
1309
|
+
/** 子元素 (如提交按钮) */
|
|
1310
|
+
children?: ReactNode;
|
|
1311
|
+
/** 容器样式 */
|
|
1312
|
+
sx?: any;
|
|
1313
|
+
/** 编译器配置 */
|
|
1314
|
+
compilerOptions?: UseSchemaFormOptions<T>["compilerOptions"];
|
|
1315
|
+
/** 运行时配置 */
|
|
1316
|
+
runtimeConfig?: UseSchemaFormOptions<T>["runtimeConfig"];
|
|
1317
|
+
};
|
|
1318
|
+
|
|
1319
|
+
export declare const SchemaFormProvider: default_2.FC<{
|
|
1320
|
+
runtime: FormRuntime;
|
|
1321
|
+
children: default_2.ReactNode;
|
|
1322
|
+
}>;
|
|
1323
|
+
|
|
1324
|
+
/**
|
|
1325
|
+
* 用户输入的 Schema (Source)
|
|
1326
|
+
*/
|
|
1327
|
+
export declare type SchemaInput = {
|
|
1328
|
+
meta?: SchemaMeta;
|
|
1329
|
+
fields: SchemaField[];
|
|
1330
|
+
};
|
|
1331
|
+
|
|
1332
|
+
/**
|
|
1333
|
+
* Schema 校验器
|
|
1334
|
+
*
|
|
1335
|
+
* 在编译时检测 Schema 中的问题
|
|
1336
|
+
*/
|
|
1337
|
+
export declare class SchemaLinter {
|
|
1338
|
+
private options;
|
|
1339
|
+
constructor(options?: LinterOptions);
|
|
1340
|
+
/**
|
|
1341
|
+
* 校验 Schema
|
|
1342
|
+
*/
|
|
1343
|
+
lint(schema: SchemaInput): LintResult;
|
|
1344
|
+
/**
|
|
1345
|
+
* 递归校验字段
|
|
1346
|
+
*/
|
|
1347
|
+
private lintFields;
|
|
1348
|
+
/**
|
|
1349
|
+
* 校验表达式
|
|
1350
|
+
*/
|
|
1351
|
+
private lintExpression;
|
|
1352
|
+
}
|
|
1353
|
+
|
|
1354
|
+
/**
|
|
1355
|
+
* 默认 Linter 实例
|
|
1356
|
+
*/
|
|
1357
|
+
export declare const schemaLinter: SchemaLinter;
|
|
1358
|
+
|
|
1359
|
+
/**
|
|
1360
|
+
* Schema 版本与兼容性信息
|
|
1361
|
+
*/
|
|
1362
|
+
export declare type SchemaMeta = {
|
|
1363
|
+
version: string;
|
|
1364
|
+
compatibleWith?: string[];
|
|
1365
|
+
};
|
|
1366
|
+
|
|
1367
|
+
/**
|
|
1368
|
+
* Schema 渲染器
|
|
1369
|
+
*
|
|
1370
|
+
* 根据编译后的 Schema 自动渲染表单字段
|
|
1371
|
+
*
|
|
1372
|
+
* @example
|
|
1373
|
+
* ```tsx
|
|
1374
|
+
* <SchemaRenderer
|
|
1375
|
+
* schema={compiledSchema}
|
|
1376
|
+
* form={form}
|
|
1377
|
+
* widgets={{ CustomWidget: MyCustomWidget }}
|
|
1378
|
+
* />
|
|
1379
|
+
* ```
|
|
1380
|
+
*/
|
|
1381
|
+
export declare const SchemaRenderer: default_2.NamedExoticComponent<SchemaRendererProps>;
|
|
1382
|
+
|
|
1383
|
+
export declare type SchemaRendererProps = {
|
|
1384
|
+
/** 编译后的 Schema */
|
|
1385
|
+
schema: CompiledSchema;
|
|
1386
|
+
/** TanStack Form 实例 */
|
|
1387
|
+
form: any;
|
|
1388
|
+
/** 自定义 Widget 映射 (覆盖默认) */
|
|
1389
|
+
widgets?: WidgetRegistry;
|
|
409
1390
|
/** 全局禁用 */
|
|
410
1391
|
disabled?: boolean;
|
|
411
|
-
/**
|
|
412
|
-
|
|
413
|
-
/**
|
|
414
|
-
children?: React.ReactNode;
|
|
415
|
-
/** 间距 */
|
|
1392
|
+
/** 全局只读 */
|
|
1393
|
+
readOnly?: boolean;
|
|
1394
|
+
/** 栅格间距 */
|
|
416
1395
|
spacing?: number;
|
|
417
1396
|
};
|
|
418
1397
|
|
|
419
|
-
|
|
420
|
-
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
|
|
1398
|
+
/**
|
|
1399
|
+
* 规则类型定义
|
|
1400
|
+
*/
|
|
1401
|
+
export declare type SchemaRule = {
|
|
1402
|
+
type: 'derive';
|
|
1403
|
+
target: string;
|
|
1404
|
+
deps: string[];
|
|
1405
|
+
/** 预编译后的执行函数 */
|
|
1406
|
+
evaluator: (scope: EvalScope) => any;
|
|
1407
|
+
priority: number;
|
|
1408
|
+
} | {
|
|
1409
|
+
type: 'gate';
|
|
1410
|
+
target: string;
|
|
1411
|
+
deps: string[];
|
|
1412
|
+
evaluator: (scope: EvalScope) => boolean;
|
|
1413
|
+
effect: 'visible' | 'disabled' | 'required';
|
|
1414
|
+
priority: number;
|
|
1415
|
+
} | {
|
|
1416
|
+
type: 'options';
|
|
1417
|
+
target: string;
|
|
1418
|
+
deps: string[];
|
|
1419
|
+
fetcher: (scope: EvalScope, signal: AbortSignal) => Promise<any>;
|
|
1420
|
+
/** 生成缓存 Key 的策略,e.g., `${field}:${hash(deps)}` */
|
|
1421
|
+
cacheKey?: (scope: EvalScope) => string;
|
|
1422
|
+
priority: number;
|
|
1423
|
+
} | {
|
|
1424
|
+
type: 'effect';
|
|
1425
|
+
deps: string[];
|
|
1426
|
+
handler: (scope: EvalScope, api: any) => void;
|
|
1427
|
+
priority: number;
|
|
424
1428
|
};
|
|
425
1429
|
|
|
426
|
-
/**
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
notIn?: unknown[];
|
|
437
|
-
empty?: boolean;
|
|
438
|
-
notEmpty?: boolean;
|
|
1430
|
+
/** 搜索清空相关配置 */
|
|
1431
|
+
declare type SearchClearConfig = {
|
|
1432
|
+
/** 关闭面板后保持搜索值,默认 false */
|
|
1433
|
+
keepSearchOnClose?: boolean;
|
|
1434
|
+
/** 选中选项后保持搜索值,默认 false */
|
|
1435
|
+
keepSearchOnSelect?: boolean;
|
|
1436
|
+
/** 缓存最后一次非空搜索值,默认 false */
|
|
1437
|
+
cacheSearchKeyword?: boolean;
|
|
1438
|
+
/** 仅清空搜索值,不重置列表,默认 false */
|
|
1439
|
+
clearValueOnly?: boolean;
|
|
439
1440
|
};
|
|
440
1441
|
|
|
441
|
-
|
|
442
|
-
|
|
1442
|
+
export declare const SelectWidget: FC<AutocompleteWidgetProps>;
|
|
1443
|
+
|
|
1444
|
+
export declare type SelectWidgetProps = AutocompleteWidgetProps;
|
|
443
1445
|
|
|
444
1446
|
/**
|
|
445
|
-
*
|
|
446
|
-
*
|
|
1447
|
+
* SelectWidget is now an alias for AutocompleteWidget.
|
|
1448
|
+
* It provides unified functionality using MUI Autocomplete.
|
|
447
1449
|
*/
|
|
448
|
-
export declare const
|
|
1450
|
+
export declare const SelectWidgetRender: NamedExoticComponent<AutocompleteWidgetRenderProps>;
|
|
449
1451
|
|
|
450
|
-
export declare
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
|
|
1452
|
+
export declare const SliderWidget: default_2.FC<SliderWidgetProps>;
|
|
1453
|
+
|
|
1454
|
+
export declare type SliderWidgetProps = {
|
|
1455
|
+
form: any;
|
|
1456
|
+
name: string;
|
|
1457
|
+
validate?: any;
|
|
1458
|
+
} & Omit<SliderWidgetRenderProps, keyof WidgetProps>;
|
|
1459
|
+
|
|
1460
|
+
export declare const SliderWidgetRender: default_2.NamedExoticComponent<SliderWidgetRenderProps>;
|
|
1461
|
+
|
|
1462
|
+
export declare type SliderWidgetRenderProps = WidgetProps & {
|
|
1463
|
+
label?: string;
|
|
1464
|
+
helperText?: string;
|
|
1465
|
+
min?: number;
|
|
1466
|
+
max?: number;
|
|
1467
|
+
step?: number;
|
|
1468
|
+
marks?: boolean | {
|
|
1469
|
+
value: number;
|
|
1470
|
+
label?: string;
|
|
1471
|
+
}[];
|
|
1472
|
+
valueLabelDisplay?: "on" | "auto" | "off";
|
|
1473
|
+
showValue?: boolean;
|
|
1474
|
+
/** 内联模式:label 和 slider 在同一行 */
|
|
1475
|
+
inline?: boolean;
|
|
1476
|
+
};
|
|
1477
|
+
|
|
1478
|
+
/**
|
|
1479
|
+
* 静态分析报告
|
|
1480
|
+
*/
|
|
1481
|
+
export declare type StaticAnalysisReport = {
|
|
1482
|
+
/** 循环依赖 (SCC with size > 1) */
|
|
1483
|
+
cycles: string[][];
|
|
1484
|
+
/** 孤立字段 (无入边也无出边的节点,即没有依赖也不被依赖) */
|
|
1485
|
+
isolatedFields: string[];
|
|
1486
|
+
/** 警告信息 */
|
|
1487
|
+
warnings: string[];
|
|
1488
|
+
};
|
|
1489
|
+
|
|
1490
|
+
/** Suffix 按钮渲染函数 */
|
|
1491
|
+
declare type SuffixButtonRender = (searchValue: string, hasOptions: boolean) => ButtonConfig | false | null;
|
|
1492
|
+
|
|
1493
|
+
export declare const SwitchWidget: default_2.FC<SwitchWidgetProps>;
|
|
1494
|
+
|
|
1495
|
+
export declare type SwitchWidgetProps = {
|
|
1496
|
+
form: any;
|
|
1497
|
+
name: string;
|
|
1498
|
+
validate?: any;
|
|
1499
|
+
} & Omit<SwitchWidgetRenderProps, keyof WidgetProps>;
|
|
1500
|
+
|
|
1501
|
+
export declare const SwitchWidgetRender: default_2.NamedExoticComponent<SwitchWidgetRenderProps>;
|
|
1502
|
+
|
|
1503
|
+
declare type SwitchWidgetRenderProps = WidgetProps & {
|
|
1504
|
+
label?: string;
|
|
1505
|
+
helperText?: string;
|
|
1506
|
+
switchProps?: Partial<SwitchProps>;
|
|
1507
|
+
};
|
|
1508
|
+
|
|
1509
|
+
/**
|
|
1510
|
+
* 文本输入组件 (MUI TextField)
|
|
1511
|
+
*
|
|
1512
|
+
* 包含 FieldAdapter,可独立使用
|
|
1513
|
+
*
|
|
1514
|
+
* @example
|
|
1515
|
+
* ```tsx
|
|
1516
|
+
* <TextWidget form={form} name="username" label="用户名" />
|
|
1517
|
+
* ```
|
|
1518
|
+
*/
|
|
1519
|
+
export declare const TextWidget: default_2.FC<TextWidgetProps>;
|
|
1520
|
+
|
|
1521
|
+
/**
|
|
1522
|
+
* 独立组件 Props (带 form/name)
|
|
1523
|
+
*/
|
|
1524
|
+
export declare type TextWidgetProps = {
|
|
1525
|
+
form: any;
|
|
1526
|
+
name: string;
|
|
1527
|
+
validate?: any;
|
|
1528
|
+
} & Omit<TextWidgetRenderProps, keyof WidgetProps>;
|
|
1529
|
+
|
|
1530
|
+
/**
|
|
1531
|
+
* 文本输入渲染组件
|
|
1532
|
+
*
|
|
1533
|
+
* 接收 WidgetProps,不包含 FieldAdapter
|
|
1534
|
+
*/
|
|
1535
|
+
export declare const TextWidgetRender: default_2.NamedExoticComponent<TextWidgetRenderProps>;
|
|
1536
|
+
|
|
1537
|
+
/**
|
|
1538
|
+
* 纯渲染组件 Props (用于 SchemaRenderer)
|
|
1539
|
+
*/
|
|
1540
|
+
export declare type TextWidgetRenderProps = WidgetProps & {
|
|
1541
|
+
label?: string;
|
|
1542
|
+
placeholder?: string;
|
|
1543
|
+
helperText?: string;
|
|
1544
|
+
multiline?: boolean;
|
|
1545
|
+
rows?: number;
|
|
1546
|
+
type?: "text" | "password" | "email" | "url" | "tel";
|
|
1547
|
+
inputProps?: Record<string, any>;
|
|
1548
|
+
slotProps?: TextFieldProps["slotProps"];
|
|
1549
|
+
};
|
|
1550
|
+
|
|
1551
|
+
export declare const TIME_FORMAT = "HH:mm";
|
|
1552
|
+
|
|
1553
|
+
export declare const TimeWidget: default_2.FC<TimeWidgetProps>;
|
|
1554
|
+
|
|
1555
|
+
export declare type TimeWidgetProps = {
|
|
1556
|
+
form: any;
|
|
1557
|
+
name: string;
|
|
1558
|
+
validate?: any;
|
|
1559
|
+
} & Omit<TimeWidgetRenderProps, keyof WidgetProps>;
|
|
1560
|
+
|
|
1561
|
+
export declare const TimeWidgetRender: default_2.NamedExoticComponent<TimeWidgetRenderProps>;
|
|
1562
|
+
|
|
1563
|
+
export declare type TimeWidgetRenderProps = WidgetProps & {
|
|
1564
|
+
label?: string;
|
|
1565
|
+
helperText?: string;
|
|
1566
|
+
format?: string;
|
|
1567
|
+
ampm?: boolean;
|
|
1568
|
+
/** 分钟步长,默认 1 */
|
|
1569
|
+
minutesStep?: number;
|
|
1570
|
+
/** 秒步长,默认无 */
|
|
1571
|
+
secondsStep?: number;
|
|
1572
|
+
};
|
|
1573
|
+
|
|
1574
|
+
export declare const useLayoutContext: () => LayoutContextType;
|
|
1575
|
+
|
|
1576
|
+
export declare const useRuntime: () => FormRuntime;
|
|
1577
|
+
|
|
1578
|
+
/**
|
|
1579
|
+
* Schema Form 主 Hook (V4)
|
|
1580
|
+
*
|
|
1581
|
+
* 整合 Schema 编译、TanStack Form 和 Runtime
|
|
1582
|
+
*
|
|
1583
|
+
* @example
|
|
1584
|
+
* ```tsx
|
|
1585
|
+
* const { form, runtime } = useSchemaForm({
|
|
1586
|
+
* schema: mySchema,
|
|
1587
|
+
* defaultValues: { name: '' },
|
|
1588
|
+
* onSubmit: (values) => console.log(values),
|
|
1589
|
+
* });
|
|
1590
|
+
* ```
|
|
1591
|
+
*/
|
|
1592
|
+
export declare function useSchemaForm<T extends Record<string, any> = Record<string, any>>(options: UseSchemaFormOptions<T>): UseSchemaFormReturn<T>;
|
|
1593
|
+
|
|
1594
|
+
export declare type UseSchemaFormOptions<T extends Record<string, any> = Record<string, any>> = {
|
|
1595
|
+
/** Schema 输入 */
|
|
1596
|
+
schema: SchemaInput;
|
|
1597
|
+
/** 默认值 */
|
|
1598
|
+
defaultValues?: Partial<T>;
|
|
1599
|
+
/** 提交回调 */
|
|
1600
|
+
onSubmit?: (values: T) => void | Promise<void>;
|
|
1601
|
+
/** 值变化回调 */
|
|
1602
|
+
onValuesChange?: (values: T) => void;
|
|
1603
|
+
/** 编译器配置 */
|
|
1604
|
+
compilerOptions?: CompilerOptions;
|
|
1605
|
+
/** 运行时配置 */
|
|
1606
|
+
runtimeConfig?: RuntimeConfig;
|
|
1607
|
+
/** TanStack Form 额外配置 */
|
|
1608
|
+
formOptions?: Record<string, any>;
|
|
1609
|
+
};
|
|
456
1610
|
|
|
457
|
-
|
|
458
|
-
|
|
1611
|
+
export declare type UseSchemaFormReturn<T extends Record<string, any> = Record<string, any>> = {
|
|
1612
|
+
/** TanStack Form 实例 */
|
|
1613
|
+
form: AnyFormApi_3;
|
|
1614
|
+
/** 运行时实例 */
|
|
1615
|
+
runtime: FormRuntime;
|
|
1616
|
+
/** 编译后的 Schema */
|
|
1617
|
+
compiledSchema: CompiledSchema;
|
|
1618
|
+
/** 提交表单 */
|
|
1619
|
+
handleSubmit: () => void;
|
|
1620
|
+
/** 重置表单 */
|
|
1621
|
+
handleReset: () => void;
|
|
1622
|
+
/** 获取表单值 */
|
|
1623
|
+
getValues: () => T;
|
|
1624
|
+
/** 设置字段值 */
|
|
1625
|
+
setValue: (name: keyof T, value: any) => void;
|
|
1626
|
+
};
|
|
459
1627
|
|
|
460
|
-
/**
|
|
461
|
-
|
|
1628
|
+
/**
|
|
1629
|
+
* 验证预设 Hook
|
|
1630
|
+
*
|
|
1631
|
+
* @example
|
|
1632
|
+
* ```tsx
|
|
1633
|
+
* function MyForm() {
|
|
1634
|
+
* const { toSchema, override, register } = useValidationPresets({
|
|
1635
|
+
* extend: {
|
|
1636
|
+
* // 覆盖默认 email 规则 - 只允许特定后缀
|
|
1637
|
+
* email: (config) => v.check(
|
|
1638
|
+
* (val) => !val || /@(163|qq|gmail)\.com$/.test(String(val)),
|
|
1639
|
+
* config?.message ?? '只支持 163、QQ、Gmail 邮箱'
|
|
1640
|
+
* ),
|
|
1641
|
+
* },
|
|
1642
|
+
* });
|
|
1643
|
+
*
|
|
1644
|
+
* // 动态添加新规则
|
|
1645
|
+
* useEffect(() => {
|
|
1646
|
+
* register('companyEmail', (config) => v.check(
|
|
1647
|
+
* (val) => !val || /@mycompany\.com$/.test(String(val)),
|
|
1648
|
+
* config?.message ?? '请使用公司邮箱'
|
|
1649
|
+
* ));
|
|
1650
|
+
* }, []);
|
|
1651
|
+
*
|
|
1652
|
+
* // 使用预设规则
|
|
1653
|
+
* const emailSchema = toSchema([
|
|
1654
|
+
* { type: 'required', message: '邮箱必填' },
|
|
1655
|
+
* { type: 'email' },
|
|
1656
|
+
* ]);
|
|
1657
|
+
*
|
|
1658
|
+
* return <SchemaForm ... />;
|
|
1659
|
+
* }
|
|
1660
|
+
* ```
|
|
1661
|
+
*/
|
|
1662
|
+
export declare function useValidationPresets(options?: UseValidationPresetsOptions): UseValidationPresetsReturn;
|
|
462
1663
|
|
|
463
|
-
/**
|
|
464
|
-
|
|
1664
|
+
/**
|
|
1665
|
+
* 使用 Provider 中的验证预设
|
|
1666
|
+
*
|
|
1667
|
+
* 如果没有 Provider,则使用默认全局预设
|
|
1668
|
+
*/
|
|
1669
|
+
export declare function useValidationPresetsContext(): UseValidationPresetsReturn;
|
|
465
1670
|
|
|
466
|
-
|
|
467
|
-
|
|
1671
|
+
export declare type UseValidationPresetsOptions = {
|
|
1672
|
+
/**
|
|
1673
|
+
* 是否使用独立的注册表实例
|
|
1674
|
+
* - true: 创建新的注册表,不影响全局
|
|
1675
|
+
* - false: 使用全局注册表 (默认)
|
|
1676
|
+
*/
|
|
1677
|
+
isolated?: boolean;
|
|
1678
|
+
/**
|
|
1679
|
+
* 初始规则扩展
|
|
1680
|
+
* 可用于覆盖默认规则或添加新规则
|
|
1681
|
+
*/
|
|
1682
|
+
extend?: Record<string, RuleFactory>;
|
|
1683
|
+
};
|
|
1684
|
+
|
|
1685
|
+
export declare type UseValidationPresetsReturn = {
|
|
1686
|
+
/**
|
|
1687
|
+
* 注册新的预设规则
|
|
1688
|
+
* @param name 规则名称
|
|
1689
|
+
* @param factory 规则工厂函数
|
|
1690
|
+
*/
|
|
1691
|
+
register: (name: string, factory: RuleFactory) => void;
|
|
1692
|
+
/**
|
|
1693
|
+
* 覆盖已有的预设规则
|
|
1694
|
+
* @param name 规则名称
|
|
1695
|
+
* @param factory 规则工厂函数
|
|
1696
|
+
*/
|
|
1697
|
+
override: (name: string, factory: RuleFactory) => void;
|
|
1698
|
+
/**
|
|
1699
|
+
* 批量注册/覆盖规则
|
|
1700
|
+
* @param rules 规则映射
|
|
1701
|
+
*/
|
|
1702
|
+
extend: (rules: Record<string, RuleFactory>) => void;
|
|
1703
|
+
/**
|
|
1704
|
+
* 检查规则是否存在
|
|
1705
|
+
*/
|
|
1706
|
+
has: (name: string) => boolean;
|
|
1707
|
+
/**
|
|
1708
|
+
* 获取所有已注册的规则名称
|
|
1709
|
+
*/
|
|
1710
|
+
getNames: () => string[];
|
|
1711
|
+
/**
|
|
1712
|
+
* 将预设规则数组转换为 valibot schema
|
|
1713
|
+
*
|
|
1714
|
+
* @example
|
|
1715
|
+
* ```tsx
|
|
1716
|
+
* const schema = toSchema([
|
|
1717
|
+
* { type: 'required', message: '必填' },
|
|
1718
|
+
* { type: 'email', message: '请输入有效邮箱' },
|
|
1719
|
+
* ]);
|
|
1720
|
+
*
|
|
1721
|
+
* // 带参数
|
|
1722
|
+
* const schema = toSchema([
|
|
1723
|
+
* { type: 'required' },
|
|
1724
|
+
* { type: 'minLength', value: 3, message: '至少3个字符' },
|
|
1725
|
+
* ], { label: '用户名' });
|
|
1726
|
+
* ```
|
|
1727
|
+
*/
|
|
1728
|
+
toSchema: (rules: PresetRule[], options?: {
|
|
1729
|
+
label?: string;
|
|
1730
|
+
baseType?: "string" | "number" | "any";
|
|
1731
|
+
}) => v.BaseSchema<unknown, unknown, v.BaseIssue<unknown>>;
|
|
1732
|
+
/**
|
|
1733
|
+
* 获取原始注册表实例
|
|
1734
|
+
*/
|
|
1735
|
+
registry: ValidationPresetRegistry;
|
|
1736
|
+
};
|
|
1737
|
+
|
|
1738
|
+
/**
|
|
1739
|
+
* 表单级校验适配器
|
|
1740
|
+
*/
|
|
1741
|
+
export declare const valibotFormValidator: (schemaOrRules: any) => ({ value }: {
|
|
1742
|
+
value: any;
|
|
1743
|
+
}) => string | undefined;
|
|
1744
|
+
|
|
1745
|
+
/**
|
|
1746
|
+
* 将 Valibot Schema 或预设规则数组转换为 TanStack Form Validator
|
|
1747
|
+
* 支持同步和异步校验
|
|
1748
|
+
*
|
|
1749
|
+
* @example 支持两种校验格式
|
|
1750
|
+
* ```tsx
|
|
1751
|
+
* // 格式 1: Valibot Schema (高度自定义)
|
|
1752
|
+
* validate: v.pipe(v.string(), v.email('请输入有效邮箱'))
|
|
1753
|
+
*
|
|
1754
|
+
* // 格式 2: 预设规则数组 (简洁声明式)
|
|
1755
|
+
* validate: [
|
|
1756
|
+
* { type: 'required', message: '必填项' },
|
|
1757
|
+
* { type: 'email', message: '请输入有效邮箱' },
|
|
1758
|
+
* ]
|
|
1759
|
+
* ```
|
|
1760
|
+
*/
|
|
1761
|
+
export declare const valibotValidator: (schemaOrRules: any) => ({ value }: {
|
|
1762
|
+
value: any;
|
|
1763
|
+
}) => any;
|
|
1764
|
+
|
|
1765
|
+
/** 验证预设注册表类型 */
|
|
1766
|
+
export declare type ValidationPresetRegistry = {
|
|
1767
|
+
/** 获取规则工厂 */
|
|
1768
|
+
get: (name: string) => RuleFactory | undefined;
|
|
1769
|
+
/** 注册新规则 */
|
|
1770
|
+
register: (name: string, factory: RuleFactory) => void;
|
|
1771
|
+
/** 覆盖已有规则 */
|
|
1772
|
+
override: (name: string, factory: RuleFactory) => void;
|
|
1773
|
+
/** 批量注册规则 */
|
|
1774
|
+
registerAll: (rules: Record<string, RuleFactory>) => void;
|
|
1775
|
+
/** 检查规则是否存在 */
|
|
1776
|
+
has: (name: string) => boolean;
|
|
1777
|
+
/** 获取所有规则名称 */
|
|
1778
|
+
getNames: () => string[];
|
|
1779
|
+
/** 将预设规则数组转换为 valibot schema */
|
|
1780
|
+
toSchema: (rules: PresetRule[], options?: {
|
|
1781
|
+
label?: string;
|
|
1782
|
+
baseType?: "string" | "number" | "any";
|
|
1783
|
+
}) => v.BaseSchema<unknown, unknown, v.BaseIssue<unknown>>;
|
|
1784
|
+
};
|
|
1785
|
+
|
|
1786
|
+
/**
|
|
1787
|
+
* 验证预设 Provider
|
|
1788
|
+
*
|
|
1789
|
+
* 用于在应用级别配置验证预设,所有子组件共享
|
|
1790
|
+
*
|
|
1791
|
+
* @example
|
|
1792
|
+
* ```tsx
|
|
1793
|
+
* function App() {
|
|
1794
|
+
* return (
|
|
1795
|
+
* <ValidationPresetsProvider
|
|
1796
|
+
* extend={{
|
|
1797
|
+
* email: (config) => v.check(
|
|
1798
|
+
* (val) => !val || /@company\.com$/.test(String(val)),
|
|
1799
|
+
* '请使用公司邮箱'
|
|
1800
|
+
* ),
|
|
1801
|
+
* employeeId: (config) => v.check(
|
|
1802
|
+
* (val) => !val || /^EMP\d{6}$/.test(String(val)),
|
|
1803
|
+
* '员工编号格式不正确'
|
|
1804
|
+
* ),
|
|
1805
|
+
* }}
|
|
1806
|
+
* >
|
|
1807
|
+
* <MyForms />
|
|
1808
|
+
* </ValidationPresetsProvider>
|
|
1809
|
+
* );
|
|
1810
|
+
* }
|
|
1811
|
+
* ```
|
|
1812
|
+
*/
|
|
1813
|
+
export declare function ValidationPresetsProvider({ children, extend, isolated, }: ValidationPresetsProviderProps): JSX.Element;
|
|
1814
|
+
|
|
1815
|
+
export declare type ValidationPresetsProviderProps = {
|
|
1816
|
+
children: ReactNode;
|
|
1817
|
+
/**
|
|
1818
|
+
* 扩展规则
|
|
1819
|
+
*/
|
|
1820
|
+
extend?: Record<string, RuleFactory>;
|
|
1821
|
+
/**
|
|
1822
|
+
* 是否使用独立注册表
|
|
1823
|
+
*/
|
|
1824
|
+
isolated?: boolean;
|
|
1825
|
+
};
|
|
468
1826
|
|
|
469
1827
|
/** 基础验证规则 */
|
|
470
1828
|
export declare type ValidationRule = {
|
|
471
|
-
type:
|
|
1829
|
+
type: "required";
|
|
472
1830
|
message?: string;
|
|
473
1831
|
} | {
|
|
474
|
-
type:
|
|
1832
|
+
type: "minLength";
|
|
475
1833
|
value: number;
|
|
476
1834
|
message?: string;
|
|
477
1835
|
} | {
|
|
478
|
-
type:
|
|
1836
|
+
type: "maxLength";
|
|
479
1837
|
value: number;
|
|
480
1838
|
message?: string;
|
|
481
1839
|
} | {
|
|
482
|
-
type:
|
|
1840
|
+
type: "min";
|
|
483
1841
|
value: number;
|
|
484
1842
|
message?: string;
|
|
485
1843
|
} | {
|
|
486
|
-
type:
|
|
1844
|
+
type: "max";
|
|
487
1845
|
value: number;
|
|
488
1846
|
message?: string;
|
|
489
1847
|
} | {
|
|
490
|
-
type:
|
|
1848
|
+
type: "pattern";
|
|
491
1849
|
value: string | RegExp;
|
|
492
1850
|
message?: string;
|
|
493
1851
|
} | {
|
|
494
|
-
type:
|
|
1852
|
+
type: "email";
|
|
495
1853
|
message?: string;
|
|
496
1854
|
} | {
|
|
497
|
-
type:
|
|
1855
|
+
type: "url";
|
|
498
1856
|
message?: string;
|
|
499
1857
|
} | {
|
|
500
|
-
type:
|
|
1858
|
+
type: "custom";
|
|
501
1859
|
validate: (value: unknown, values: unknown) => boolean | string;
|
|
502
1860
|
} | {
|
|
503
|
-
type:
|
|
1861
|
+
type: "array";
|
|
504
1862
|
minItems?: number;
|
|
505
1863
|
maxItems?: number;
|
|
506
1864
|
message?: string;
|
|
507
1865
|
};
|
|
508
1866
|
|
|
509
|
-
|
|
510
|
-
|
|
1867
|
+
export declare interface WidgetProps {
|
|
1868
|
+
/** 字段值 */
|
|
1869
|
+
value: any;
|
|
1870
|
+
/** 值变更回调 */
|
|
1871
|
+
onChange: (val: any) => void;
|
|
1872
|
+
/** 失焦回调 */
|
|
1873
|
+
onBlur: () => void;
|
|
1874
|
+
/** 错误信息 */
|
|
1875
|
+
error?: string;
|
|
1876
|
+
/** 是否禁用 */
|
|
1877
|
+
disabled?: boolean;
|
|
1878
|
+
/** 是否可见 */
|
|
1879
|
+
visible?: boolean;
|
|
1880
|
+
/** 是否必填 */
|
|
1881
|
+
required?: boolean;
|
|
1882
|
+
/** 选项列表 (Select/Radio 等) */
|
|
1883
|
+
options?: any[];
|
|
1884
|
+
/** 字段名 */
|
|
1885
|
+
name?: string;
|
|
1886
|
+
/** 是否为脏数据 */
|
|
1887
|
+
isDirty?: boolean;
|
|
1888
|
+
/** 是否被触摸过 */
|
|
1889
|
+
isTouched?: boolean;
|
|
1890
|
+
/** 子布局节点 (用于容器型 Widget) */
|
|
1891
|
+
layoutChildren?: LayoutNode[];
|
|
1892
|
+
}
|
|
1893
|
+
|
|
1894
|
+
export declare type WidgetRegistry = Record<string, default_2.ComponentType<any>>;
|
|
511
1895
|
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
|
|
515
|
-
|
|
516
|
-
|
|
517
|
-
/** 是否有错误 */
|
|
518
|
-
error?: boolean;
|
|
519
|
-
/** 帮助/错误文本 */
|
|
520
|
-
helperText?: React.ReactNode;
|
|
521
|
-
/** 选项(用于 Select 等) */
|
|
522
|
-
options?: OptionItem[];
|
|
523
|
-
/** 透传属性 */
|
|
524
|
-
fieldProps?: Record<string, unknown> & {
|
|
525
|
-
disabled?: boolean;
|
|
526
|
-
required?: boolean;
|
|
527
|
-
readOnly?: boolean;
|
|
528
|
-
};
|
|
529
|
-
/** 表单实例 */
|
|
530
|
-
form?: UseFormReturn<T>;
|
|
531
|
-
/** 字段 Schema(用于 Group/FormList) */
|
|
532
|
-
schema?: FieldSchema<T>;
|
|
533
|
-
/** Widget 映射(用于嵌套渲染) */
|
|
534
|
-
widgets?: Record<string, WidgetComponent<T>>;
|
|
535
|
-
/** 选项映射(用于嵌套渲染) */
|
|
536
|
-
optionsMap?: Record<string, OptionItem[]>;
|
|
537
|
-
/** 全局禁用 */
|
|
538
|
-
globalDisabled?: boolean;
|
|
539
|
-
/** 全局只读 */
|
|
540
|
-
globalReadOnly?: boolean;
|
|
541
|
-
/** 当前表单值 (优化) */
|
|
542
|
-
values?: Record<string, unknown>;
|
|
543
|
-
};
|
|
1896
|
+
/**
|
|
1897
|
+
* Widget 渲染函数类型
|
|
1898
|
+
* 接收 WidgetProps 和额外的 UI 属性
|
|
1899
|
+
*/
|
|
1900
|
+
export declare type WidgetRenderFn = React.ComponentType<WidgetProps & Record<string, any>>;
|
|
544
1901
|
|
|
545
1902
|
export { }
|