### Install Valibot from JSR for Node, Deno, and Bun Source: https://valibot.dev/guides/installation.md Installs Valibot from the JSR registry using various package managers, compatible with Node.js, Deno, and Bun. This method allows for importing Valibot schemas into your project. ```bash deno add jsr:@valibot/valibot # deno npx jsr add @valibot/valibot # npm yarn dlx jsr add @valibot/valibot # yarn pnpm dlx jsr add @valibot/valibot # pnpm bunx jsr add @valibot/valibot # bun ``` -------------------------------- ### Install Valibot via npm, Yarn, pnpm, or Bun Source: https://valibot.dev/guides/installation.md Installs the Valibot library for Node.js and Bun environments using common package managers. This allows for subsequent import into JavaScript or TypeScript files. ```bash npm install valibot # npm yarn add valibot # yarn pnpm add valibot # pnpm bun add valibot # bun ``` -------------------------------- ### Install Valibot Agent Skill for AI Agents Source: https://valibot.dev/guides/installation.md Installs the Valibot agent skill using npx, enabling AI agents to generate Valibot schemas correctly. This command requires Node.js and npm to be installed. ```bash npx skills add open-circle/agent-skills --skill valibot ``` -------------------------------- ### Import Valibot Schemas in JavaScript/TypeScript Source: https://valibot.dev/guides/installation.md Demonstrates how to import Valibot schemas into JavaScript or TypeScript files using either individual imports or a wildcard import. Assumes Valibot has been installed. ```typescript // With individual imports import { … } from 'valibot'; // With a wildcard import import * as v from 'valibot'; ``` -------------------------------- ### Implement validation pipelines Source: https://valibot.dev/guides/quick-start.md Shows how to use the pipe method to chain multiple validation and transformation actions, such as checking for email formats and specific domain constraints. ```typescript import * as v from 'valibot'; const EmailSchema = v.pipe(v.string(), v.email(), v.endsWith('@example.com')); ``` -------------------------------- ### Define basic Valibot schemas Source: https://valibot.dev/guides/quick-start.md Demonstrates how to define a Valibot schema for an object, mirroring a standard TypeScript type definition to ensure runtime type safety. ```typescript import * as v from 'valibot'; // TypeScript type LoginData = { email: string; password: string; }; // Valibot const LoginSchema = v.object({ email: v.string(), password: v.string(), }); ``` -------------------------------- ### Infer types and parse data Source: https://valibot.dev/guides/quick-start.md Demonstrates how to use v.InferOutput to extract TypeScript types from a schema and v.parse to validate unknown data at runtime. ```typescript import * as v from 'valibot'; const LoginSchema = v.object({…}); type LoginData = v.InferOutput; function getLoginData(data: unknown): LoginData { return v.parse(LoginSchema, data); } ``` -------------------------------- ### Configure custom error messages Source: https://valibot.dev/guides/quick-start.md Illustrates how to provide custom error messages to schema actions, allowing for localized or user-friendly feedback when validation fails. ```typescript import * as v from 'valibot'; const LoginSchema = v.object({ email: v.pipe( v.string('Your email must be a string.'), v.nonEmpty('Please enter your email.'), v.email('The email address is badly formatted.') ), password: v.pipe( v.string('Your password must be a string.'), v.nonEmpty('Please enter your password.'), v.minLength(8, 'Your password must have 8 characters or more.') ), }); ``` -------------------------------- ### Direct Deno Import from deno.land/x Source: https://valibot.dev/guides/installation.md Allows direct referencing of the Valibot library in Deno projects via its deno.land/x URL. This method bypasses package managers for Deno users. ```typescript // With individual imports import { … } from 'https://deno.land/x/valibot/mod.ts'; // With a wildcard import import * as v from 'https://deno.land/x/valibot/mod.ts'; ``` -------------------------------- ### Import Valibot Schemas from JSR Source: https://valibot.dev/guides/installation.md Shows how to import Valibot schemas from JSR using individual or wildcard imports in JavaScript or TypeScript. This method is suitable for Node, Deno, and Bun. ```typescript // With individual imports import { … } from '@valibot/valibot'; // With a wildcard import import * as v from '@valibot/valibot'; ``` -------------------------------- ### Direct JSR Import in Deno Source: https://valibot.dev/guides/installation.md Enables direct importing of Valibot using JSR specifiers within Deno projects. This method simplifies dependency management for Deno users. ```typescript // With individual imports import { … } from 'jsr:@valibot/valibot'; // With a wildcard import import * as v from 'jsr:@valibot/valibot'; ``` -------------------------------- ### Custom Transformation with Valibot Pipe Source: https://valibot.dev/guides/pipelines.md This example shows how to implement a custom transformation using Valibot's `pipe` and `transform` functions. The provided function modifies the input data based on a condition, returning `null` for numbers less than 10 in this case. ```typescript import * as v from 'valibot'; const NumberSchema = v.pipe( v.number(), v.transform((input) => (input < 10 ? null : input)) ); ``` -------------------------------- ### Validate Login Schema with Valibot and Zod Source: https://valibot.dev/guides/comparison.md A comparison of implementing a login schema validation using Valibot, standard Zod, and Zod Mini. These examples demonstrate the syntax differences and the resulting impact on bundle size. ```typescript import * as v from 'valibot'; // 1.37 kB const LoginSchema = v.object({ email: v.pipe( v.string(), v.nonEmpty('Please enter your email.'), v.email('The email address is badly formatted.') ), password: v.pipe( v.string(), v.nonEmpty('Please enter your password.'), v.minLength(8, 'Your password must have 8 characters or more.') ), }); ``` ```typescript import * as z from 'zod'; // 17.7 kB with esbuild const LoginSchema = z.object({ email: z.string() .min(1, 'Please enter your email.') .email('The email address is badly formatted.'), password: z.string() .min(1, 'Please enter your password.') .min(8, 'Your password must have 8 characters or more.'), }); ``` ```typescript import * as z from 'zod/mini'; // 6.88 kB with esbuild const LoginSchema = z.object({ email: z.check( z.string(), z.minLength(1, 'Please enter your email.'), z.email('The email address is badly formatted.') ), password: z.check( z.string(), z.minLength(1, 'Please enter your password.'), z.minLength(8, 'Your password must have 8 characters or more.') ), }); ``` -------------------------------- ### Validate and Transform Strings to Numbers Source: https://valibot.dev/guides/migrate-from-zod.md Provides an example of using Valibot's pipe to validate string formatting before transforming it into a number, ensuring higher type safety. ```typescript const NumberSchema = v.pipe(v.string(), v.decimal(), v.transform(Number)); ``` -------------------------------- ### Apply Minimum Value Validation to Different Data Types in TypeScript Source: https://valibot.dev/guides/pipelines.md This example shows how to use the `v.minValue()` validation action within a pipeline for various data types including string, number, bigint, and date. It ensures the input meets a specified minimum threshold. ```typescript import * as v from 'valibot'; const StringSchema = v.pipe(v.string(), v.minValue('foo')); const NumberSchema = v.pipe(v.number(), v.minValue(1234)); const BigintSchema = v.pipe(v.bigint(), v.minValue(1234n)); const DateSchema = v.pipe(v.date(), v.minValue(new Date())); ``` -------------------------------- ### Add Title and Description Metadata with Valibot Pipe Source: https://valibot.dev/guides/pipelines.md This snippet illustrates how to add metadata like 'title' and 'description' to a Valibot schema using the `pipe` function. It defines a username schema with a regular expression and associated metadata for clarity and potential AI usage. ```typescript const UsernameSchema = v.pipe( v.string(), v.regex(/^[a-z0-9_-]{4,16}$/iu), v.title('Username'), v.description( 'A username must be between 4 and 16 characters long and can only contain letters, numbers, underscores and hyphens.' ) ); ``` -------------------------------- ### Create Email Validation Pipeline in TypeScript Source: https://valibot.dev/guides/pipelines.md This snippet demonstrates creating a pipeline schema to validate and transform a string into a specific email format. It uses `v.string()`, `v.trim()`, `v.email()`, and `v.endsWith()` to ensure the string is trimmed, a valid email, and ends with '@example.com'. ```typescript import * as v from 'valibot'; const EmailSchema = v.pipe( v.string(), v.trim(), v.email(), v.endsWith('@example.com') ); ``` -------------------------------- ### Configure TypeScript Strict Mode for Valibot Source: https://valibot.dev/guides/installation.md Enables strict type checking in TypeScript projects, ensuring accurate type calculations for Valibot schemas. This is a recommended setting for Valibot development. ```json { "compilerOptions": { "strict": true, "//": "..." } } ``` -------------------------------- ### Enforce Minimum Value with Valibot Pipe Source: https://valibot.dev/guides/pipelines.md This code snippet demonstrates how to use Valibot's `pipe` and `toMinValue` transformation to ensure a number input is at least a specified minimum value. It takes a number schema and applies the minimum value constraint. ```typescript import * as v from 'valibot'; const NumberSchema = v.pipe(v.number(), v.toMinValue(10)); ``` -------------------------------- ### Pipeline Validation for Tuple Schema with Valibot Source: https://valibot.dev/guides/arrays.md Applies a pipeline of validations to a tuple schema with a rest element using Valibot. This example validates a tuple starting with a string, followed by any number of strings, ensuring it has a maximum length of 5, includes 'foo', and excludes 'bar'. It requires the 'valibot' library and several validation functions. ```typescript import * as v from 'valibot'; const TupleSchema = v.pipe( v.tupleWithRest([v.string()], v.string()), v.maxLength(5), v.includes('foo'), v.excludes('bar') ); ``` -------------------------------- ### Define and validate data schemas with Valibot Source: https://valibot.dev/guides/introduction.md Demonstrates how to create a schema using Valibot's object and pipe functions, infer the TypeScript type, and perform runtime validation using the parse method. ```typescript import * as v from 'valibot'; // Create login schema with email and password const LoginSchema = v.object({ email: v.pipe(v.string(), v.email()), password: v.pipe(v.string(), v.minLength(8)), }); // Infer output TypeScript type of login schema as // { email: string; password: string } type LoginData = v.InferOutput; // Throws error for email and password const output1 = v.parse(LoginSchema, { email: '', password: '' }); // Returns data as { email: string; password: string } const output2 = v.parse(LoginSchema, { email: 'jane@example.com', password: '12345678', }); ``` -------------------------------- ### Restructuring Schema Pipelines Source: https://valibot.dev/guides/migrate-to-v0.31.0 Demonstrates the syntax change from passing an array of actions to schema functions to using the new v.pipe() method for schema extension. ```typescript // Change this const Schema = v.string([v.email()]); // To this const Schema = v.pipe(v.string(), v.email()); ``` -------------------------------- ### Implement Pipe for Transformations and Branding Source: https://valibot.dev/guides/migrate-to-v0.31.0 Illustrates how to use the pipe method to replace legacy brand and transform methods for improved readability. ```typescript // Change this const BrandedSchema = v.brand(v.string(), 'foo'); const TransformedSchema = v.transform(v.string(), (input) => input.length); // To this const BrandedSchema = v.pipe(v.string(), v.brand('foo')); const TransformedSchema = v.pipe( v.string(), v.transform((input) => input.length) ); ``` -------------------------------- ### Adapt Parse and SafeParse Methods for Valibot Source: https://valibot.dev/guides/migrate-from-zod.md Shows how to correctly use the `parse` and `safeParse` functions in Valibot, contrasting with Zod's method chaining. In Valibot, the schema is passed as the first argument. ```typescript // Change this const value = z.string().parse('foo'); // To this const value = v.parse(v.string(), 'foo'); ``` -------------------------------- ### Import and Use Schema and Types Separately (Valibot) Source: https://valibot.dev/guides/naming-convention.md Demonstrates importing and using a Valibot schema and its input/output types separately, following Convention 2. This approach enhances clarity and flexibility by explicitly naming each component, suitable for complex scenarios or when input/output types diverge. ```typescript import * as v from 'valibot'; import { ImageInput, ImageOutput, ImageSchema } from './types'; export function createImage(input: ImageInput): ImageOutput { return v.parse(ImageSchema, input); } ``` -------------------------------- ### Migrate Object and Tuple Schemas Source: https://valibot.dev/guides/migrate-to-v0.31.0 Demonstrates the migration from generic object/tuple schemas with rest arguments to explicit schemas like objectWithRest, looseObject, and strictObject. ```typescript // Change this const ObjectSchema = v.object({ key: v.string() }, v.null_()); const TupleSchema = v.tuple([v.string()], v.null_()); // To this const ObjectSchema = v.objectWithRest({ key: v.string() }, v.null_()); const TupleSchema = v.tupleWithRest([v.string()], v.null_()); ``` ```typescript // Change this const LooseObjectSchema = v.object({ key: v.string() }, v.unknown()); const LooseTupleSchema = v.tuple([v.string()], v.unknown()); const StrictObjectSchema = v.object({ key: v.string() }, v.never()); const StrictTupleSchema = v.tuple([v.string()], v.never()); // To this const LooseObjectSchema = v.looseObject({ key: v.string() }); const LooseTupleSchema = v.looseTuple([v.string()]); const StrictObjectSchema = v.strictObject({ key: v.string() }); const StrictTupleSchema = v.strictTuple([v.string()]); ``` -------------------------------- ### Valibot Type Guards for Schema Inspection Source: https://valibot.dev/guides/integrate-valibot.md Demonstrates how to use `isOfKind` and `isOfType` to narrow down the TypeScript type of a Valibot schema object at runtime. These helpers improve type inference compared to direct equality checks on `kind` and `type` properties. ```typescript import * as v from 'valibot'; // Narrows to BaseSchema by kind if (v.isOfKind('schema', item)) { item; // BaseSchema<...> } // Narrows to StringSchema by type if (v.isOfType('string', schema)) { schema; // StringSchema<...> } ``` -------------------------------- ### Implement Custom Validation with `v.check` in TypeScript Source: https://valibot.dev/guides/pipelines.md This snippet illustrates how to create a custom validation rule using `v.check` within a Valibot pipeline. It applies a user-defined `isValidUsername` function to validate the input string, providing a custom error message if the validation fails. ```typescript import * as v from 'valibot'; import { isValidUsername } from '~/utils'; const UsernameSchema = v.pipe( v.string(), v.check(isValidUsername, 'This username is invalid.') ); ``` -------------------------------- ### Create dynamic schema factories with Valibot Source: https://valibot.dev/guides/extend-valibot.md Demonstrates how to compose existing schemas into a reusable generic factory using GenericSchema. This approach allows for wrapping user-provided schemas in envelopes like pagination wrappers while maintaining full TypeScript type inference. ```typescript import * as v from 'valibot'; function paginatedList(item: TItem) { return v.object({ items: v.array(item), total: v.number(), page: v.number(), }); } const UserList = paginatedList(v.object({ id: v.number(), name: v.string() })); type UserList = v.InferOutput; ``` -------------------------------- ### Tuple Schema with Specific Rest Element using Valibot Source: https://valibot.dev/guides/arrays.md Creates a tuple schema with a specific schema for any remaining elements using Valibot's `tupleWithRest`. This example defines the first two elements as a string and a number, respectively, and all subsequent elements must be null. It requires the 'valibot' library. ```typescript import * as v from 'valibot'; const TupleSchema = v.tupleWithRest([v.string(), v.number()], v.null()); ``` -------------------------------- ### Create immutable schema modifications using fallback pattern Source: https://valibot.dev/guides/internal-architecture.md This function demonstrates how to create a new schema object by spreading an existing one. It highlights the necessity of re-binding the '~standard' getter and using a closure to correctly invoke the original '~run' logic. ```typescript function fallback(schema, fallbackValue) { return { // Copy all properties from the original schema ...schema, // Add the new fallback property as metadata fallback: fallbackValue, // Re-bind '~standard' so `this` refers to the new object get '~standard'() { return _getStandardProps(this); }, // Override '~run' to return the fallback value on failure '~run'(dataset, config) { const outputDataset = schema['~run'](dataset, config); return outputDataset.issues ? { typed: true, value: fallbackValue } : outputDataset; }, }; } ``` -------------------------------- ### Pipeline Validation for Array Schema with Valibot Source: https://valibot.dev/guides/arrays.md Applies a pipeline of validations to an array schema using Valibot. This example validates that the array contains only strings, has a minimum length of 1, a maximum length of 5, includes the string 'foo', and excludes the string 'bar'. It requires the 'valibot' library and several validation functions. ```typescript import * as v from 'valibot'; const ArraySchema = v.pipe( v.array(v.string()), v.minLength(1), v.maxLength(5), v.includes('foo'), v.excludes('bar') ); ``` -------------------------------- ### Configure Error Messages Source: https://valibot.dev/guides/migrate-from-zod.md Shows how to replace Zod's object-based error configuration with Valibot's simplified string-based error messages within a pipe. ```typescript // Change this const StringSchema = z .string({ invalid_type_error: 'Not a string' }) .min(5, { message: 'Too short' }); // To this const StringSchema = v.pipe( v.string('Not a string'), v.minLength(5, 'Too short') ); ``` -------------------------------- ### Replace Coerce with Pipe and Transform Source: https://valibot.dev/guides/migrate-to-v0.31.0 Demonstrates replacing the removed coerce method with a pipe and transform combination to safely handle data type conversions. ```typescript // Change this const DateSchema = v.coerce(v.date(), (input) => new Date(input)); // To this const DateSchema = v.pipe( v.union([v.string(), v.number()]), v.transform((input) => new Date(input)) ); ``` -------------------------------- ### Run Zod to Valibot Codemod Locally Source: https://valibot.dev/guides/migrate-from-zod.md Commands to run the Zod to Valibot codemod locally. The `--dry` flag previews changes without modifying files, while the default command applies the changes directly. ```bash npx @valibot/zod-to-valibot src/**/* --dry npx @valibot/zod-to-valibot src/**/* ``` -------------------------------- ### Parse Data with a Schema using Valibot's parse Method Source: https://valibot.dev/guides/mental-model.md Shows how to use the `parse` method from Valibot to validate and transform unknown data against a predefined schema. The schema is always passed as the first argument to the method. ```typescript import * as v from 'valibot'; const BookSchema = v.object({ title: v.string(), numberOfPages: v.number(), publication: v.date(), tags: v.array(v.string()), }); function createBook(data: unknown) { return v.parse(BookSchema, data); } ``` -------------------------------- ### Create Email Validation and Transformation Schema with Valibot Source: https://valibot.dev/guides/mental-model.md Illustrates the use of the `pipe` method in Valibot to chain multiple actions, such as `trim` and `email`, to a base `string` schema. This allows for sequential validation and transformation of data. ```typescript import * as v from 'valibot'; const EmailSchema = v.pipe(v.string(), v.trim(), v.email()); ``` -------------------------------- ### Define Optional, Exact Optional, Undefinedable, Nullable, and Nullish Schemas in TypeScript Source: https://valibot.dev/guides/optionals.md Demonstrates how to define various optional schemas using Valibot functions. These functions allow schemas to accept `undefined` or `null` in addition to the base type, with `exactOptional` having specific behavior for object entries. ```typescript import * as v from 'valibot'; const OptionalStringSchema = v.optional(v.string()); // string | undefined const ExactOptionalStringSchema = v.exactOptional(v.string()); // string const UndefinedableStringSchema = v.undefinedable(v.string()); // string | undefined const NullableStringSchema = v.nullable(v.string()); // string | null const NullishStringSchema = v.nullish(v.string()); // string | null | undefined ``` -------------------------------- ### Implement custom schemas from scratch in Valibot Source: https://valibot.dev/guides/extend-valibot.md Shows how to define a custom schema by implementing a BaseIssue interface, a BaseSchema interface, and a factory function. It utilizes internal utilities _getStandardProps and _addIssue to integrate with Valibot's validation pipeline. ```typescript import * as v from 'valibot'; interface StringIssue extends v.BaseIssue { kind: 'schema'; type: 'string'; expected: 'string'; } interface StringSchema | undefined> extends v.BaseSchema { type: 'string'; reference: typeof string; expects: 'string'; message: TMessage; } function string | undefined>( message?: TMessage ): StringSchema { return { kind: 'schema', type: 'string', reference: string, expects: 'string', async: false, message, get '~standard'() { return v._getStandardProps(this); }, '~run'(dataset, config) { if (typeof dataset.value === 'string') { // @ts-expect-error dataset.typed = true; } else { v._addIssue(this, 'type', dataset, config); } // @ts-expect-error return dataset as v.OutputDataset; }, }; } ``` -------------------------------- ### Define Strict Object Schemas Source: https://valibot.dev/guides/migrate-from-zod.md Demonstrates how to transition from Zod's .strict() method to Valibot's dedicated strictObject schema function for preventing unknown object keys. ```typescript // Change this const ObjectSchema = z.object({ key: z.string() }).strict(); // To this const ObjectSchema = v.strictObject({ key: v.string() }); ``` -------------------------------- ### Implement pipe function for schema composition Source: https://valibot.dev/guides/internal-architecture.md The pipe function creates a new schema by chaining multiple actions. It overrides the '~run' method to iterate through the pipe items, respecting metadata, early abort configurations, and existing issue states. ```typescript function pipe(...pipe) { return { ...pipe[0], pipe, get '~standard'() { return _getStandardProps(this); }, '~run'(dataset, config) { for (const item of pipe) { if (item.kind !== 'metadata') { if ( dataset.issues && (item.kind === 'schema' || item.kind === 'transformation') ) { dataset.typed = false; break; } if ( !dataset.issues || (!config.abortEarly && !config.abortPipeEarly) ) { dataset = item['~run'](dataset, config); } } } return dataset; }, }; } ``` -------------------------------- ### Import and Use Schema and Type Together (Valibot) Source: https://valibot.dev/guides/naming-convention.md Demonstrates how to import and utilize a Valibot schema and its corresponding type when they share the same name, as per Convention 1. The type is used for variable annotations, and the schema is used for parsing data. ```typescript import * as v from 'valibot'; import { PublicUser } from './types'; // Use `PublicUser` as a type const publicUsers: PublicUser[] = []; publicUsers.push( // Use `PublicUser` as a schema v.parse(PublicUser, { name: 'Jane Doe', email: 'jane@example.com', avatar: null, bio: 'Lorem ipsum ...', }) ); ``` -------------------------------- ### Define Primitive Schemas with Valibot Source: https://valibot.dev/guides/schemas.md Demonstrates how to create validation schemas for primitive JavaScript types such as string, number, boolean, and bigint using the Valibot library. ```typescript import * as v from 'valibot'; const BigintSchema = v.bigint(); // bigint const BooleanSchema = v.boolean(); // boolean const NullSchema = v.null(); // null const NumberSchema = v.number(); // number const StringSchema = v.string(); // string const SymbolSchema = v.symbol(); // symbol const UndefinedSchema = v.undefined(); // undefined ``` -------------------------------- ### Infer output types with InferOutput Source: https://valibot.dev/guides/infer-types.md Shows how to extract the resulting type after schema transformation or parsing using InferOutput. This reflects the final data structure after applying pipes, transforms, or default values. ```typescript import * as v from 'valibot'; import { hashPassword } from '~/utils'; const LoginSchema = v.pipe( v.object({ email: v.string(), password: v.pipe(v.string(), v.transform(hashPassword)), }), v.transform((input) => { return { ...input, timestamp: new Date().toISOString(), }; }) ); type LoginOutput = v.InferOutput; // { email: string; password: string; timestamp: string } ``` -------------------------------- ### Automated Migration via CLI Source: https://valibot.dev/guides/migrate-to-v0.31.0 Commands to automatically upgrade Valibot schemas to v0.31.0 using Codemod or Grit tools. These commands should be executed in the project root directory. ```bash # Codemod npx codemod valibot/migrate-to-v0.31.0 # Grit npx @getgrit/cli apply github.com/open-circle/valibot#migrate_to_v0_31_0 ``` -------------------------------- ### Format Data for Picklist Validation Source: https://valibot.dev/guides/enums.md Demonstrates how to transform complex data structures using the map method to create a compatible array for the picklist schema function. ```typescript import * as v from 'valibot'; const countries = [ { name: 'Germany', code: 'DE' }, { name: 'France', code: 'FR' }, { name: 'United States', code: 'US' }, ] as const; const CountrySchema = v.picklist(countries.map((country) => country.code)); ``` -------------------------------- ### Restructure Validation with Pipelines in Valibot Source: https://valibot.dev/guides/migrate-from-zod.md Illustrates the difference in structuring chained validations between Zod and Valibot. Valibot uses pipelines, combining multiple validation or transformation steps into a single function. ```typescript // Change this const Schema = z.string().email().endsWith('@example.com'); // To this const Schema = v.pipe(v.string(), v.email(), v.endsWith('@example.com')); ``` -------------------------------- ### Valibot Schemas with Dynamic Default Values (TypeScript) Source: https://valibot.dev/guides/optionals.md Demonstrates how to use a function to dynamically generate a default value for a Valibot schema. This is useful when the default value needs to be created at runtime, such as generating a new Date object. ```typescript import * as v from 'valibot'; const NullableDateSchema = v.nullable(v.date(), () => new Date()); ``` -------------------------------- ### Infer input types with InferInput Source: https://valibot.dev/guides/infer-types.md Demonstrates how to extract the expected input TypeScript type from a Valibot schema using the InferInput utility. This is useful for validating incoming data structures before processing. ```typescript import * as v from 'valibot'; const LoginSchema = v.object({ email: v.string(), password: v.string(), }); type LoginInput = v.InferInput; // { email: string; password: string } ``` -------------------------------- ### Define Asynchronous Schema with Valibot Source: https://valibot.dev/guides/async-validation.md Demonstrates how to create an asynchronous schema using objectAsync and pipeAsync. This pattern allows for mixing synchronous and asynchronous validations within a single schema definition. ```typescript import * as v from 'valibot'; import { isUsernameAvailable } from '~/api'; const ProfileSchema = v.objectAsync({ username: v.pipeAsync(v.string(), v.checkAsync(isUsernameAvailable)), avatar: v.pipe(v.string(), v.url()), description: v.pipe(v.string(), v.maxLength(1000)), }); ``` -------------------------------- ### Importing Valibot i18n translations Source: https://valibot.dev/guides/internationalization.md Demonstrates how to import official translations from the @valibot/i18n package. Imports can be scoped to specific languages, schema functions, or individual pipeline functions to optimize bundle size. ```typescript // Import every translation (not recommended) import '@valibot/i18n'; // Import every translation for a specific language import '@valibot/i18n/de'; // Import only the translation for schema functions import '@valibot/i18n/de/schema'; // Import only the translation for a specific pipeline function import '@valibot/i18n/de/minLength'; ``` -------------------------------- ### Coerce Primitive Types Source: https://valibot.dev/guides/migrate-from-zod.md Illustrates replacing Zod's coerce object with Valibot's pipe and transform pattern to safely convert input types. ```typescript // Change this const NumberSchema = z.coerce.number(); // To this const NumberSchema = v.pipe(v.unknown(), v.transform(Number)); ``` -------------------------------- ### Export Schema with Suffixes for Types (Valibot) Source: https://valibot.dev/guides/naming-convention.md This convention exports a Valibot schema with a 'Schema' suffix and its inferred input and output types with 'Input' and 'Output' suffixes, respectively. This provides more precise naming and flexibility, especially when input and output types differ. The 'Data' suffix can be used if input and output types are the same. ```typescript import * as v from 'valibot'; export const ImageSchema = v.object({ status: v.optional(v.picklist(['public', 'private']), 'private'), created: v.optional(v.date(), () => new Date()), title: v.pipe(v.string(), v.maxLength(100)), source: v.pipe(v.string(), v.url()), size: v.pipe(v.number(), v.minValue(0)), }); export type ImageInput = v.InferInput; export type ImageOutput = v.InferOutput; ``` -------------------------------- ### Valibot Schemas with Default Values (TypeScript) Source: https://valibot.dev/guides/optionals.md Shows how to define Valibot schemas that automatically provide a default value when the input is missing or `undefined`/`null`. This can change the input type from the output type. ```typescript import * as v from 'valibot'; const OptionalStringSchema = v.optional(v.string(), "I'm the default!"); type OptionalStringInput = v.InferInput; // string | undefined type OptionalStringOutput = v.InferOutput; // string ``` -------------------------------- ### Merge Object Schemas Source: https://valibot.dev/guides/migrate-to-v0.31.0 Shows the manual approach to merging object schemas by spreading their entries, replacing the removed merge function. ```typescript const ObjectSchema1 = v.object({ foo: v.string() }); const ObjectSchema2 = v.object({ bar: v.number() }); // Change this const MergedObject = v.merge([ObjectSchema1, ObjectSchema2]); // To this const MergedObject = v.object({ ...ObjectSchema1.entries, ...ObjectSchema2.entries, }); ``` -------------------------------- ### Optional Keys in Valibot Object Schemas (TypeScript) Source: https://valibot.dev/guides/optionals.md Illustrates how to define an object schema in Valibot where a specific key is optional. This translates to a TypeScript type with an optional property (using '?'). ```typescript import * as v from 'valibot'; const OptionalKeySchema = v.object({ key: v.optional(v.string()) }); // { key?: string | undefined } ``` -------------------------------- ### Update Imports from Zod to Valibot Source: https://valibot.dev/guides/migrate-from-zod.md Demonstrates how to change import statements and schema definitions when migrating from Zod to Valibot. This involves updating the import source and replacing 'z.' with 'v.'. ```typescript // Change this import { z } from 'zod'; const Schema = z.object({ key: z.string() }); // To this import * as v from 'valibot'; const Schema = v.object({ key: v.string() }); ``` -------------------------------- ### Validate Data with Standard Schema v1 Source: https://valibot.dev/guides/integrate-valibot.md Demonstrates how to validate data against a schema using the Standard Schema v1 interface. It uses the vendor-neutral 'validate' function exposed by the '~standard' property. This method relies on Valibot's global configuration and does not support custom configurations like 'abortEarly' or 'lang'. ```typescript import type { StandardSchemaV1 } from '@standard-schema/spec'; async function validateData(schema: StandardSchemaV1, data: unknown) { const result = await schema['~standard'].validate(data); if (result.issues) { // Validation failed — result.issues is a readonly array of StandardIssue console.log(result.issues); } else { // Validation succeeded — result.value is the typed output console.log(result.value); } } ``` -------------------------------- ### Parse and Return Issues with safeParse Source: https://valibot.dev/guides/parse-data.md The `safeParse` method validates data against a schema and returns an object with a `success` boolean. If `success` is true, the validated data is in `.output`. If false, validation issues are in `.issues`. ```typescript import * as v from 'valibot'; const EmailSchema = v.pipe(v.string(), v.email()); const result = v.safeParse(EmailSchema, 'jane@example.com'); if (result.success) { const email = result.output; } else { console.log(result.issues); } ``` -------------------------------- ### Implement Pipeline Validation for Object Entries in Valibot Source: https://valibot.dev/guides/objects.md Demonstrates pipeline validation for object entries using Valibot's `pipe`, `check`, and `forward`. The `check` action validates a condition based on object properties, and `forward` assigns any validation errors to a specific key, ensuring complex cross-property validation logic can be applied. ```typescript import * as v from 'valibot'; const CalculationSchema = v.pipe( v.object({ a: v.number(), b: v.number(), sum: v.number(), }), v.forward( v.check(({ a, b, sum }) => a + b === sum, 'The calculation is incorrect.'), ['sum'] ) ); ``` -------------------------------- ### Transform object schemas with utility methods Source: https://valibot.dev/guides/methods.md Valibot provides utility methods like partial, pick, and omit that mirror TypeScript's built-in utility types. These allow for dynamic modification of object schemas. ```typescript import * as v from 'valibot'; // TypeScript type Object1 = Partial<{ key1: string; key2: number }>; // Valibot const object1 = v.partial(v.object({ key1: v.string(), key2: v.number() })); // TypeScript type Object2 = Pick; // Valibot const object2 = v.pick(object1, ['key1']); ``` -------------------------------- ### Handle Union validation issues Source: https://valibot.dev/guides/unions.md Demonstrates the structure of validation issues returned by a union schema when input fails all provided schema checks. ```json [ { "kind": "schema", "type": "union", "input": null, "expected": "string | number", "received": "null", "message": "Invalid type: Expected string | number but received null", "issues": [ { "kind": "schema", "type": "string", "input": null, "expected": "string", "received": "null", "message": "Invalid type: Expected string but received null" }, { "kind": "schema", "type": "number", "input": null, "expected": "number", "received": "null", "message": "Invalid type: Expected number but received null" } ] } ] ```