Skip to content

feat(core): add a pluggable Form Validator next to Ajv - #2644

Open
gigibiffi84 wants to merge 1 commit into
eclipsesource:masterfrom
gigibiffi84:feat/form-validator-bridge
Open

gigibiffi84 wants to merge 1 commit into
eclipsesource:masterfrom
gigibiffi84:feat/form-validator-bridge

Conversation

@gigibiffi84

Copy link
Copy Markdown

Part of #1498. Follows the agreement to land validator decoupling incrementally and non-breaking in 3.x, shaped after the FormValidator / ValidationIssue types on feat/presentation-model (#2571).

What changed

@jsonforms/core gains a pluggable validation seam next to Ajv:

  • InitActionOptions.validator: a FormValidatorFactory (schema) => FormValidator, or a FormValidator already bound to the schema. Precedence: validator, then ajv, then the default Ajv instance.
  • FormValidator has validate(data): ValidationIssue[] (synchronous in 3.x) and an optional matches(schema, data) for rule conditions (wired up in a follow-up PR).
  • ValidationIssue mirrors 4.x (path, key, message, severity) plus optional params and parentSchema.
  • The reducer creates the Form Validator through the factory whenever the schema changes and caches it in state.formValidator. state.validator keeps holding the compiled Ajv function whenever Ajv validates.
  • issuesToErrors converts issues from custom validators to the Ajv error shape the rest of core and the renderers read: missing key becomes custom, a required issue addressed to the missing property is split into parent path plus params.missingProperty, non-error severities are dropped, and a missing parentSchema is resolved from the form schema by path. Ajv-backed validators bypass the conversion, so Ajv users get identical errors.
  • Built-in adapter: createAjvValidator(ajv?); compiledAjvValidator(validateFn) wraps Ajv standalone code for CSP setups that keep Ajv but cannot allow unsafe-eval.
  • New selector getValidator(state).

For adopters

Nothing changes without the new option: all existing core tests pass unchanged. One small fix: setValidationMode('NoValidation') now also drops the cached validator, as init and updateCore already did; previously a later data update could reintroduce errors in that mode.

Tests

  • test/util/formValidator.test.ts: lossless Ajv round trip, every normalization rule, resolveParentSchema over properties, items, additionalProperties and $ref, both adapters, guards.
  • test/reducers/core.test.ts: a fake validator receives every compile and validation, Ajv is never asked to compile when a validator is given, bound validators, updateCore recompiling only on schema change, options without a validator key keeping the current validator, explicit undefined switching back to Ajv, update, setSchema, NoValidation, setAjv precedence, issue normalization, getValidator.
  • 466 core tests green; @jsonforms/react, @jsonforms/vue and @jsonforms/angular build against the new types; typedoc succeeds.

Follow-ups (separate PRs)

Rule conditions through matches / the factory; the validator prop in the React, Angular and Vue bindings with an example; a Structural Matcher fallback for rules.

🤖 Generated with Claude Code

Adds the validation seam from issue eclipsesource#1498 as a non-breaking addition:
the `validator` init/updateCore option takes a FormValidatorFactory
`(schema) => FormValidator` or a FormValidator already bound to the
schema. The types mirror the FormValidator / ValidationIssue of the 4.x
presentation-model branch, restricted to synchronous results.

- The core reducer creates the Form Validator through the factory
  whenever the schema changes and caches it in `state.formValidator`;
  `state.validator` keeps holding the compiled Ajv function when Ajv
  validates, so existing consumers are unaffected.
- Issues from custom validators are converted to the Ajv error shape
  the rest of core and the renderers read (`issuesToErrors`): missing
  `key` becomes `custom`, `required` issues addressed to the missing
  property are split into parent path plus `params.missingProperty`,
  non-error severities are dropped and a missing `parentSchema` is
  resolved from the form schema.
- `createAjvValidator(ajv?)` is the built-in adapter;
  `compiledAjvValidator(validateFn)` wraps Ajv standalone code for CSP
  setups without unsafe-eval.
- `getValidator(state)` exposes the bound Form Validator.
- Switching to NoValidation via setValidationMode now also drops the
  cached validator, as init and updateCore already did.

Precedence: `validator` wins, otherwise `ajv`, otherwise the default
Ajv instance. Existing users notice nothing.

Part of eclipsesource#1498

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
@netlify

netlify Bot commented Oct 7, 2026 •

Copy link
Copy Markdown

✅ Deploy Preview for jsonforms-examples ready!

Name Link
🔨 Latest commit bb5d28c
🔍 Latest deploy log https://app.netlify.com/projects/jsonforms-examples/deploys/6ac67efa1a2a910008dd9c76
😎 Deploy Preview https://deploy-preview-2644--jsonforms-examples.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.

To edit notification comments on pull requests, go to your Netlify project configuration.

@CLAassistant

CLAassistant commented Oct 7, 2026 •

Copy link
Copy Markdown

CLA assistant check
All committers have signed the CLA.

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants