diff --git a/resources/js/Pages/forms.jsx b/resources/js/Pages/forms.jsx
index f5eed89f..d03880b9 100644
--- a/resources/js/Pages/forms.jsx
+++ b/resources/js/Pages/forms.jsx
@@ -5,6 +5,7 @@ export const meta = {
title: 'Forms',
links: [
{ url: '#form-component', name: 'Form component' },
+ { url: '#precognition', name: 'Precognition' },
{ url: '#form-helper', name: 'Form helper' },
{ url: '#server-side-responses', name: 'Server-side responses' },
{ url: '#server-side-validation', name: 'Server-side validation' },
@@ -1096,6 +1097,588 @@ export default function () {
methods, so reactive state like isDirty and errors should be accessed via{' '}
slot props instead.
+ The {' component includes built-in support for precognition, enabling real-time form
+ validation without duplicating your server-side validation rules on the client.
+
+ Before using precognition, ensure your server-side framework is configured to handle precognitive requests. + Laravel users can follow the Precognition documentation for + setup instructions. Other frameworks can implement precognition support by following the{' '} + precognition protocol. +
+
+ Once your server is configured, call validate() with a field name to trigger validation for that
+ field. The invalid() helper checks if a field has validation errors, while validating{' '}
+ indicates when a request is in progress.
+
{{ errors.name }}
+ + + +{{ errors.email }}
+ +Validating...
+ + + + `, + }, + { + name: 'React', + language: 'jsx', + code: dedent` + + `, + }, + { + name: 'Svelte 4', + language: 'html', + code: dedent` + + `, + }, + { + name: 'Svelte 5', + language: 'html', + code: dedent` + + `, + }, + ]} + /> +
+ You can also use the valid() helper to check if a field has passed validation. This is useful for
+ showing success states or visual indicators.
+
Valid email address
+{{ errors.email }}
+ + `, + }, + { + name: 'React', + language: 'jsx', + code: dedent` + + `, + }, + { + name: 'Svelte', + language: 'html', + code: dedent` + + `, + }, + ]} + /> +
+ Validation requests are automatically debounced. The first validation request for a field fires immediately to
+ provide instant feedback. Subsequent changes are then debounced, waiting 1500ms before sending another request.
+ You can configure the debounce timeout using the{' '}
+ validateTimeout
+ validateTimeout
+ validate-timeout
+
+ You can validate multiple fields at once by passing an array to validate(). This is useful when you
+ want to validate an entire section of a form at once.
+
{{ errors.name }}
+ + +{{ errors.email }}
+ + + + `, + }, + { + name: 'React', + language: 'jsx', + code: dedent` + + `, + }, + { + name: 'Svelte', + language: 'html', + code: dedent` + + `, + }, + ]} + /> +
+ The touch() method marks fields as "touched" without triggering validation. This is useful for
+ tracking which fields the user has interacted with. You can then validate all touched fields at once by calling{' '}
+ validate() without arguments.
+
Name has been touched
+ + `, + }, + { + name: 'React', + language: 'jsx', + code: dedent` + + `, + }, + { + name: 'Svelte', + language: 'html', + code: dedent` + + `, + }, + ]} + /> +
+ The touched() helper can also be called with a specific field name to check if that field has been
+ touched. In addition to resetting one or more values with the reset() method, it also clears the
+ touched state for those fields.
+
+ By default, files are not included in precognitive validation requests to avoid unnecessary uploads. If you need
+ to validate file fields, set{' '}
+ validateFiles={'{true}'}
+ validateFiles={'{true}'}
+ :validate-files="true"
+
{{ errors.avatar }}
+ + `, + }, + { + name: 'React', + language: 'jsx', + code: dedent` + + `, + }, + { + name: 'Svelte', + language: 'html', + code: dedent` + + `, + }, + ]} + /> +
+ The validate() method accepts several callbacks that let you respond to validation results. Use{' '}
+ onSuccess when validation passes, onError when it fails, and onFinish{' '}
+ when validation completes regardless of the result.
+
+ The onBefore callback allows you to intercept validation requests before they're sent to the
+ server. Return false to prevent validation from occurring. This is useful for implementing
+ conditional validation logic or rate limiting.
+
+ For handling unexpected server errors during validation (non-422 responses), use the onException{' '}
+ callback. This allows you to gracefully handle network errors, server errors, or other unexpected issues.
+
+ Instead of passing fields as an array, you can pass an options object with only to specify which
+ fields to validate. This also allows you to include other options like headers and{' '}
+ errorBag.
+
+ Laravel validation errors are typically arrays of messages per field. For example, a field might have multiple
+ validation rules that each produce an error. Normally, Laravel's Inertia middleware simplifies these to single
+ strings (the first error only) before sending them to the client. However, during precognitive validation, the{' '}
+ 422 response returns early (without the Inertia middleware handling it) so the{' '}
+ {' component handles this simplification on the frontend instead.
+
+ By default, validation errors are automatically simplified to strings. If you need access to all error messages
+ for a field, you can disable this behavior by setting{' '}
+ simpleValidationErrors={'{false}'}
+ simpleValidationErrors={'{false}'}
+ :simple-validation-errors="false"
+
+ Validation requests are automatically canceled when a new validation is triggered for the same form, preventing
+ race conditions and ensuring only the most recent validation is processed. You can also manually cancel pending
+ validation requests using the cancelValidation() method.
+
In addition to the {' component, Inertia also provides a useForm helper for
diff --git a/resources/js/Pages/the-protocol.jsx b/resources/js/Pages/the-protocol.jsx
index 7db6967e..b1fe21ff 100644
--- a/resources/js/Pages/the-protocol.jsx
+++ b/resources/js/Pages/the-protocol.jsx
@@ -182,6 +182,18 @@ export default function () {
appended or prepended when using Infinite scroll.
+
+ The following headers are used for precognitive form validation. +
+true to indicate this is a precognitive validation request.
+
The following headers should be sent by your server-side adapter in Inertia responses. If you're using an
@@ -519,6 +531,19 @@ export default function () {
X-Inertia-Location header and triggers a window.location redirect client-side.
+
+ The following status codes are used for precognitive form validation. +
+