# Class Validator Documentation by Sonicar.Tech > Class-validator documentation: decorator-based and manual validation for TypeScript and JavaScript classes, powered by validator.js. > Maintained by Sonicar Tech LLC (https://sonicar.tech) — a docs-as-code documentation agency for SaaS, B2B, Enterprise, FinTech, and AI companies. --- ## Home Source: https://class-validator.sonicar.tech/ # Class Validator Class-validator is a powerful validation library for TypeScript and JavaScript that allows you to use decorator and non-decorator based validation. It uses [validator.js](https://github.com/chriso/validator.js) internally to perform validation and works on both browser and node.js platforms. ## Key Features - Decorator and non-decorator based validation - Cross-platform compatibility (browser & node.js) - Works with TypeScript and JavaScript - Validates objects against classes - Validates arrays and nested objects - Custom validation decorators - Service container support - Rich set of built-in validators ## Quick Example ```typescript import { validate } from 'class-validator'; import { Length, Contains, IsInt, Min, Max, IsEmail } from 'class-validator'; export class Post { @Length(10, 20) title: string; @Contains('hello') text: string; @IsInt() @Min(0) @Max(10) rating: number; @IsEmail() email: string; } let post = new Post(); post.title = 'Hello'; // too short post.text = 'this is a great post about hell world'; // doesn't contain "hello" post.rating = 11; // too high post.email = 'google.com'; // not an email validate(post).then(errors => { if (errors.length > 0) { console.log('validation failed. errors: ', errors); } else { console.log('validation succeed'); } }); ``` Ready to get started? Head over to [Installation](installation.md). ## Contributing For information about how to contribute to this project, see [TypeStack's general contribution guide](https://github.com/typestack/.github/blob/master/CONTRIBUTING.md). --- ## Installation Source: https://class-validator.sonicar.tech/installation/ # Installation ## Requirements - npm version 6 or higher - Node.js ## Installing the Package ```sh npm install class-validator --save ``` !!! note It's important to use at least npm@6 when using class-validator. From npm@6 the dependency tree is flattened, which is required by class-validator to function properly. ## Basic Setup Import the necessary decorators: ```typescript import { validate } from 'class-validator'; ``` Enable decorators in your `tsconfig.json`: ```json { "compilerOptions": { "experimentalDecorators": true } } ``` You're now ready to start using class-validator in your project! Continue to [Basic Usage](usage.md). --- ## Basic Usage Source: https://class-validator.sonicar.tech/usage/ # Basic Usage ## Creating a Validated Class To start using class-validator, first create a class with validation decorators: ```typescript import { Length, IsEmail, Min } from 'class-validator'; export class User { @Length(4, 20) username: string; @IsEmail() email: string; @Min(18) age: number; } ``` ## Validating an Object Once you have a class with validation decorators, you can validate instances of this class: ```typescript import { validate } from 'class-validator'; let user = new User(); user.username = "Sh"; // too short user.email = "invalid-email"; // not an email user.age = 16; // under 18 validate(user).then(errors => { if (errors.length > 0) { console.log('Validation failed:', errors); } else { console.log('Validation successful'); } }); ``` ## Validation Options You can pass options to the `validate` function: ```typescript validate(user, { skipMissingProperties: true, // skip validation of missing properties whitelist: true, // strip non-decorated properties forbidNonWhitelisted: true // throw error if non-whitelisted properties exist }); ``` ## Synchronous Validation If you don't need async validation, you can use `validateSync`: ```typescript import { validateSync } from 'class-validator'; const errors = validateSync(user); if (errors.length > 0) { console.log('Validation failed:', errors); } else { console.log('Validation successful'); } ``` --- ## Validation Decorators Source: https://class-validator.sonicar.tech/decorators/ # Validation Decorators ## Common validation decorators | Decorator | Description | | --- | --- | | `@IsDefined(value: any)` | Checks if value is defined (`!== undefined`, `!== null`). This is the only decorator that ignores `skipMissingProperties` option. | | `@IsOptional()` | Checks if given value is empty (`=== null`, `=== undefined`) and if so, ignores all the validators on the property. | | `@Equals(comparison: any)` | Checks if value equals (`===`) comparison. | | `@NotEquals(comparison: any)` | Checks if value not equal (`!==`) comparison. | | `@IsEmpty()` | Checks if given value is empty (`=== ''`, `=== null`, `=== undefined`). | | `@IsNotEmpty()` | Checks if given value is not empty (`!== ''`, `!== null`, `!== undefined`). | | `@IsIn(values: any[])` | Checks if value is in an array of allowed values. | | `@IsNotIn(values: any[])` | Checks if value is not in an array of disallowed values. | ## Type validation decorators | Decorator | Description | | --- | --- | | `@IsBoolean()` | Checks if a value is a boolean. | | `@IsDate()` | Checks if the value is a date. | | `@IsString()` | Checks if the value is a string. | | `@IsNumber(options: IsNumberOptions)` | Checks if the value is a number. | | `@IsInt()` | Checks if the value is an integer number. | | `@IsArray()` | Checks if the value is an array. | | `@IsEnum(entity: object)` | Checks if the value is a valid enum. | See the full list of [validation decorators](validation-decorators.md) for more details. --- ## Validation Messages Source: https://class-validator.sonicar.tech/messages/ # Validation Messages You can specify validation messages in the decorator options and that message will be returned in the `ValidationError` returned by the `validate` method (in the case that validation for this field fails). ## Basic Usage ```typescript import { MinLength, MaxLength } from 'class-validator'; export class Post { @MinLength(10, { message: 'Title is too short', }) @MaxLength(50, { message: 'Title is too long', }) title: string; } ``` ## Message Variables There are few special tokens you can use in your messages: - `$value` - the value that is being validated - `$property` - name of the object's property being validated - `$target` - name of the object's class being validated - `$constraint1`, `$constraint2`, ... `$constraintN` - constraints defined by specific validation type Example: ```typescript import { MinLength, MaxLength } from 'class-validator'; export class Post { @MinLength(10, { message: 'Title is too short. Minimal length is $constraint1 characters, but actual is $value', }) @MaxLength(50, { message: 'Title is too long. Maximal length is $constraint1 characters, but actual is $value', }) title: string; } ``` ## Dynamic Messages You can also provide a function that returns a message. This allows you to create more granular messages: ```typescript import { MinLength, ValidationArguments } from 'class-validator'; export class Post { @MinLength(10, { message: (args: ValidationArguments) => { if (args.value.length === 1) { return 'Too short, minimum length is 1 character'; } else { return 'Too short, minimum length is ' + args.constraints[0] + ' characters'; } }, }) title: string; } ``` The message function accepts `ValidationArguments` which contains: - `value` - the value that is being validated - `constraints` - array of constraints defined by specific validation type - `targetName` - name of the object's class being validated - `object` - object that is being validated - `property` - name of the object's property being validated --- ## Validating Arrays Source: https://class-validator.sonicar.tech/arrays/ # Validating Arrays ## Basic Array Validation If your field is an array and you want to perform validation of each item in the array, you must specify a special `each: true` decorator option: ```typescript import { MaxLength } from 'class-validator'; export class Post { @MaxLength(20, { each: true, }) tags: string[]; } ``` This will validate each item in `post.tags` array. The same `each: true` option also works for `Set` and `Map` fields. ## Array-specific Decorators There are also several decorators specifically for array validation: | Decorator | Description | | --- | --- | | `@ArrayContains(values: any[])` | Checks if array contains all values from the given array of values. | | `@ArrayNotContains(values: any[])` | Checks if array does not contain any of the given values. | | `@ArrayNotEmpty()` | Checks if given array is not empty. | | `@ArrayMinSize(min: number)` | Checks if array's length is greater than or equal to the specified number. | | `@ArrayMaxSize(max: number)` | Checks if array's length is less or equal to the specified number. | | `@ArrayUnique()` | Checks if all array's values are unique. | Example: ```typescript import { ArrayMinSize, ArrayMaxSize, ArrayUnique } from 'class-validator'; export class Post { @ArrayMinSize(1) @ArrayMaxSize(10) @ArrayUnique() tags: string[]; } ``` --- ## Validating Nested Objects Source: https://class-validator.sonicar.tech/nested-objects/ # Validating Nested Objects ## Basic Nested Validation If your object contains nested objects and you want the validator to perform their validation too, then you need to use the `@ValidateNested()` decorator: ```typescript import { ValidateNested } from 'class-validator'; export class Post { @ValidateNested() user: User; } ``` ## Array of Nested Objects It also works with arrays of nested objects: ```typescript import { ValidateNested } from 'class-validator'; import { Type } from 'class-transformer'; export class Post { @ValidateNested({ each: true }) @Type(() => User) users: User[]; } ``` ## Deep Nested Objects You can validate deeply nested objects: ```typescript import { ValidateNested } from 'class-validator'; import { Type } from 'class-transformer'; export class Profile { @IsString() name: string; } export class User { @ValidateNested() @Type(() => Profile) profile: Profile; } export class Post { @ValidateNested() @Type(() => User) user: User; } ``` !!! note The nested object must be an instance of a class, otherwise `@ValidateNested` won't know what to validate against. See also [Validating Plain Objects](usage.md). --- ## Validating Promises Source: https://class-validator.sonicar.tech/promises/ # Validating Promises ## Basic Promise Validation If your object contains properties with `Promise`-returned values that should be validated, you need to use the `@ValidatePromise()` decorator: ```typescript import { ValidatePromise, Min } from 'class-validator'; export class Post { @Min(0) @ValidatePromise() userId: Promise; } ``` ## Combining with Nested Validation It works great with the `@ValidateNested` decorator: ```typescript import { ValidateNested, ValidatePromise } from 'class-validator'; export class Post { @ValidateNested() @ValidatePromise() user: Promise; } ``` ## Async Validation When validating promises, the validation itself becomes asynchronous: ```typescript import { validate } from 'class-validator'; let post = new Post(); post.userId = Promise.resolve(1); validate(post).then(errors => { // handle errors }); ``` --- ## Inheriting Validation Decorators Source: https://class-validator.sonicar.tech/inheritance/ # Inheriting Validation Decorators When you define a subclass that extends from another class, the subclass will automatically inherit the parent's decorators. If a property is redefined in the descendant class, decorators will be applied from both its own class and the base class. ## Example ```typescript import { validate } from 'class-validator'; class BaseContent { @IsEmail() email: string; @IsString() password: string; } class User extends BaseContent { @MinLength(10) @MaxLength(20) name: string; @Contains('hello') welcome: string; @MinLength(20) password: string; } let user = new User(); user.email = 'invalid email'; // inherited property user.password = 'too short'; // password will be validated against IsString and MinLength user.name = 'not valid'; user.welcome = 'helo'; validate(user).then(errors => { // handle errors }); // it will return errors for email, password, name and welcome properties ``` ## Inheritance Rules - All decorators from the base class are inherited - Decorators can be overridden in the child class - Multiple decorators are combined when a property is redefined - Inheritance works with multiple levels of inheritance --- ## Conditional Validation Source: https://class-validator.sonicar.tech/conditional/ # Conditional Validation The conditional validation decorator (`@ValidateIf`) can be used to ignore the validators on a property when the provided condition function returns false. The condition function takes the object being validated and must return a `boolean`. ## Basic Usage ```typescript import { ValidateIf, IsNotEmpty } from 'class-validator'; export class Post { otherProperty: string; @ValidateIf(o => o.otherProperty === 'value') @IsNotEmpty() example: string; } ``` In this example, the validation rules applied to `example` won't be run unless the object's `otherProperty` is `"value"`. ## Important Notes - When the condition is false, all validation decorators are ignored, including `@IsDefined` - The condition function takes the object being validated as a parameter - The condition function must return a boolean - Multiple `@ValidateIf` decorators can be used on the same property ## Advanced Example ```typescript import { ValidateIf, IsNotEmpty, IsString } from 'class-validator'; export class User { @IsString() type: string; @ValidateIf(o => o.type === 'admin') @IsNotEmpty() adminKey: string; @ValidateIf(o => o.type === 'user') @IsNotEmpty() userKey: string; } ``` --- ## Whitelisting Source: https://class-validator.sonicar.tech/whitelisting/ # Whitelisting ## Overview Even if your object is an instance of a validation class, it can contain additional properties that are not defined. If you don't want to have such properties on your object, you can use whitelisting. ## Basic Usage ```typescript import { validate } from 'class-validator'; // ... class definition validate(post, { whitelist: true }); ``` This will strip all properties that don't have any decorators. If no other decorator is suitable for your property, you can use the `@Allow` decorator: ```typescript import { validate, Allow, Min } from 'class-validator'; export class Post { @Allow() title: string; @Min(0) views: number; nonWhitelistedProperty: number; } let post = new Post(); post.title = 'Hello world!'; post.views = 420; post.nonWhitelistedProperty = 69; (post as any).anotherNonWhitelistedProperty = "something"; validate(post, { whitelist: true }).then(errors => { // post.nonWhitelistedProperty is not defined // (post as any).anotherNonWhitelistedProperty is not defined }); ``` ## Forbidding Non-whitelisted Properties If you would rather have an error thrown when any non-whitelisted properties are present: ```typescript import { validate } from 'class-validator'; validate(post, { whitelist: true, forbidNonWhitelisted: true }); ``` --- ## Passing Context to Decorators Source: https://class-validator.sonicar.tech/context/ # Passing Context to Decorators ## Overview It's possible to pass a custom object to decorators which will be accessible on the `ValidationError` instance of the property if validation failed. ## Example ```typescript import { validate } from 'class-validator'; class MyClass { @MinLength(32, { message: 'EIC code must be at least 32 characters', context: { errorCode: 1003, developerNote: 'The validated string must contain 32 or more characters.', }, }) eicCode: string; } const model = new MyClass(); validate(model).then(errors => { // errors[0].contexts['minLength'].errorCode === 1003 }); ``` ## Use Cases - Adding error codes for API responses - Including developer notes in validation errors - Providing additional metadata for error handling - Customizing error messages based on context --- ## Validation Groups Source: https://class-validator.sonicar.tech/groups/ # Validation Groups ## Overview In different situations you may want to use different validation schemas for the same object. In such cases you can use validation groups. !!! important Calling a validation with a group combination that would not result in a validation (e.g. a non-existent group name) will result in an unknown value error. When validating with groups, the provided group combination should match at least one decorator. ## Basic Usage ```typescript import { validate, Min, Length } from 'class-validator'; export class User { @Min(12, { groups: ['registration'] }) age: number; @Length(2, 20, { groups: ['registration', 'admin'] }) name: string; } let user = new User(); user.age = 10; user.name = 'Alex'; validate(user, { groups: ['registration'] }); // this will not pass validation validate(user, { groups: ['admin'] }); // this will pass validation validate(user, { groups: ['registration', 'admin'] }); // this will not pass validation validate(user, { groups: undefined // the default }); // this will not pass validation since all properties get validated regardless of their groups ``` ## Important Notes - The `always: true` flag in validation options means the validation must be applied regardless of groups - Multiple groups can be specified for a single decorator - If no groups are specified, the default group is used - Groups can be used to create different validation scenarios for the same object --- ## Custom Validation Source: https://class-validator.sonicar.tech/custom-validation/ # Custom Validation ## Custom Validation Classes ### Creating a Custom Validator ```typescript import { ValidatorConstraint, ValidatorConstraintInterface, ValidationArguments } from 'class-validator'; @ValidatorConstraint({ name: 'customText', async: false }) export class CustomTextLength implements ValidatorConstraintInterface { validate(text: string, args: ValidationArguments) { return text.length > 1 && text.length < 10; } defaultMessage(args: ValidationArguments) { return 'Text ($value) is too short or too long!'; } } ``` We marked our class with the `@ValidatorConstraint` decorator. You can also supply a validation constraint name — this name will be used as the "error type" in `ValidationError`. If you don't supply a constraint name, it will be auto-generated. Our class must implement the `ValidatorConstraintInterface` interface and its `validate` method, which defines the validation logic. If validation succeeds, the method returns `true`, otherwise `false`. Custom validators can be asynchronous — if you want to perform validation after some asynchronous operation, simply return a `Promise` from `validate`. The optional `defaultMessage` method defines a default error message, used when the decorator's implementation doesn't set its own error message. ### Using Custom Validator ```typescript import { Validate } from 'class-validator'; import { CustomTextLength } from './CustomTextLength'; export class Post { @Validate(CustomTextLength, { message: 'Title is too short or long!' }) title: string; } ``` You can also pass constraints to your validator: ```typescript import { Validate } from 'class-validator'; import { CustomTextLength } from './CustomTextLength'; export class Post { @Validate(CustomTextLength, [3, 20], { message: 'Wrong post title', }) title: string; } ``` And use them from the `validationArguments` object: ```typescript import { ValidationArguments, ValidatorConstraint, ValidatorConstraintInterface } from 'class-validator'; @ValidatorConstraint() export class CustomTextLength implements ValidatorConstraintInterface { validate(text: string, validationArguments: ValidationArguments) { return text.length > validationArguments.constraints[0] && text.length < validationArguments.constraints[1]; } } ``` ## Custom Validation Decorators You can also create a custom decorator. It's the most elegant way of using custom validations. Let's create a decorator called `@IsLongerThan`: ### Creating a Custom Decorator ```typescript import { registerDecorator, ValidationOptions, ValidationArguments } from 'class-validator'; export function IsLongerThan(property: string, validationOptions?: ValidationOptions) { return function (object: Object, propertyName: string) { registerDecorator({ name: 'isLongerThan', target: object.constructor, propertyName: propertyName, constraints: [property], options: validationOptions, validator: { validate(value: any, args: ValidationArguments) { const [relatedPropertyName] = args.constraints; const relatedValue = (args.object as any)[relatedPropertyName]; return typeof value === 'string' && typeof relatedValue === 'string' && value.length > relatedValue.length; } } }); }; } ``` ### Using Custom Decorator ```typescript import { IsLongerThan } from './IsLongerThan'; export class Post { title: string; @IsLongerThan('title', { message: 'Text must be longer than the title' }) text: string; } ``` In your custom decorators you can also use `ValidatorConstraint`. Let's create another custom validation decorator called `IsUserAlreadyExist`: ```typescript import { registerDecorator, ValidationOptions, ValidatorConstraint, ValidatorConstraintInterface, ValidationArguments, } from 'class-validator'; @ValidatorConstraint({ async: true }) export class IsUserAlreadyExistConstraint implements ValidatorConstraintInterface { validate(userName: any, args: ValidationArguments) { return UserRepository.findOneByName(userName).then(user => { if (user) return false; return true; }); } } export function IsUserAlreadyExist(validationOptions?: ValidationOptions) { return function (object: Object, propertyName: string) { registerDecorator({ target: object.constructor, propertyName: propertyName, options: validationOptions, constraints: [], validator: IsUserAlreadyExistConstraint, }); }; } ``` Note that we marked our constraint as async by adding `{ async: true }` to the validation options. Then put it to use: ```typescript import { IsUserAlreadyExist } from './IsUserAlreadyExist'; export class User { @IsUserAlreadyExist({ message: 'User $value already exists. Choose another name.', }) name: string; } ``` --- ## Using Service Container Source: https://class-validator.sonicar.tech/service-container/ # Using Service Container ## Overview Validator supports service container integration when you want to inject dependencies into your custom validator constraint classes. ## Integration with TypeDI Here is an example of how to integrate it with [TypeDI](https://github.com/pleerock/typedi): ```typescript import { Container } from 'typedi'; import { useContainer, Validator } from 'class-validator'; // do this somewhere in the global application level: useContainer(Container); let validator = Container.get(Validator); // now everywhere you can inject Validator class which will go from the container // also you can inject classes using constructor injection into your custom ValidatorConstraint-s ``` ## Example with Dependencies ```typescript import { ValidatorConstraint, ValidatorConstraintInterface } from 'class-validator'; import { UserRepository } from './UserRepository'; @ValidatorConstraint({ async: true }) export class IsUserAlreadyExistConstraint implements ValidatorConstraintInterface { constructor(protected userRepository: UserRepository) {} validate(userName: string) { return this.userRepository.findOneByName(userName).then(user => { if (user) return false; return true; }); } } ``` --- ## Validation Decorators Reference Source: https://class-validator.sonicar.tech/validation-decorators/ # Validation Decorators Reference The full list of decorators shipped with class-validator, grouped by category. ## Common Validation Decorators | Decorator | Description | | --- | --- | | `@IsDefined(value: any)` | Checks if value is defined (`!== undefined`, `!== null`). This is the only decorator that ignores `skipMissingProperties` option. | | `@IsOptional()` | Checks if given value is empty (`=== null`, `=== undefined`) and if so, ignores all the validators on the property. | | `@Equals(comparison: any)` | Checks if value equals (`===`) comparison. | | `@NotEquals(comparison: any)` | Checks if value not equal (`!==`) comparison. | | `@IsEmpty()` | Checks if given value is empty (`=== ''`, `=== null`, `=== undefined`). | | `@IsNotEmpty()` | Checks if given value is not empty (`!== ''`, `!== null`, `!== undefined`). | | `@IsIn(values: any[])` | Checks if value is in an array of allowed values. | | `@IsNotIn(values: any[])` | Checks if value is not in an array of disallowed values. | ## Type Validation Decorators | Decorator | Description | | --- | --- | | `@IsBoolean()` | Checks if a value is a boolean. | | `@IsDate()` | Checks if the value is a date. | | `@IsString()` | Checks if the value is a string. | | `@IsNumber(options: IsNumberOptions)` | Checks if the value is a number. | | `@IsInt()` | Checks if the value is an integer number. | | `@IsArray()` | Checks if the value is an array. | | `@IsEnum(entity: object)` | Checks if the value is a valid enum. | ## Number Validation Decorators | Decorator | Description | | --- | --- | | `@IsDivisibleBy(num: number)` | Checks if the value is a number that's divisible by another. | | `@IsPositive()` | Checks if the value is a positive number greater than zero. | | `@IsNegative()` | Checks if the value is a negative number smaller than zero. | | `@Min(min: number)` | Checks if the given number is greater than or equal to given number. | | `@Max(max: number)` | Checks if the given number is less than or equal to given number. | ## Date Validation Decorators | Decorator | Description | | --- | --- | | `@MinDate(date: Date \| (() => Date))` | Checks if the value is a date that's after the specified date. | | `@MaxDate(date: Date \| (() => Date))` | Checks if the value is a date that's before the specified date. | ## String-type Validation Decorators | Decorator | Description | | --- | --- | | `@IsBooleanString()` | Checks if a string is a boolean (e.g. is "true" or "false" or "1", "0"). | | `@IsDateString()` | Alias for `@IsISO8601()`. | | `@IsNumberString(options?: IsNumericOptions)` | Checks if a string is a number. | ## String Validation Decorators | Decorator | Description | | --- | --- | | `@Contains(seed: string)` | Checks if the string contains the seed. | | `@NotContains(seed: string)` | Checks if the string not contains the seed. | | `@IsAlpha()` | Checks if the string contains only letters (a-zA-Z). | | `@IsAlphanumeric()` | Checks if the string contains only letters and numbers. | | `@IsDecimal(options?: IsDecimalOptions)` | Checks if the string is a valid decimal value. Default `IsDecimalOptions` are `force_decimal=False`, `decimal_digits: '1,'`, `locale: 'en-US'`. | | `@IsAscii()` | Checks if the string contains ASCII chars only. | | `@IsBase32()` | Checks if a string is base32 encoded. | | `@IsBase58()` | Checks if a string is base58 encoded. | | `@IsBase64(options?: IsBase64Options)` | Checks if a string is base64 encoded. | | `@IsIBAN()` | Checks if a string is an IBAN (International Bank Account Number). | | `@IsBIC()` | Checks if a string is a BIC (Bank Identification Code) or SWIFT code. | | `@IsByteLength(min: number, max?: number)` | Checks if the string's length (in bytes) falls in a range. | | `@IsCreditCard()` | Checks if the string is a credit card. | | `@IsCurrency(options?: IsCurrencyOptions)` | Checks if the string is a valid currency amount. | | `@IsISO4217CurrencyCode()` | Checks if the string is an ISO 4217 currency code. | | `@IsEthereumAddress()` | Checks if the string is an Ethereum address using basic regex. Does not validate address checksums. | | `@IsBtcAddress()` | Checks if the string is a valid BTC address. | | `@IsDataURI()` | Checks if the string is a data uri format. | | `@IsEmail(options?: IsEmailOptions)` | Checks if the string is an email. | | `@IsFQDN(options?: IsFQDNOptions)` | Checks if the string is a fully qualified domain name (e.g. domain.com). | | `@IsFullWidth()` | Checks if the string contains any full-width chars. | | `@IsHalfWidth()` | Checks if the string contains any half-width chars. | | `@IsVariableWidth()` | Checks if the string contains a mixture of full and half-width chars. | | `@IsHexColor()` | Checks if the string is a hexadecimal color. | | `@IsHSL()` | Checks if the string is an HSL color based on the [CSS Colors Level 4 specification](https://developer.mozilla.org/en-US/docs/Web/CSS/color_value). | | `@IsRgbColor(options?: IsRgbOptions)` | Checks if the string is a rgb or rgba color. | | `@IsIdentityCard(locale?: string)` | Checks if the string is a valid identity card code. | | `@IsPassportNumber(countryCode?: string)` | Checks if the string is a valid passport number relative to a specific country code. | | `@IsPostalCode(locale?: string)` | Checks if the string is a postal code. | | `@IsHexadecimal()` | Checks if the string is a hexadecimal number. | | `@IsOctal()` | Checks if the string is an octal number. | | `@IsMACAddress(options?: IsMACAddressOptions)` | Checks if the string is a MAC Address. | | `@IsIP(version?: "4"\|"6")` | Checks if the string is an IP (version 4 or 6). | | `@IsPort()` | Checks if the string is a valid port number. | | `@IsISBN(version?: "10"\|"13")` | Checks if the string is an ISBN (version 10 or 13). | | `@IsEAN()` | Checks if the string is an EAN (European Article Number). | | `@IsISIN()` | Checks if the string is an ISIN (stock/security identifier). | | `@IsISO8601(options?: IsISO8601Options)` | Checks if the string is a valid ISO 8601 date format. Use the option `strict = true` for additional checks for a valid date. | | `@IsJSON()` | Checks if the string is valid JSON. | | `@IsJWT()` | Checks if the string is valid JWT. | | `@IsObject()` | Checks if the object is a valid Object (`null`, functions, arrays will return false). | | `@IsNotEmptyObject()` | Checks if the object is not empty. | | `@IsLowercase()` | Checks if the string is lowercase. | | `@IsLatLong()` | Checks if the string is a valid latitude-longitude coordinate in the format `lat, long`. | | `@IsLatitude()` | Checks if the string or number is a valid latitude coordinate. | | `@IsLongitude()` | Checks if the string or number is a valid longitude coordinate. | | `@IsMobilePhone(locale: string)` | Checks if the string is a mobile phone number. | | `@IsISO6391()` | Checks if the string is a valid ISO 639-1 officially assigned language code. | | `@IsISO31661Alpha2()` | Checks if the string is a valid ISO 3166-1 alpha-2 officially assigned country code. | | `@IsISO31661Alpha3()` | Checks if the string is a valid ISO 3166-1 alpha-3 officially assigned country code. | | `@IsISO31661Numeric()` | Checks if the string is a valid ISO 3166-1 numeric officially assigned country code. | | `@IsLocale()` | Checks if the string is a locale. | | `@IsPhoneNumber(region: string)` | Checks if the string is a valid phone number using libphonenumber-js. | | `@IsMongoId()` | Checks if the string is a valid hex-encoded representation of a MongoDB ObjectId. | | `@IsMultibyte()` | Checks if the string contains one or more multibyte chars. | | `@IsNumberString(options?: IsNumericOptions)` | Checks if the string is numeric. | | `@IsSurrogatePair()` | Checks if the string contains any surrogate pairs chars. | | `@IsTaxId()` | Checks if the string is a valid tax ID. Default locale is `en-US`. | | `@IsUrl(options?: IsURLOptions)` | Checks if the string is a URL. | | `@IsMagnetURI()` | Checks if the string is a [magnet uri format](https://en.wikipedia.org/wiki/Magnet_URI_scheme). | | `@IsUUID(version?: UUIDVersion)` | Checks if the string is a UUID (version 1-8, nil, max, loose, all). Also accepts array of versions. | | `@IsFirebasePushId()` | Checks if the string is a [Firebase Push ID](https://firebase.googleblog.com/2015/02/the-2120-ways-to-ensure-unique_68.html). | | `@IsUppercase()` | Checks if the string is uppercase. | | `@Length(min: number, max?: number)` | Checks if the string's length falls in a range. | | `@MinLength(min: number)` | Checks if the string's length is not less than given number. | | `@MaxLength(max: number)` | Checks if the string's length is not more than given number. | | `@Matches(pattern: RegExp, modifiers?: string)` | Checks if string matches the pattern. Either `matches('foo', /foo/i)` or `matches('foo', 'foo', 'i')`. | | `@IsMilitaryTime()` | Checks if the string is a valid representation of military time in the format HH:MM. | | `@IsTimeZone()` | Checks if the string represents a valid IANA time-zone. | | `@IsHash(algorithm: string)` | Checks if the string is a hash. Supported: `md4`, `md5`, `sha1`, `sha256`, `sha384`, `sha512`, `ripemd128`, `ripemd160`, `tiger128`, `tiger160`, `tiger192`, `crc32`, `crc32b`. | | `@IsMimeType()` | Checks if the string matches a valid [MIME type](https://en.wikipedia.org/wiki/Media_type) format. | | `@IsSemVer()` | Checks if the string is a Semantic Versioning Specification (SemVer). | | `@IsISSN(options?: IsISSNOptions)` | Checks if the string is an ISSN. | | `@IsISRC()` | Checks if the string is an [ISRC](https://en.wikipedia.org/wiki/International_Standard_Recording_Code). | | `@IsRFC3339()` | Checks if the string is a valid [RFC 3339](https://tools.ietf.org/html/rfc3339) date. | | `@IsStrongPassword(options?: IsStrongPasswordOptions)` | Checks if the string is a strong password. | ## Array Validation Decorators | Decorator | Description | | --- | --- | | `@ArrayContains(values: any[])` | Checks if array contains all values from the given array of values. | | `@ArrayNotContains(values: any[])` | Checks if array does not contain any of the given values. | | `@ArrayNotEmpty()` | Checks if given array is not empty. | | `@ArrayMinSize(min: number)` | Checks if the array's length is greater than or equal to the specified number. | | `@ArrayMaxSize(max: number)` | Checks if the array's length is less or equal to the specified number. | | `@ArrayUnique(identifier?: (o) => any)` | Checks if all array's values are unique. Comparison for objects is reference-based. An optional function can be specified whose return value is used for the comparison. | ## Object Validation Decorators | Decorator | Description | | --- | --- | | `@IsInstance(value: any)` | Checks if the property is an instance of the passed value. | ## Other Decorators | Decorator | Description | | --- | --- | | `@Allow()` | Prevent stripping off the property when no other constraint is specified for it. | --- ## Manual Validation Source: https://class-validator.sonicar.tech/manual-validation/ # Manual Validation ## Overview There are several methods in the Validator that allow performing non-decorator based validation. ## Basic Usage ```typescript import { isEmpty, isBoolean } from 'class-validator'; isEmpty(value); isBoolean(value); ``` ## Available Validation Functions All validation decorators have corresponding functions that can be used manually: ```typescript import { isEmail, isLength, isInt, min, max } from 'class-validator'; // String validation isEmail('example@email.com'); // true isLength('text', 2, 10); // true // Number validation isInt(123); // true min(5, 3); // true max(5, 10); // true ``` ## Synchronous vs Asynchronous Most validation functions are synchronous, but some (like those involving database queries) are asynchronous: ```typescript import { validate, validateSync, validateOrReject } from 'class-validator'; // Synchronous const errors = validateSync(object); if (errors.length > 0) { console.log('Validation failed:', errors); } // Asynchronous validate(object).then(errors => { if (errors.length > 0) { console.log('Validation failed:', errors); } }); // Using validateOrReject validateOrReject(object).catch(errors => { console.log('Validation failed:', errors); }); ``` --- ## About Sonicar Tech Source: https://class-validator.sonicar.tech/about-sonicar-tech/ # About Sonicar Tech **Sonicar Tech LLC** is a documentation-as-code agency. We design and build professional, searchable, versioned documentation sites — like this one — for SaaS, B2B, Enterprise, FinTech, and AI companies, using tools such as [Material for MkDocs](https://squidfunk.github.io/mkdocs-material/) and Docusaurus. ## What we do - **Docs-as-code builds**: documentation sites that live in Git, build with CI, and deploy like software. - **API & SDK references**: decorator/parameter tables, code samples, and versioned reference docs. - **Migrations & rewrites**: turning a sprawling README or wiki into a structured, navigable site. - **Search, SEO & AI/LLM discovery**: sitemaps, structured data, and `llms.txt` so both search engines and AI assistants can find and cite your docs accurately. ## Why it's fast Most engagements ship a first draft in **1 week**, at roughly **60% less cost** than staffing an in-house technical writer or docs team — without sacrificing the polish of a dedicated design system, dark/light theming, and consistent branding across every page. ## This site This Class Validator documentation is an independent example built by Sonicar Tech to showcase our documentation-as-code approach on a real, popular open-source library. It is not officially affiliated with or endorsed by the [class-validator](https://github.com/typestack/class-validator) maintainers or TypeStack. ## Get your own docs Ready to see what your product's documentation could look like? [:octicons-arrow-right-24: Visit sonicar.tech](https://sonicar.tech){ .md-button .md-button--primary target="_blank" } [:fontawesome-brands-whatsapp: Chat on WhatsApp](https://wa.me/201012506388){ .md-button target="_blank" }