fastify 5.2.1 → 5.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +1 -1
- package/PROJECT_CHARTER.md +7 -7
- package/README.md +24 -25
- package/SPONSORS.md +1 -0
- package/docs/Guides/Benchmarking.md +4 -4
- package/docs/Guides/Database.md +1 -1
- package/docs/Guides/Delay-Accepting-Requests.md +10 -10
- package/docs/Guides/Ecosystem.md +7 -1
- package/docs/Guides/Fluent-Schema.md +1 -1
- package/docs/Guides/Getting-Started.md +9 -5
- package/docs/Guides/Index.md +1 -1
- package/docs/Guides/Migration-Guide-V4.md +1 -1
- package/docs/Guides/Migration-Guide-V5.md +12 -2
- package/docs/Guides/Plugins-Guide.md +6 -6
- package/docs/Guides/Serverless.md +14 -48
- package/docs/Guides/Style-Guide.md +2 -2
- package/docs/Guides/Testing.md +2 -2
- package/docs/Guides/Write-Plugin.md +2 -3
- package/docs/Reference/ContentTypeParser.md +58 -78
- package/docs/Reference/Decorators.md +249 -60
- package/docs/Reference/Encapsulation.md +28 -33
- package/docs/Reference/Errors.md +52 -53
- package/docs/Reference/HTTP2.md +7 -7
- package/docs/Reference/Hooks.md +31 -30
- package/docs/Reference/LTS.md +10 -15
- package/docs/Reference/Lifecycle.md +19 -24
- package/docs/Reference/Logging.md +59 -56
- package/docs/Reference/Middleware.md +19 -19
- package/docs/Reference/Plugins.md +55 -71
- package/docs/Reference/Principles.md +25 -30
- package/docs/Reference/Reply.md +11 -10
- package/docs/Reference/Request.md +89 -98
- package/docs/Reference/Routes.md +108 -128
- package/docs/Reference/Server.md +18 -16
- package/docs/Reference/Type-Providers.md +19 -21
- package/docs/Reference/TypeScript.md +1 -18
- package/docs/Reference/Validation-and-Serialization.md +134 -159
- package/docs/Reference/Warnings.md +22 -25
- package/fastify.js +3 -2
- package/lib/contentTypeParser.js +7 -8
- package/lib/decorate.js +18 -3
- package/lib/error-handler.js +14 -12
- package/lib/errors.js +4 -0
- package/lib/headRoute.js +4 -2
- package/lib/pluginUtils.js +4 -2
- package/lib/reply.js +17 -2
- package/lib/request.js +28 -2
- package/lib/server.js +5 -0
- package/lib/validation.js +1 -1
- package/lib/warnings.js +9 -0
- package/lib/wrapThenable.js +8 -1
- package/package.json +12 -12
- package/test/bundler/esbuild/package.json +1 -1
- package/test/close.test.js +125 -108
- package/test/custom-parser-async.test.js +34 -36
- package/test/custom-parser.4.test.js +55 -38
- package/test/decorator.test.js +174 -4
- package/test/fastify-instance.test.js +12 -2
- package/test/genReqId.test.js +125 -174
- package/test/has-route.test.js +1 -3
- package/test/hooks.on-listen.test.js +17 -14
- package/test/internals/content-type-parser.test.js +1 -1
- package/test/internals/errors.test.js +14 -1
- package/test/issue-4959.test.js +84 -0
- package/test/listen.1.test.js +37 -34
- package/test/listen.2.test.js +50 -40
- package/test/listen.3.test.js +28 -32
- package/test/listen.4.test.js +61 -45
- package/test/listen.5.test.js +23 -0
- package/test/register.test.js +55 -50
- package/test/request-error.test.js +114 -94
- package/test/route-shorthand.test.js +36 -32
- package/test/stream.5.test.js +35 -33
- package/test/throw.test.js +87 -91
- package/test/toolkit.js +32 -0
- package/test/trust-proxy.test.js +23 -23
- package/test/types/instance.test-d.ts +4 -0
- package/test/types/reply.test-d.ts +1 -0
- package/test/types/request.test-d.ts +4 -0
- package/test/types/type-provider.test-d.ts +40 -0
- package/test/upgrade.test.js +32 -33
- package/types/instance.d.ts +6 -0
- package/types/reply.d.ts +1 -0
- package/types/request.d.ts +2 -0
- package/types/type-provider.d.ts +12 -3
|
@@ -14,7 +14,7 @@ suggestion"](https://github.com/fastify/fastify/issues?q=is%3Aissue+is%3Aopen+la
|
|
|
14
14
|
in our issue tracker!*
|
|
15
15
|
|
|
16
16
|
## Code
|
|
17
|
-
Fastify uses different techniques to optimize its code, many of
|
|
17
|
+
Fastify uses different techniques to optimize its code, many of which are
|
|
18
18
|
documented in our Guides. We highly recommend you read [the hitchhiker's guide
|
|
19
19
|
to plugins](./Plugins-Guide.md) to discover all the APIs you can use to build
|
|
20
20
|
your plugin and learn how to use them.
|
|
@@ -53,8 +53,7 @@ Always put an example file in your repository. Examples are very helpful for
|
|
|
53
53
|
users and give a very fast way to test your plugin. Your users will be grateful.
|
|
54
54
|
|
|
55
55
|
## Test
|
|
56
|
-
|
|
57
|
-
working properly.
|
|
56
|
+
A plugin **must** be thoroughly tested to verify that is working properly.
|
|
58
57
|
|
|
59
58
|
A plugin without tests will not be accepted to the ecosystem list. A lack of
|
|
60
59
|
tests does not inspire trust nor guarantee that the code will continue to work
|
|
@@ -1,38 +1,32 @@
|
|
|
1
1
|
<h1 align="center">Fastify</h1>
|
|
2
2
|
|
|
3
3
|
## `Content-Type` Parser
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
Other common content types are supported through the use of
|
|
8
|
-
[plugins](https://fastify.dev/ecosystem/).
|
|
4
|
+
Fastify natively supports `'application/json'` and `'text/plain'` content types
|
|
5
|
+
with a default charset of `utf-8`. These default parsers can be changed or
|
|
6
|
+
removed.
|
|
9
7
|
|
|
10
|
-
|
|
11
|
-
you can use the `addContentTypeParser` API. *The default JSON and/or plain text
|
|
12
|
-
parser can be changed or removed.*
|
|
8
|
+
Unsupported content types will throw an `FST_ERR_CTP_INVALID_MEDIA_TYPE` error.
|
|
13
9
|
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
`text/html; charset=utf-8`.*
|
|
10
|
+
To support other content types, use the `addContentTypeParser` API or an
|
|
11
|
+
existing [plugin](https://fastify.dev/ecosystem/).
|
|
17
12
|
|
|
18
|
-
As with
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
available only in that scope and its children.
|
|
13
|
+
As with other APIs, `addContentTypeParser` is encapsulated in the scope in which
|
|
14
|
+
it is declared. If declared in the root scope, it is available everywhere; if
|
|
15
|
+
declared in a plugin, it is available only in that scope and its children.
|
|
22
16
|
|
|
23
17
|
Fastify automatically adds the parsed request payload to the [Fastify
|
|
24
|
-
request](./Request.md) object
|
|
25
|
-
|
|
26
|
-
Note that for `GET` and `HEAD` requests the payload is never parsed. For
|
|
27
|
-
`OPTIONS` and `DELETE` requests the payload is only
|
|
28
|
-
|
|
29
|
-
[catch-all](#catch-all) parser is not executed
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
>
|
|
33
|
-
> When using
|
|
34
|
-
>
|
|
35
|
-
>
|
|
18
|
+
request](./Request.md) object, accessible via `request.body`.
|
|
19
|
+
|
|
20
|
+
Note that for `GET` and `HEAD` requests, the payload is never parsed. For
|
|
21
|
+
`OPTIONS` and `DELETE` requests, the payload is parsed only if a valid
|
|
22
|
+
`content-type` header is provided. Unlike `POST`, `PUT`, and `PATCH`, the
|
|
23
|
+
[catch-all](#catch-all) parser is not executed, and the payload is simply not
|
|
24
|
+
parsed.
|
|
25
|
+
|
|
26
|
+
> ⚠ Warning:
|
|
27
|
+
> When using regular expressions to detect `Content-Type`, it is important to
|
|
28
|
+
> ensure proper detection. For example, to match `application/*`, use
|
|
29
|
+
> `/^application\/([\w-]+);?/` to match the
|
|
36
30
|
> [essence MIME type](https://mimesniff.spec.whatwg.org/#mime-type-miscellaneous)
|
|
37
31
|
> only.
|
|
38
32
|
|
|
@@ -70,11 +64,10 @@ fastify.addContentTypeParser('text/json', { parseAs: 'string' }, fastify.getDefa
|
|
|
70
64
|
```
|
|
71
65
|
|
|
72
66
|
Fastify first tries to match a content-type parser with a `string` value before
|
|
73
|
-
trying to find a matching `RegExp`.
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
more specific one, like in the example below.
|
|
67
|
+
trying to find a matching `RegExp`. For overlapping content types, it starts
|
|
68
|
+
with the last one configured and ends with the first (last in, first out).
|
|
69
|
+
To specify a general content type more precisely, first specify the general
|
|
70
|
+
type, then the specific one, as shown below.
|
|
78
71
|
|
|
79
72
|
```js
|
|
80
73
|
// Here only the second content type parser is called because its value also matches the first one
|
|
@@ -88,10 +81,9 @@ fastify.addContentTypeParser('application/vnd.custom+xml', (request, body, done)
|
|
|
88
81
|
```
|
|
89
82
|
|
|
90
83
|
### Using addContentTypeParser with fastify.register
|
|
91
|
-
When using `addContentTypeParser`
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
before the addContentTypeParser has been set.
|
|
84
|
+
When using `addContentTypeParser` with `fastify.register`, avoid `await`
|
|
85
|
+
when registering routes. Using `await` makes route registration asynchronous,
|
|
86
|
+
potentially registering routes before `addContentTypeParser` is set.
|
|
95
87
|
|
|
96
88
|
#### Correct Usage
|
|
97
89
|
```js
|
|
@@ -109,14 +101,13 @@ fastify.register((fastify, opts) => {
|
|
|
109
101
|
});
|
|
110
102
|
```
|
|
111
103
|
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
`removeAllContentTypeParsers`.
|
|
104
|
+
In addition to `addContentTypeParser`, the `hasContentTypeParser`,
|
|
105
|
+
`removeContentTypeParser`, and `removeAllContentTypeParsers` APIs are available.
|
|
115
106
|
|
|
116
107
|
#### hasContentTypeParser
|
|
117
108
|
|
|
118
|
-
|
|
119
|
-
|
|
109
|
+
Use the `hasContentTypeParser` API to check if a specific content type parser
|
|
110
|
+
exists.
|
|
120
111
|
|
|
121
112
|
```js
|
|
122
113
|
if (!fastify.hasContentTypeParser('application/jsoff')){
|
|
@@ -130,8 +121,8 @@ if (!fastify.hasContentTypeParser('application/jsoff')){
|
|
|
130
121
|
|
|
131
122
|
#### removeContentTypeParser
|
|
132
123
|
|
|
133
|
-
|
|
134
|
-
|
|
124
|
+
`removeContentTypeParser` can remove a single content type or an array of
|
|
125
|
+
content types, supporting both `string` and `RegExp`.
|
|
135
126
|
|
|
136
127
|
```js
|
|
137
128
|
fastify.addContentTypeParser('text/xml', function (request, payload, done) {
|
|
@@ -145,16 +136,11 @@ fastify.removeContentTypeParser(['application/json', 'text/plain'])
|
|
|
145
136
|
```
|
|
146
137
|
|
|
147
138
|
#### removeAllContentTypeParsers
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
the example above except that we do not need to specify each content type to
|
|
154
|
-
delete. Just like `removeContentTypeParser`, this API supports encapsulation.
|
|
155
|
-
The API is especially useful if you want to register a [catch-all content type
|
|
156
|
-
parser](#catch-all) that should be executed for every content type and the
|
|
157
|
-
built-in parsers should be ignored as well.
|
|
139
|
+
The `removeAllContentTypeParsers` API removes all existing content type parsers
|
|
140
|
+
eliminating the need to specify each one individually. This API supports
|
|
141
|
+
encapsulation and is useful for registering a
|
|
142
|
+
[catch-all content type parser](#catch-all) that should be executed for every
|
|
143
|
+
content type, ignoring built-in parsers.
|
|
158
144
|
|
|
159
145
|
```js
|
|
160
146
|
fastify.removeAllContentTypeParsers()
|
|
@@ -166,18 +152,16 @@ fastify.addContentTypeParser('text/xml', function (request, payload, done) {
|
|
|
166
152
|
})
|
|
167
153
|
```
|
|
168
154
|
|
|
169
|
-
|
|
170
|
-
|
|
155
|
+
> 🛈 Note: `function(req, done)` and `async function(req)` are
|
|
156
|
+
> still supported but deprecated.
|
|
171
157
|
|
|
172
158
|
#### Body Parser
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
size](./Server.md#factory-body-limit) of the body and the content length. If the
|
|
180
|
-
limit is exceeded the custom parser will not be invoked.
|
|
159
|
+
The request body can be parsed in two ways. First, add a custom content type
|
|
160
|
+
parser and handle the request stream. Or second, use the `parseAs` option in the
|
|
161
|
+
`addContentTypeParser` API, specifying `'string'` or `'buffer'`. Fastify will
|
|
162
|
+
handle the stream, check the [maximum size](./Server.md#factory-body-limit) of
|
|
163
|
+
the body, and the content length. If the limit is exceeded, the custom parser
|
|
164
|
+
will not be invoked.
|
|
181
165
|
```js
|
|
182
166
|
fastify.addContentTypeParser('application/json', { parseAs: 'string' }, function (req, body, done) {
|
|
183
167
|
try {
|
|
@@ -195,15 +179,14 @@ See
|
|
|
195
179
|
for an example.
|
|
196
180
|
|
|
197
181
|
##### Custom Parser Options
|
|
198
|
-
+ `parseAs` (string):
|
|
199
|
-
|
|
182
|
+
+ `parseAs` (string): `'string'` or `'buffer'` to designate how the incoming
|
|
183
|
+
data should be collected. Default: `'buffer'`.
|
|
200
184
|
+ `bodyLimit` (number): The maximum payload size, in bytes, that the custom
|
|
201
185
|
parser will accept. Defaults to the global body limit passed to the [`Fastify
|
|
202
186
|
factory function`](./Server.md#bodylimit).
|
|
203
187
|
|
|
204
188
|
#### Catch-All
|
|
205
|
-
|
|
206
|
-
content type. With Fastify, you can just use the `'*'` content type.
|
|
189
|
+
To catch all requests regardless of content type, use the `'*'` content type:
|
|
207
190
|
```js
|
|
208
191
|
fastify.addContentTypeParser('*', function (request, payload, done) {
|
|
209
192
|
let data = ''
|
|
@@ -213,12 +196,10 @@ fastify.addContentTypeParser('*', function (request, payload, done) {
|
|
|
213
196
|
})
|
|
214
197
|
})
|
|
215
198
|
```
|
|
199
|
+
All requests without a corresponding content type parser will be handled by
|
|
200
|
+
this function.
|
|
216
201
|
|
|
217
|
-
|
|
218
|
-
will be handled by the specified function.
|
|
219
|
-
|
|
220
|
-
This is also useful for piping the request stream. You can define a content
|
|
221
|
-
parser like:
|
|
202
|
+
This is also useful for piping the request stream. Define a content parser like:
|
|
222
203
|
|
|
223
204
|
```js
|
|
224
205
|
fastify.addContentTypeParser('*', function (request, payload, done) {
|
|
@@ -226,7 +207,7 @@ fastify.addContentTypeParser('*', function (request, payload, done) {
|
|
|
226
207
|
})
|
|
227
208
|
```
|
|
228
209
|
|
|
229
|
-
|
|
210
|
+
And then access the core HTTP request directly for piping:
|
|
230
211
|
|
|
231
212
|
```js
|
|
232
213
|
app.post('/hello', (request, reply) => {
|
|
@@ -254,12 +235,11 @@ fastify.route({
|
|
|
254
235
|
})
|
|
255
236
|
```
|
|
256
237
|
|
|
257
|
-
For piping file uploads
|
|
258
|
-
|
|
238
|
+
For piping file uploads, check out
|
|
239
|
+
[`@fastify/multipart`](https://github.com/fastify/fastify-multipart).
|
|
259
240
|
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
`removeAllContentTypeParsers` method first.
|
|
241
|
+
To execute the content type parser on all content types, call
|
|
242
|
+
`removeAllContentTypeParsers` first.
|
|
263
243
|
|
|
264
244
|
```js
|
|
265
245
|
// Without this call, the request body with the content type application/json would be processed by the built-in JSON parser
|