I'm using Prisma, my schema has a table user where a user can have the role of a normal user or an admin.
I have an editUserDto that validates the incoming data during patch requests for the user.
I want to change the logic so that if the user role is ADMIN, the admin can only change the role of the user (so only the role will be exposed to the admin)
and if the user role is USER, only fullname and phoneNumber will be exposed
the following is edit-user.dto.ts:
import { Role } from '@prisma/client';
import { Expose } from 'class-transformer';
import { IsEmail, IsEnum, IsOptional, IsString } from 'class-validator';
export class EditUserDto {
@IsString()
@Expose({ groups: [Role.USER] })
fullname: string;
@IsString()
@Expose({ groups: [Role.USER] })
phoneNumber: string;
@IsEnum(Role)
@Expose({ groups: [Role.ADMIN] })
role: Role;
}
user.controller.ts:
import {
Body,
ClassSerializerInterceptor,
Controller,
Get,
Param,
Patch,
SerializeOptions,
UploadedFile,
UseGuards,
UseInterceptors,
} from '@nestjs/common';
import { FileInterceptor } from '@nestjs/platform-express';
import { Role, User } from '@prisma/client';
import { GetUser } from '../auth/decorator';
import { JwtGuard } from '../auth/guard';
import { EditUserDto } from './dto';
import { UserService } from './user.service';
@UseGuards(JwtGuard)
@Controller('user')
export class UserController {
constructor(private userService: UserService) {}
@Get('me')
getMe(@GetUser() user: User) {
return user;
}
@Patch('/:userId')
@UseInterceptors(ClassSerializerInterceptor, FileInterceptor('file'))
@SerializeOptions({
groups: [Role.ADMIN],
})
editUser(
@GetUser('id') requestingUserId: string,
@Param('userId') userId,
@Body() dto: EditUserDto,
@UploadedFile() file: Express.Multer.File,
) {
return this.userService.editUser(userId, dto, requestingUserId, file);
}
}
the code I have shown above acts a bit weird. when I make a request and provide the data for all properties, I get the following error:
{
"statusCode": 400,
"message": [
"fullname must be a string",
"phoneNumber must be a string",
"role must be a valid enum value"
],
"error": "Bad Request"
}
my 1st question: why would it complain that these values haven't been passed? if I comment out the expose decorator or pass an empty array, the data is accepted by the dto so I'm guessing the problem is related to expose.
my 2nd question: assuming that problem is resolved, how can I pass a dynamic group into the SerializeOptions based on the current user's role?
my 3rd question: is this the right approach? is there an entirely different way to do this?
appreciate any help I can get. thanks in advance.