You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
@@ -126,6 +126,138 @@ In order to explicitly set the type of the property, use the `type` key:
126
126
age: number;
127
127
```
128
128
129
+
#### Arrays
130
+
131
+
When the property is an array, we must manually indicate the array type as shown below:
132
+
133
+
```typescript
134
+
@ApiProperty({ type: [String] })
135
+
names: string[];
136
+
```
137
+
138
+
> info **Hint** Consider using the Swagger plugin (see [Plugin](/recipes/swagger#plugin) section) which will automatically detect arrays.
139
+
140
+
Either include the type as the first element of an array (as shown above) or set the `isArray` property to `true`.
141
+
142
+
<app-banner-enterprise></app-banner-enterprise>
143
+
144
+
#### Circular dependencies
145
+
146
+
When you have circular dependencies between classes, use a lazy function to provide the `SwaggerModule` with type information:
147
+
148
+
```typescript
149
+
@ApiProperty({ type: () =>Node })
150
+
node: Node;
151
+
```
152
+
153
+
> info **Hint** Consider using the Swagger plugin (see [Plugin](/recipes/swagger#plugin) section) which will automatically detect circular dependencies.
154
+
155
+
#### Generics and interfaces
156
+
157
+
Since TypeScript does not store metadata about generics or interfaces, when you use them in your DTOs, `SwaggerModule` may not be able to properly generate model definitions at runtime. For instance, below code won't be correctly inspected by the Swagger module:
158
+
159
+
```typescript
160
+
createBulk(@Body() usersDto: CreateUserDto[])
161
+
```
162
+
163
+
In order to overcome this limitation, you can set the type explicitly:
164
+
165
+
```typescript
166
+
@ApiBody({ type: [CreateUserDto] })
167
+
createBulk(@Body() usersDto: CreateUserDto[])
168
+
```
169
+
170
+
#### Mapped types
171
+
172
+
As you build out features like **CRUD** (Create/Read/Update/Delete) it's often useful to construct variants on a base entity type. Nest provides several utility functions that perform type transformations to make this task more convenient.
173
+
174
+
When building input validation types (also called DTOs), it's often useful to build **create** and **update** variations on the same type. For example, the **create** variant may require all fields, while the **update** variant may make all fields optional.
175
+
176
+
Nest provides the `PartialType()` utility function to make this task easier and minimize boilerplate.
177
+
178
+
The `PartialType()` function returns a type (class) with all the properties of the input type set to optional. For example, suppose we have a **create** type as follows:
179
+
180
+
```typescript
181
+
import { ApiProperty } from'@nestjs/swagger';
182
+
183
+
exportclassCreateCatDto {
184
+
@ApiProperty()
185
+
name:string;
186
+
187
+
@ApiProperty()
188
+
age:number;
189
+
190
+
@ApiProperty()
191
+
breed:string;
192
+
}
193
+
```
194
+
195
+
y default, all of these fields are required. To create a type with the same fields, but with each one optional, use `PartialType()` passing the class reference (`CreateCatDto`) as an argument:
> info **Hint** The `PartialType()` function is imported from the `@nestjs/swagger` package.
202
+
203
+
The `PickType()` function constructs a new type (class) by picking a set of properties from an input type. For example, suppose we start with a type like:
204
+
205
+
```typescript
206
+
import { ApiProperty } from'@nestjs/swagger';
207
+
208
+
exportclassCreateCatDto {
209
+
@ApiProperty()
210
+
name:string;
211
+
212
+
@ApiProperty()
213
+
age:number;
214
+
215
+
@ApiProperty()
216
+
breed:string;
217
+
}
218
+
```
219
+
220
+
We can pick a set of properties from this class using the `PickType()` utility function:
> info **Hint** The `PickType()` function is imported from the `@nestjs/swagger` package.
227
+
228
+
The `OmitType()` function constructs a type by picking all properties from an input type and then removing a particular set of keys. For example, suppose we start with a type like:
229
+
230
+
```typescript
231
+
import { ApiProperty } from'@nestjs/swagger';
232
+
233
+
exportclassCreateCatDto {
234
+
@ApiProperty()
235
+
name:string;
236
+
237
+
@ApiProperty()
238
+
age:number;
239
+
240
+
@ApiProperty()
241
+
breed:string;
242
+
}
243
+
```
244
+
245
+
We can generate a derived type that has every property **except**`name` as shown below. In this construct, the second argument to `OmitType` is an array of property names.
> info **Hint** The `OmitType()` function is imported from the `@nestjs/swagger` package.
252
+
253
+
The type mapping utility functions are composable. For example, the following will produce a type (class) that has all of the properties of the `CreateCatDto` type except for `name`, and those properties will be set to optional:
254
+
255
+
```typescript
256
+
exportclassUpdateCatDtoextendsPartialType(
257
+
OmitType(CreateCatDto, ['name']),
258
+
) {}
259
+
```
260
+
129
261
#### Enums
130
262
131
263
To identify an `enum`, we must manually set the `enum` property on the `@ApiProperty` with an array of values.
@@ -163,24 +295,20 @@ With `isArray` set to **true**, the `enum` can be selected as a **multi-select**
163
295
By default, the `enum` property will add a raw definition of [Enum](https://swagger.io/docs/specification/data-models/enums/) on the `parameter`.
164
296
165
297
```yaml
166
-
CatDetail:
167
-
type: 'object'
168
-
properties:
169
-
...
170
-
- breed:
171
-
type: 'string'
172
-
enum:
173
-
- Persian
174
-
- Tabby
175
-
- Siamese
298
+
- breed:
299
+
type: 'string'
300
+
enum:
301
+
- Persian
302
+
- Tabby
303
+
- Siamese
176
304
```
177
305
178
-
The above specification works fine for most cases. However, if you are utilizing a tool that takes the specification as **input** and generates **client-side** code, you might run into a problem with the generated code containing duplicated `enums`. Consider the following code snippet:
306
+
The above specification works fine for most cases. However, if you are utilizing a tool that takes the specification as **input** and generates **client-side** code, you might run into a problem with the generated code containing duplicated `enums`. Consider the following code snippet:
179
307
180
308
```typescript
181
309
// generated client-side code
182
310
export class CatDetail {
183
-
breed: CatDetailEnum;
311
+
breed: CatDetailEnum;
184
312
}
185
313
186
314
export class CatInformation {
@@ -190,29 +318,29 @@ export class CatInformation {
190
318
export enum CatDetailEnum {
191
319
Persian = 'Persian',
192
320
Tabby = 'Tabby',
193
-
Siamese = 'Siamese'
321
+
Siamese = 'Siamese',
194
322
}
195
323
196
324
export enum CatInformationEnum {
197
325
Persian = 'Persian',
198
326
Tabby = 'Tabby',
199
-
Siamese = 'Siamese'
327
+
Siamese = 'Siamese',
200
328
}
201
329
```
202
330
203
331
> info **Hint** The above snippet is generated using a tool called [NSwag](https://github.com/RicoSuter/NSwag).
204
332
205
-
You can see that now you have two `enums` that are exactly the same.
333
+
You can see that now you have two `enums` that are exactly the same.
206
334
To address this issue, you can pass an `enumName` next to `enum` property in your decorator.
`enumName` enables `nestjs/swagger` to turn `CatBreed` into its own `schema` which in turns makes `CatBreed` reusable. The specification will look like the following:
343
+
The `enumName` property enables `@nestjs/swagger` to turn `CatBreed` into its own `schema` which in turns makes `CatBreed` enum reusable. The specification will look like the following:
216
344
217
345
```yaml
218
346
CatDetail:
@@ -232,47 +360,6 @@ CatBreed:
232
360
233
361
> info **Hint** Any **decorator** that takes `enum` as a property will also take `enumName`.
234
362
235
-
#### Arrays
236
-
237
-
When the property is an array, we must manually indicate the array type as shown below:
238
-
239
-
```typescript
240
-
@ApiProperty({ type: [String] })
241
-
names: string[];
242
-
```
243
-
244
-
> info **Hint** Consider using the Swagger plugin (see [Plugin](/recipes/swagger#plugin) section) which will automatically detect arrays.
245
-
246
-
Either include the type as the first element of an array (as shown above) or set the `isArray` property to `true`.
247
-
248
-
<app-banner-enterprise></app-banner-enterprise>
249
-
250
-
#### Circular dependencies
251
-
252
-
When you have circular dependencies between classes, use a lazy function to provide the `SwaggerModule` with type information:
253
-
254
-
```typescript
255
-
@ApiProperty({ type: () => Node })
256
-
node: Node;
257
-
```
258
-
259
-
> info **Hint** Consider using the Swagger plugin (see [Plugin](/recipes/swagger#plugin) section) which will automatically detect circular dependencies.
260
-
261
-
#### Generics and interfaces
262
-
263
-
Since TypeScript does not store metadata about generics or interfaces, when you use them in your DTOs, `SwaggerModule` may not be able to properly generate model definitions at runtime. For instance, below code won't be correctly inspected by the Swagger module:
264
-
265
-
```typescript
266
-
createBulk(@Body() usersDto: CreateUserDto[])
267
-
```
268
-
269
-
In order to overcome this limitation, you can set the type explicitly:
270
-
271
-
```typescript
272
-
@ApiBody({ type: [CreateUserDto] })
273
-
createBulk(@Body() usersDto: CreateUserDto[])
274
-
```
275
-
276
363
#### Raw definitions
277
364
278
365
In some specific scenarios (e.g. deeply nested arrays, matrices), you may want to describe your type by hand.
0 commit comments