DEV Community

Cover image for Validating nested objects with class-validator in NestJS
Krzysztof Szala
Krzysztof Szala

Posted on • Updated on

Validating nested objects with class-validator in NestJS

Today I have for you a quick and short article. Maybe it will help someone. I'm using class-validator for request validation in NestJS really often. A few days ago I needed to validate a nested object. Quick look to the class-validator 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:

import { ValidateNested } from 'class-validator';

export class Post {
  @ValidateNested()
  user: User;
}
Enter fullscreen mode Exit fullscreen mode

But for some reason It doesn't work in NestJS! Here is an easy solution. Install class-transformer package, if you haven't done it yet. Then import @Type() decorator, and declare the type of validating object with it. Check this out:

import { ValidateNested } from 'class-validator';
import { Type } from 'class-transformer';

export class Post {
  @ValidateNested()
  @Type(() => User)
  user: User;
}
Enter fullscreen mode Exit fullscreen mode

Now our NestJS application will validate User object correctly. If you need to validate an array of objects, use each: true:

export class User {
  @ValidateNested({ each: true })
  @Type(() => Post)
  posts: Post[];
}
Enter fullscreen mode Exit fullscreen mode

Hope it will be useful for you! Cheers!

Top comments (27)

Collapse
 
olustrrax profile image
dan's cat • Edited

I had received this error

TypeError: Cannot convert undefined or null to object

after I wrote something like this

  @IsArray()
  @ArrayNotEmpty()
  @ValidateNested({ each: true })
  @Type(() => UserDto)
  items: UserDto[]
Enter fullscreen mode Exit fullscreen mode

Why its does not work for me 😢

Collapse
 
avantar profile image
Krzysztof Szala

Are you sure that items property is not null / undefined? Maybe it didn't come in the request?

Collapse
 
olustrrax profile image
dan's cat

Finally I knew why it wasn't work for me. Because I wrote nested object in array more than couple layers. By the way I have fixed it by customized validate pipe when it received bad request exception. Now it works for me!

Thread Thread
 
oliverqueen2003 profile image
oliverqueen2003

Can you share your code?

Thread Thread
 
navinmishra1717 profile image
Navin Mishra • Edited

i was able to solve this problem with the help of custom recursive function in global validation pipe like this:

helper.js
Image description

and in main.ts

Image description

Collapse
 
shanike profile image
Shani Kehati

Thanks

Collapse
 
avantar profile image
Krzysztof Szala

You’re welcome! 😄

Collapse
 
souhaildev profile image
Souhail Dev

it works! Thanks

Collapse
 
rolanday profile image
Roland Ayala

Right to the point, and just what I was looking for. Kudos, Thank you!

Collapse
 
volodymyr83 profile image
Volodymyr83 • Edited

Hi. Great article! But if an object in the array doesn't pass validation, I receive only
{
"statusCode": 500,
"message": "Internal server error"
}
How to get message with exact validation error?

Collapse
 
kanelv profile image
Cuong Le

I have faced the same problem. Did you solve it? Bro?

Collapse
 
adapting profile image
Albert

What about disallowing nested arrays within the array?

@ValidateNested({each: true})
@Type(() => myType)
myProp: myType[]
Enter fullscreen mode Exit fullscreen mode

allows the property to be both an array of arrays, or an array of objects with the form of myType, instead of only allowing it to be an array of objects.

Collapse
 
dekkaladiwakar profile image
Diwakar • Edited

Any solution for this? I want to allow only objects. @avantar

Collapse
 
rildomar_lucena profile image
Rildomar Lucena • Edited

Hello!

I'm having some problems with my validate errors.. When i tryed validate some object with one attribute is an array of object, the validate error doenst show message erro validation, only the property and value, but no showing the message.. example:

on my objectItem i have two attributes, like:

class ObjectItem {
   @IsString()
   @IsNotEmpty({ message: 'This field is required')
   attributeOne: string;

   @IsString()
   @IsNotEmpty({ message: 'This field is required')
   attributeTwo: string;
}

class ObjectFather {
   @IsArray()
  @IsObject({ each: true })
  @ValidateNested({
    each: true,
    message: 'Each value in items must be an object',
  })
  @Type(() => ObjectItem)
  components: ObjectItem[]
}
Enter fullscreen mode Exit fullscreen mode

but, i'm having this error on postman:
Image description

Why the messate of attributeOne no showing with constraints?

Collapse
 
bassochette profile image
Julien Prugne

Thanks mate, really helpful :)

Collapse
 
avantar profile image
Krzysztof Szala

Glad I could help!

Collapse
 
daygarcia profile image
Dayanne Garcia

Great article, thanks. But I'm struggling with something that looks simple, but I can't find nothing about this on internet

If i have a request like this:

[{
"name", "Azuki",
"age": 17
},
{
"name": "Luke"
"age": 18
}]

How can I validate?

Collapse
 
avantar profile image
Krzysztof Szala

But what do you want to validate exactly? That every object in array has valid structure?

Collapse
 
elijahcorleone profile image
£.j

Dont Forget to add the @IsDefined() decorator as to check as might skip validation

Collapse
 
carrasc0 profile image
Gabriel Betancourt • Edited

Throw me a Cannot access '' before initialization.

Followed exactly same steps

Collapse
 
avantar profile image
Krzysztof Szala

Hard to guess what's wrong. Share your code please, maybe then I can help. Regards :)

Collapse
 
jguillermo profile image
Jose guillermo

Thanks a lot!

Collapse
 
avantar profile image
Krzysztof Szala

You’re welcome!

Collapse
 
skona27 profile image
Jakub Skoneczny

Thanks a lot!

Collapse
 
avantar profile image
Krzysztof Szala

You're welcome!

Collapse
 
alexxiv profile image
Aleksandar Ivanov

I made account just to say THANK YOU!

Collapse
 
avantar profile image
Krzysztof Szala

Glad I could help! Cheers :)