I am facing a problem where my DTO types are named one thing, but I want them to appear with a different name in the OpenAPI doc page. For example, I have a UserDto class that I use in my controller, but wanted it to appear as simply "User" in the schemas section (and everywhere else this applies). Is that possible? Is there any decorator I can use? I know I can simply modify the class name, but there is already a different user class used elsewhere. I have searched everywhere with no avail.
BTW, I am using typescript and nestjs. Every help will be appreciated, thanks!
Out of the box, Nest.js doesn't yet offer a ready-made solution. There is an open pull request (as mentioned earlier) https://github.com/nestjs/swagger/pull/983, but when it will be merged is unknown. You can change the DTO name in schemas using one of the following approaches:
class UserDto {
static name = 'User'; // <- here
@ApiProperty()
firstName: string;
// ...
}
But in strict mode, TypeScript will show an error like:
Static property 'name' conflicts with built-in property 'Function.name' of constructor function 'UserDto'.
type Constructor<T = object> = new(...args: any[]) => T;
type Wrapper<T = object> = { new(): (T & any), prototype: T };
type DecoratorOptions = { name: string };
type ApiSchemaDecorator = <T extends Constructor>(options: DecoratorOptions) => (constructor: T) => Wrapper<T>;
const ApiSchema: ApiSchemaDecorator = ({ name }) => {
return (constructor) => {
const wrapper = class extends constructor { };
Object.defineProperty(wrapper, 'name', {
value: name,
writable: false,
});
return wrapper;
}
}
Use as suggested in the proposal:
@ApiSchema({ name: 'User' }) // <- here
class UserDto {
@ApiProperty()
firstName: string;
// ...
}
And don't forget that in TypeScript 5 the decorator API will change to something close to the implementation in JavaScript 😉