@fogpipe/forma-core 0.11.2 → 0.12.0-alpha.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.
- package/dist/{chunk-XS3BLVIZ.js → chunk-ZSW7NIMY.js} +127 -22
- package/dist/chunk-ZSW7NIMY.js.map +1 -0
- package/dist/engine/enabled.d.ts.map +1 -1
- package/dist/engine/index.cjs +105 -21
- package/dist/engine/index.cjs.map +1 -1
- package/dist/engine/index.d.ts +2 -0
- package/dist/engine/index.d.ts.map +1 -1
- package/dist/engine/index.js +5 -1
- package/dist/engine/readonly.d.ts +44 -0
- package/dist/engine/readonly.d.ts.map +1 -0
- package/dist/engine/validate.d.ts.map +1 -1
- package/dist/engine/visibility.d.ts.map +1 -1
- package/dist/index.cjs +133 -21
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +2 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +15 -1
- package/dist/types.d.ts +128 -9
- package/dist/types.d.ts.map +1 -1
- package/package.json +1 -1
- package/src/__tests__/validate.test.ts +1 -0
- package/src/engine/enabled.ts +34 -16
- package/src/engine/index.ts +10 -0
- package/src/engine/readonly.ts +169 -0
- package/src/engine/required.ts +1 -1
- package/src/engine/validate.ts +9 -3
- package/src/engine/visibility.ts +8 -6
- package/src/index.ts +20 -2
- package/src/types.ts +181 -12
- package/dist/chunk-XS3BLVIZ.js.map +0 -1
package/dist/types.d.ts
CHANGED
|
@@ -3,6 +3,16 @@
|
|
|
3
3
|
*
|
|
4
4
|
* This module defines the complete type system for Forma specifications.
|
|
5
5
|
* All conditional logic uses FEEL (Friendly Enough Expression Language).
|
|
6
|
+
*
|
|
7
|
+
* FieldDefinition is a discriminated union on the required `type` property,
|
|
8
|
+
* grouped by shared capabilities:
|
|
9
|
+
* - AdornableFieldDefinition: text-like and numeric inputs with prefix/suffix
|
|
10
|
+
* - SelectionFieldDefinition: select/multiselect with options
|
|
11
|
+
* - SimpleFieldDefinition: boolean, date, datetime (no type-specific props)
|
|
12
|
+
* - ArrayFieldDefinition: array with itemFields, minItems, maxItems
|
|
13
|
+
* - ObjectFieldDefinition: nested object grouping
|
|
14
|
+
* - DisplayFieldDefinition: presentation content and computed output (no data)
|
|
15
|
+
* - ComputedFieldDefinition: computed field reference in fields map
|
|
6
16
|
*/
|
|
7
17
|
/**
|
|
8
18
|
* FEEL expression - a string that will be evaluated at runtime.
|
|
@@ -79,7 +89,7 @@ export interface JSONSchemaEnum extends JSONSchemaBase {
|
|
|
79
89
|
/**
|
|
80
90
|
* Field type enumeration - maps to UI component types
|
|
81
91
|
*/
|
|
82
|
-
export type FieldType = "text" | "password" | "number" | "integer" | "boolean" | "select" | "multiselect" | "date" | "datetime" | "email" | "url" | "textarea" | "array" | "object" | "computed";
|
|
92
|
+
export type FieldType = "text" | "password" | "number" | "integer" | "boolean" | "select" | "multiselect" | "date" | "datetime" | "email" | "url" | "textarea" | "array" | "object" | "computed" | "display";
|
|
83
93
|
/**
|
|
84
94
|
* Validation rule with FEEL expression
|
|
85
95
|
*/
|
|
@@ -102,34 +112,137 @@ export interface SelectOption {
|
|
|
102
112
|
visibleWhen?: FEELExpression;
|
|
103
113
|
}
|
|
104
114
|
/**
|
|
105
|
-
*
|
|
115
|
+
* Base properties shared by all field types.
|
|
116
|
+
*
|
|
117
|
+
* Note: Display fields technically inherit all base properties including
|
|
118
|
+
* conditional logic (enabledWhen, requiredWhen, etc.), but these properties
|
|
119
|
+
* are semantically meaningless on display fields and should not be set.
|
|
120
|
+
* Runtime validation (Zod layer) enforces this constraint.
|
|
106
121
|
*/
|
|
107
|
-
export interface
|
|
108
|
-
/**
|
|
122
|
+
export interface FieldDefinitionBase {
|
|
123
|
+
/** Field type - REQUIRED, used as discriminant for the union */
|
|
124
|
+
type: FieldType;
|
|
125
|
+
/** Display label */
|
|
109
126
|
label?: string;
|
|
110
127
|
/** Help text or description */
|
|
111
128
|
description?: string;
|
|
112
129
|
/** Placeholder text for input fields */
|
|
113
130
|
placeholder?: string;
|
|
114
|
-
/** Field type override (inferred from schema if not provided) */
|
|
115
|
-
type?: FieldType;
|
|
116
131
|
/** When to show this field. If omitted, always visible. */
|
|
117
132
|
visibleWhen?: FEELExpression;
|
|
118
133
|
/** When this field is required. If omitted, uses schema required. */
|
|
119
134
|
requiredWhen?: FEELExpression;
|
|
120
135
|
/** When this field is editable. If omitted, always enabled. */
|
|
121
136
|
enabledWhen?: FEELExpression;
|
|
137
|
+
/** When this field is read-only (visible, not editable, value still submitted). */
|
|
138
|
+
readonlyWhen?: FEELExpression;
|
|
122
139
|
/** Custom validation rules using FEEL expressions */
|
|
123
140
|
validations?: ValidationRule[];
|
|
124
|
-
/**
|
|
141
|
+
/** Presentation variant hint (e.g., "slider", "radio", "nps", "metric") */
|
|
142
|
+
variant?: string;
|
|
143
|
+
/** Variant-specific configuration */
|
|
144
|
+
variantConfig?: Record<string, unknown>;
|
|
145
|
+
}
|
|
146
|
+
/**
|
|
147
|
+
* Text-like and numeric input fields that support prefix/suffix adorners.
|
|
148
|
+
*
|
|
149
|
+
* Adorners are cross-variant: a "$" prefix applies to input, stepper,
|
|
150
|
+
* and slider variants alike. That's why they're top-level properties
|
|
151
|
+
* rather than inside variantConfig.
|
|
152
|
+
*/
|
|
153
|
+
export interface AdornableFieldDefinition extends FieldDefinitionBase {
|
|
154
|
+
type: "text" | "email" | "url" | "password" | "textarea" | "number" | "integer";
|
|
155
|
+
/** Text/symbol displayed before input (e.g., "$", "https://") */
|
|
156
|
+
prefix?: string;
|
|
157
|
+
/** Text/symbol displayed after input (e.g., "USD", "kg", "%") */
|
|
158
|
+
suffix?: string;
|
|
159
|
+
}
|
|
160
|
+
/**
|
|
161
|
+
* Selection fields that have options.
|
|
162
|
+
*/
|
|
163
|
+
export interface SelectionFieldDefinition extends FieldDefinitionBase {
|
|
164
|
+
type: "select" | "multiselect";
|
|
165
|
+
/** Available options for selection */
|
|
166
|
+
options?: SelectOption[];
|
|
167
|
+
}
|
|
168
|
+
/**
|
|
169
|
+
* Simple fields with no type-specific properties beyond the base.
|
|
170
|
+
*/
|
|
171
|
+
export interface SimpleFieldDefinition extends FieldDefinitionBase {
|
|
172
|
+
type: "boolean" | "date" | "datetime";
|
|
173
|
+
}
|
|
174
|
+
/**
|
|
175
|
+
* Array fields with item field definitions and count constraints.
|
|
176
|
+
*/
|
|
177
|
+
export interface ArrayFieldDefinition extends FieldDefinitionBase {
|
|
178
|
+
type: "array";
|
|
179
|
+
/** Field definitions for each array item. Use `item.fieldName` in FEEL. */
|
|
125
180
|
itemFields?: Record<string, FieldDefinition>;
|
|
126
181
|
/** Minimum number of items (overrides schema) */
|
|
127
182
|
minItems?: number;
|
|
128
183
|
/** Maximum number of items (overrides schema) */
|
|
129
184
|
maxItems?: number;
|
|
130
|
-
/** For select fields: available options */
|
|
131
|
-
options?: SelectOption[];
|
|
132
185
|
}
|
|
186
|
+
/**
|
|
187
|
+
* Object fields (nested grouping).
|
|
188
|
+
*/
|
|
189
|
+
export interface ObjectFieldDefinition extends FieldDefinitionBase {
|
|
190
|
+
type: "object";
|
|
191
|
+
}
|
|
192
|
+
/**
|
|
193
|
+
* Display-only fields for presentation content and computed output.
|
|
194
|
+
* Collect no data - excluded from JSON Schema, validation, and submission.
|
|
195
|
+
*
|
|
196
|
+
* Although display fields inherit all base properties, conditional logic
|
|
197
|
+
* properties (readonlyWhen, requiredWhen, enabledWhen, validations, placeholder)
|
|
198
|
+
* are semantically meaningless on display fields. Only visibleWhen is meaningful
|
|
199
|
+
* (to conditionally show/hide display content). The Zod validation layer
|
|
200
|
+
* enforces this constraint at runtime.
|
|
201
|
+
*/
|
|
202
|
+
export interface DisplayFieldDefinition extends FieldDefinitionBase {
|
|
203
|
+
type: "display";
|
|
204
|
+
/** Static content (plain text or markdown). For text, heading, alert, callout. */
|
|
205
|
+
content?: string;
|
|
206
|
+
/** Data source for dynamic display (e.g., "computed.totalPrice"). For metric, alert, summary. */
|
|
207
|
+
source?: string;
|
|
208
|
+
/** Display format (e.g., "currency", "percent", "decimal(2)", or template "{value} Nm") */
|
|
209
|
+
format?: string;
|
|
210
|
+
}
|
|
211
|
+
/**
|
|
212
|
+
* Computed fields (read-only calculated values).
|
|
213
|
+
* Note: Computed field definitions live in Forma.computed, not Forma.fields.
|
|
214
|
+
* This type exists for completeness if computed fields appear in the fields map.
|
|
215
|
+
*/
|
|
216
|
+
export interface ComputedFieldDefinition extends FieldDefinitionBase {
|
|
217
|
+
type: "computed";
|
|
218
|
+
}
|
|
219
|
+
/**
|
|
220
|
+
* Field definition - discriminated union on `type`.
|
|
221
|
+
*
|
|
222
|
+
* Use type narrowing to access type-specific properties:
|
|
223
|
+
*
|
|
224
|
+
* @example
|
|
225
|
+
* if (field.type === "number") {
|
|
226
|
+
* field.prefix; // string | undefined
|
|
227
|
+
* }
|
|
228
|
+
* if (field.type === "display") {
|
|
229
|
+
* field.content; // string | undefined
|
|
230
|
+
* }
|
|
231
|
+
* if (field.type === "select") {
|
|
232
|
+
* field.options; // SelectOption[] | undefined
|
|
233
|
+
* }
|
|
234
|
+
*/
|
|
235
|
+
export type FieldDefinition = AdornableFieldDefinition | SelectionFieldDefinition | SimpleFieldDefinition | ArrayFieldDefinition | ObjectFieldDefinition | DisplayFieldDefinition | ComputedFieldDefinition;
|
|
236
|
+
/** Check if field supports prefix/suffix adorners */
|
|
237
|
+
export declare function isAdornableField(field: FieldDefinition): field is AdornableFieldDefinition;
|
|
238
|
+
/** Check if field is a display-only field (no data) */
|
|
239
|
+
export declare function isDisplayField(field: FieldDefinition): field is DisplayFieldDefinition;
|
|
240
|
+
/** Check if field is a selection field (has options) */
|
|
241
|
+
export declare function isSelectionField(field: FieldDefinition): field is SelectionFieldDefinition;
|
|
242
|
+
/** Check if field is an array field */
|
|
243
|
+
export declare function isArrayField(field: FieldDefinition): field is ArrayFieldDefinition;
|
|
244
|
+
/** Check if field collects data (not display) */
|
|
245
|
+
export declare function isDataField(field: FieldDefinition): boolean;
|
|
133
246
|
/**
|
|
134
247
|
* Computed field definition - derived values from form data
|
|
135
248
|
*/
|
|
@@ -241,6 +354,12 @@ export type RequiredFieldsResult = RequiredResult;
|
|
|
241
354
|
export interface EnabledResult {
|
|
242
355
|
[fieldPath: string]: boolean;
|
|
243
356
|
}
|
|
357
|
+
/**
|
|
358
|
+
* Readonly fields result - map of field path to readonly state
|
|
359
|
+
*/
|
|
360
|
+
export interface ReadonlyResult {
|
|
361
|
+
[fieldPath: string]: boolean;
|
|
362
|
+
}
|
|
244
363
|
/**
|
|
245
364
|
* Field validation error
|
|
246
365
|
*/
|
package/dist/types.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
package/src/engine/enabled.ts
CHANGED
|
@@ -11,6 +11,7 @@ import type {
|
|
|
11
11
|
FieldDefinition,
|
|
12
12
|
EvaluationContext,
|
|
13
13
|
EnabledResult,
|
|
14
|
+
ArrayFieldDefinition,
|
|
14
15
|
} from "../types.js";
|
|
15
16
|
import { calculate } from "./calculate.js";
|
|
16
17
|
|
|
@@ -69,24 +70,10 @@ export function getEnabled(
|
|
|
69
70
|
|
|
70
71
|
// Also check array item fields
|
|
71
72
|
for (const [fieldPath, fieldDef] of Object.entries(spec.fields)) {
|
|
72
|
-
if (fieldDef.itemFields) {
|
|
73
|
+
if (fieldDef.type === "array" && fieldDef.itemFields) {
|
|
73
74
|
const arrayData = data[fieldPath];
|
|
74
75
|
if (Array.isArray(arrayData)) {
|
|
75
|
-
|
|
76
|
-
const item = arrayData[i] as Record<string, unknown>;
|
|
77
|
-
const itemContext: EvaluationContext = {
|
|
78
|
-
data,
|
|
79
|
-
computed,
|
|
80
|
-
referenceData: spec.referenceData,
|
|
81
|
-
item,
|
|
82
|
-
itemIndex: i,
|
|
83
|
-
};
|
|
84
|
-
|
|
85
|
-
for (const [itemFieldName, itemFieldDef] of Object.entries(fieldDef.itemFields)) {
|
|
86
|
-
const itemFieldPath = `${fieldPath}[${i}].${itemFieldName}`;
|
|
87
|
-
result[itemFieldPath] = isFieldEnabled(itemFieldDef, itemContext);
|
|
88
|
-
}
|
|
89
|
-
}
|
|
76
|
+
evaluateArrayItemEnabled(fieldPath, fieldDef, arrayData, data, computed, spec, result);
|
|
90
77
|
}
|
|
91
78
|
}
|
|
92
79
|
}
|
|
@@ -114,6 +101,37 @@ function isFieldEnabled(
|
|
|
114
101
|
return true;
|
|
115
102
|
}
|
|
116
103
|
|
|
104
|
+
/**
|
|
105
|
+
* Evaluate enabled state for array item fields
|
|
106
|
+
*/
|
|
107
|
+
function evaluateArrayItemEnabled(
|
|
108
|
+
arrayPath: string,
|
|
109
|
+
fieldDef: ArrayFieldDefinition,
|
|
110
|
+
arrayData: unknown[],
|
|
111
|
+
data: Record<string, unknown>,
|
|
112
|
+
computed: Record<string, unknown>,
|
|
113
|
+
spec: Forma,
|
|
114
|
+
result: EnabledResult
|
|
115
|
+
): void {
|
|
116
|
+
if (!fieldDef.itemFields) return;
|
|
117
|
+
|
|
118
|
+
for (let i = 0; i < arrayData.length; i++) {
|
|
119
|
+
const item = arrayData[i] as Record<string, unknown>;
|
|
120
|
+
const itemContext: EvaluationContext = {
|
|
121
|
+
data,
|
|
122
|
+
computed,
|
|
123
|
+
referenceData: spec.referenceData,
|
|
124
|
+
item,
|
|
125
|
+
itemIndex: i,
|
|
126
|
+
};
|
|
127
|
+
|
|
128
|
+
for (const [itemFieldName, itemFieldDef] of Object.entries(fieldDef.itemFields)) {
|
|
129
|
+
const itemFieldPath = `${arrayPath}[${i}].${itemFieldName}`;
|
|
130
|
+
result[itemFieldPath] = isFieldEnabled(itemFieldDef, itemContext);
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
|
|
117
135
|
/**
|
|
118
136
|
* Check if a single field is currently enabled
|
|
119
137
|
*
|
package/src/engine/index.ts
CHANGED
|
@@ -57,6 +57,16 @@ export type {
|
|
|
57
57
|
EnabledOptions,
|
|
58
58
|
} from "./enabled.js";
|
|
59
59
|
|
|
60
|
+
// Readonly
|
|
61
|
+
export {
|
|
62
|
+
getReadonly,
|
|
63
|
+
isReadonly,
|
|
64
|
+
} from "./readonly.js";
|
|
65
|
+
|
|
66
|
+
export type {
|
|
67
|
+
ReadonlyOptions,
|
|
68
|
+
} from "./readonly.js";
|
|
69
|
+
|
|
60
70
|
// Validate
|
|
61
71
|
export {
|
|
62
72
|
validate,
|
|
@@ -0,0 +1,169 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Readonly Fields Engine
|
|
3
|
+
*
|
|
4
|
+
* Determines which fields are currently read-only based on
|
|
5
|
+
* conditional readonlyWhen expressions.
|
|
6
|
+
*
|
|
7
|
+
* Readonly vs disabled:
|
|
8
|
+
* - readonlyWhen: field is visible with normal appearance, not editable, value IS submitted
|
|
9
|
+
* - enabledWhen: field is greyed out/dimmed, not interactive, value may be excluded
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
import { evaluateBoolean } from "../feel/index.js";
|
|
13
|
+
import type {
|
|
14
|
+
Forma,
|
|
15
|
+
FieldDefinition,
|
|
16
|
+
ArrayFieldDefinition,
|
|
17
|
+
EvaluationContext,
|
|
18
|
+
ReadonlyResult,
|
|
19
|
+
} from "../types.js";
|
|
20
|
+
import { calculate } from "./calculate.js";
|
|
21
|
+
|
|
22
|
+
// ============================================================================
|
|
23
|
+
// Types
|
|
24
|
+
// ============================================================================
|
|
25
|
+
|
|
26
|
+
export interface ReadonlyOptions {
|
|
27
|
+
/** Pre-calculated computed values */
|
|
28
|
+
computed?: Record<string, unknown>;
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
// ============================================================================
|
|
32
|
+
// Main Function
|
|
33
|
+
// ============================================================================
|
|
34
|
+
|
|
35
|
+
/**
|
|
36
|
+
* Determine which fields are currently read-only
|
|
37
|
+
*
|
|
38
|
+
* Returns a map of field paths to boolean readonly states.
|
|
39
|
+
* Fields without readonlyWhen expressions are never readonly.
|
|
40
|
+
*
|
|
41
|
+
* @param data - Current form data
|
|
42
|
+
* @param spec - Form specification
|
|
43
|
+
* @param options - Optional pre-calculated computed values
|
|
44
|
+
* @returns Map of field paths to readonly states
|
|
45
|
+
*
|
|
46
|
+
* @example
|
|
47
|
+
* const readonly = getReadonly(
|
|
48
|
+
* { status: "submitted" },
|
|
49
|
+
* forma
|
|
50
|
+
* );
|
|
51
|
+
* // => { status: false, policyNumber: true, ... }
|
|
52
|
+
*/
|
|
53
|
+
export function getReadonly(
|
|
54
|
+
data: Record<string, unknown>,
|
|
55
|
+
spec: Forma,
|
|
56
|
+
options: ReadonlyOptions = {}
|
|
57
|
+
): ReadonlyResult {
|
|
58
|
+
const computed = options.computed ?? calculate(data, spec);
|
|
59
|
+
const context: EvaluationContext = {
|
|
60
|
+
data,
|
|
61
|
+
computed,
|
|
62
|
+
referenceData: spec.referenceData,
|
|
63
|
+
};
|
|
64
|
+
|
|
65
|
+
const result: ReadonlyResult = {};
|
|
66
|
+
|
|
67
|
+
// Evaluate each field's readonly status
|
|
68
|
+
for (const fieldPath of spec.fieldOrder) {
|
|
69
|
+
const fieldDef = spec.fields[fieldPath];
|
|
70
|
+
if (fieldDef) {
|
|
71
|
+
result[fieldPath] = isFieldReadonly(fieldDef, context);
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
// Also check array item fields
|
|
76
|
+
for (const [fieldPath, fieldDef] of Object.entries(spec.fields)) {
|
|
77
|
+
if (fieldDef.type === "array" && fieldDef.itemFields) {
|
|
78
|
+
const arrayData = data[fieldPath];
|
|
79
|
+
if (Array.isArray(arrayData)) {
|
|
80
|
+
evaluateArrayItemReadonly(fieldPath, fieldDef, arrayData, data, computed, spec, result);
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
return result;
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
// ============================================================================
|
|
89
|
+
// Field Readonly Check
|
|
90
|
+
// ============================================================================
|
|
91
|
+
|
|
92
|
+
/**
|
|
93
|
+
* Check if a field is readonly based on its definition
|
|
94
|
+
*/
|
|
95
|
+
function isFieldReadonly(
|
|
96
|
+
fieldDef: FieldDefinition,
|
|
97
|
+
context: EvaluationContext
|
|
98
|
+
): boolean {
|
|
99
|
+
// If field has readonlyWhen, evaluate it
|
|
100
|
+
if (fieldDef.readonlyWhen) {
|
|
101
|
+
return evaluateBoolean(fieldDef.readonlyWhen, context);
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
// No condition = never readonly
|
|
105
|
+
return false;
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
/**
|
|
109
|
+
* Evaluate readonly state for array item fields
|
|
110
|
+
*/
|
|
111
|
+
function evaluateArrayItemReadonly(
|
|
112
|
+
arrayPath: string,
|
|
113
|
+
fieldDef: ArrayFieldDefinition,
|
|
114
|
+
arrayData: unknown[],
|
|
115
|
+
data: Record<string, unknown>,
|
|
116
|
+
computed: Record<string, unknown>,
|
|
117
|
+
spec: Forma,
|
|
118
|
+
result: ReadonlyResult
|
|
119
|
+
): void {
|
|
120
|
+
if (!fieldDef.itemFields) return;
|
|
121
|
+
|
|
122
|
+
for (let i = 0; i < arrayData.length; i++) {
|
|
123
|
+
const item = arrayData[i] as Record<string, unknown>;
|
|
124
|
+
const itemContext: EvaluationContext = {
|
|
125
|
+
data,
|
|
126
|
+
computed,
|
|
127
|
+
referenceData: spec.referenceData,
|
|
128
|
+
item,
|
|
129
|
+
itemIndex: i,
|
|
130
|
+
};
|
|
131
|
+
|
|
132
|
+
for (const [itemFieldName, itemFieldDef] of Object.entries(fieldDef.itemFields)) {
|
|
133
|
+
const itemFieldPath = `${arrayPath}[${i}].${itemFieldName}`;
|
|
134
|
+
result[itemFieldPath] = isFieldReadonly(itemFieldDef, itemContext);
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
/**
|
|
140
|
+
* Check if a single field is currently readonly
|
|
141
|
+
*
|
|
142
|
+
* @param fieldPath - Path to the field
|
|
143
|
+
* @param data - Current form data
|
|
144
|
+
* @param spec - Form specification
|
|
145
|
+
* @returns True if the field is readonly
|
|
146
|
+
*/
|
|
147
|
+
export function isReadonly(
|
|
148
|
+
fieldPath: string,
|
|
149
|
+
data: Record<string, unknown>,
|
|
150
|
+
spec: Forma
|
|
151
|
+
): boolean {
|
|
152
|
+
const fieldDef = spec.fields[fieldPath];
|
|
153
|
+
if (!fieldDef) {
|
|
154
|
+
return false; // Unknown fields are not readonly by default
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
if (!fieldDef.readonlyWhen) {
|
|
158
|
+
return false; // No condition = never readonly
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
const computed = calculate(data, spec);
|
|
162
|
+
const context: EvaluationContext = {
|
|
163
|
+
data,
|
|
164
|
+
computed,
|
|
165
|
+
referenceData: spec.referenceData,
|
|
166
|
+
};
|
|
167
|
+
|
|
168
|
+
return evaluateBoolean(fieldDef.readonlyWhen, context);
|
|
169
|
+
}
|
package/src/engine/required.ts
CHANGED
|
@@ -69,7 +69,7 @@ export function getRequired(
|
|
|
69
69
|
|
|
70
70
|
// Also check array item fields
|
|
71
71
|
for (const [fieldPath, fieldDef] of Object.entries(spec.fields)) {
|
|
72
|
-
if (fieldDef.itemFields) {
|
|
72
|
+
if (fieldDef.type === "array" && fieldDef.itemFields) {
|
|
73
73
|
const arrayData = data[fieldPath];
|
|
74
74
|
if (Array.isArray(arrayData)) {
|
|
75
75
|
for (let i = 0; i < arrayData.length; i++) {
|
package/src/engine/validate.ts
CHANGED
|
@@ -12,6 +12,7 @@ import { evaluateBoolean } from "../feel/index.js";
|
|
|
12
12
|
import type {
|
|
13
13
|
Forma,
|
|
14
14
|
FieldDefinition,
|
|
15
|
+
ArrayFieldDefinition,
|
|
15
16
|
ValidationRule,
|
|
16
17
|
EvaluationContext,
|
|
17
18
|
ValidationResult,
|
|
@@ -95,6 +96,11 @@ export function validate(
|
|
|
95
96
|
continue;
|
|
96
97
|
}
|
|
97
98
|
|
|
99
|
+
// Skip display fields - they collect no data and need no validation
|
|
100
|
+
if (fieldDef.type === "display") {
|
|
101
|
+
continue;
|
|
102
|
+
}
|
|
103
|
+
|
|
98
104
|
// Get schema property for type validation
|
|
99
105
|
const schemaProperty = spec.schema.properties[fieldPath];
|
|
100
106
|
|
|
@@ -173,7 +179,7 @@ function validateField(
|
|
|
173
179
|
}
|
|
174
180
|
|
|
175
181
|
// 4. Array validation
|
|
176
|
-
if (Array.isArray(value)) {
|
|
182
|
+
if (Array.isArray(value) && fieldDef.type === "array") {
|
|
177
183
|
const arrayErrors = validateArray(
|
|
178
184
|
path,
|
|
179
185
|
value,
|
|
@@ -212,7 +218,7 @@ function validateType(
|
|
|
212
218
|
path: string,
|
|
213
219
|
value: unknown,
|
|
214
220
|
schema: JSONSchemaProperty,
|
|
215
|
-
fieldDef:
|
|
221
|
+
fieldDef: { label?: string }
|
|
216
222
|
): FieldError | null {
|
|
217
223
|
const label = fieldDef.label ?? path;
|
|
218
224
|
|
|
@@ -514,7 +520,7 @@ function validateCustomRules(
|
|
|
514
520
|
function validateArray(
|
|
515
521
|
path: string,
|
|
516
522
|
value: unknown[],
|
|
517
|
-
fieldDef:
|
|
523
|
+
fieldDef: ArrayFieldDefinition,
|
|
518
524
|
schemaProperty: JSONSchemaProperty | undefined,
|
|
519
525
|
spec: Forma,
|
|
520
526
|
data: Record<string, unknown>,
|
package/src/engine/visibility.ts
CHANGED
|
@@ -9,10 +9,12 @@ import { evaluateBoolean } from "../feel/index.js";
|
|
|
9
9
|
import type {
|
|
10
10
|
Forma,
|
|
11
11
|
FieldDefinition,
|
|
12
|
+
ArrayFieldDefinition,
|
|
12
13
|
EvaluationContext,
|
|
13
14
|
VisibilityResult,
|
|
14
15
|
SelectOption,
|
|
15
16
|
} from "../types.js";
|
|
17
|
+
import { isArrayField, isSelectionField } from "../types.js";
|
|
16
18
|
import { calculate } from "./calculate.js";
|
|
17
19
|
|
|
18
20
|
// ============================================================================
|
|
@@ -62,7 +64,7 @@ function filterOptionsByContext(
|
|
|
62
64
|
*/
|
|
63
65
|
function processArrayItemOptions(
|
|
64
66
|
arrayPath: string,
|
|
65
|
-
fieldDef:
|
|
67
|
+
fieldDef: ArrayFieldDefinition,
|
|
66
68
|
arrayData: readonly unknown[],
|
|
67
69
|
baseContext: EvaluationContext,
|
|
68
70
|
result: Record<string, SelectOption[]>
|
|
@@ -78,7 +80,7 @@ function processArrayItemOptions(
|
|
|
78
80
|
};
|
|
79
81
|
|
|
80
82
|
for (const [itemFieldName, itemFieldDef] of Object.entries(fieldDef.itemFields)) {
|
|
81
|
-
if (itemFieldDef.options && itemFieldDef.options.length > 0) {
|
|
83
|
+
if (isSelectionField(itemFieldDef) && itemFieldDef.options && itemFieldDef.options.length > 0) {
|
|
82
84
|
const itemFieldPath = `${arrayPath}[${i}].${itemFieldName}`;
|
|
83
85
|
result[itemFieldPath] = filterOptionsByContext(itemFieldDef.options, itemContext);
|
|
84
86
|
}
|
|
@@ -153,7 +155,7 @@ function evaluateFieldVisibility(
|
|
|
153
155
|
return;
|
|
154
156
|
}
|
|
155
157
|
|
|
156
|
-
if (fieldDef.itemFields) {
|
|
158
|
+
if (isArrayField(fieldDef) && fieldDef.itemFields) {
|
|
157
159
|
const arrayData = data[path];
|
|
158
160
|
if (Array.isArray(arrayData)) {
|
|
159
161
|
evaluateArrayItemVisibility(path, fieldDef, arrayData, context, result);
|
|
@@ -166,7 +168,7 @@ function evaluateFieldVisibility(
|
|
|
166
168
|
*/
|
|
167
169
|
function evaluateArrayItemVisibility(
|
|
168
170
|
arrayPath: string,
|
|
169
|
-
fieldDef:
|
|
171
|
+
fieldDef: ArrayFieldDefinition,
|
|
170
172
|
arrayData: unknown[],
|
|
171
173
|
baseContext: EvaluationContext,
|
|
172
174
|
result: VisibilityResult
|
|
@@ -308,12 +310,12 @@ export function getOptionsVisibility(
|
|
|
308
310
|
if (!fieldDef) continue;
|
|
309
311
|
|
|
310
312
|
// Top-level fields with options
|
|
311
|
-
if (fieldDef.options && fieldDef.options.length > 0) {
|
|
313
|
+
if (isSelectionField(fieldDef) && fieldDef.options && fieldDef.options.length > 0) {
|
|
312
314
|
result[fieldPath] = filterOptionsByContext(fieldDef.options, baseContext);
|
|
313
315
|
}
|
|
314
316
|
|
|
315
317
|
// Array item fields with options
|
|
316
|
-
if (fieldDef.itemFields) {
|
|
318
|
+
if (isArrayField(fieldDef) && fieldDef.itemFields) {
|
|
317
319
|
const arrayData = data[fieldPath];
|
|
318
320
|
if (Array.isArray(arrayData)) {
|
|
319
321
|
processArrayItemOptions(fieldPath, fieldDef, arrayData, baseContext, result);
|
package/src/index.ts
CHANGED
|
@@ -20,11 +20,19 @@ export type {
|
|
|
20
20
|
JSONSchemaArray,
|
|
21
21
|
JSONSchemaObject,
|
|
22
22
|
JSONSchemaEnum,
|
|
23
|
-
// Field types
|
|
23
|
+
// Field types - base and groups
|
|
24
24
|
FieldType,
|
|
25
|
+
FieldDefinitionBase,
|
|
26
|
+
AdornableFieldDefinition,
|
|
27
|
+
SelectionFieldDefinition,
|
|
28
|
+
SimpleFieldDefinition,
|
|
29
|
+
ArrayFieldDefinition,
|
|
30
|
+
ObjectFieldDefinition,
|
|
31
|
+
DisplayFieldDefinition,
|
|
32
|
+
ComputedFieldDefinition,
|
|
33
|
+
FieldDefinition,
|
|
25
34
|
ValidationRule,
|
|
26
35
|
SelectOption,
|
|
27
|
-
FieldDefinition,
|
|
28
36
|
ComputedField,
|
|
29
37
|
PageDefinition,
|
|
30
38
|
FormMeta,
|
|
@@ -36,12 +44,22 @@ export type {
|
|
|
36
44
|
RequiredResult,
|
|
37
45
|
RequiredFieldsResult,
|
|
38
46
|
EnabledResult,
|
|
47
|
+
ReadonlyResult,
|
|
39
48
|
FieldError,
|
|
40
49
|
ValidationResult,
|
|
41
50
|
CalculationError,
|
|
42
51
|
CalculationResult,
|
|
43
52
|
} from "./types.js";
|
|
44
53
|
|
|
54
|
+
// Type guards (runtime exports)
|
|
55
|
+
export {
|
|
56
|
+
isAdornableField,
|
|
57
|
+
isDisplayField,
|
|
58
|
+
isSelectionField,
|
|
59
|
+
isArrayField,
|
|
60
|
+
isDataField,
|
|
61
|
+
} from "./types.js";
|
|
62
|
+
|
|
45
63
|
// FEEL expression evaluation
|
|
46
64
|
export * from "./feel/index.js";
|
|
47
65
|
|