fastify 5.4.0 → 5.5.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/.vscode/settings.json +22 -0
- package/LICENSE +1 -1
- package/SECURITY.md +158 -2
- package/build/build-validation.js +19 -1
- package/docs/Guides/Delay-Accepting-Requests.md +8 -5
- package/docs/Guides/Ecosystem.md +11 -0
- package/docs/Guides/Migration-Guide-V5.md +6 -10
- package/docs/Guides/Recommendations.md +1 -1
- package/docs/Reference/Errors.md +3 -1
- package/docs/Reference/Hooks.md +2 -6
- package/docs/Reference/Lifecycle.md +2 -2
- package/docs/Reference/Request.md +1 -1
- package/docs/Reference/Routes.md +4 -3
- package/docs/Reference/Server.md +306 -179
- package/docs/Reference/TypeScript.md +1 -3
- package/docs/Reference/Validation-and-Serialization.md +55 -3
- package/docs/Reference/Warnings.md +2 -1
- package/fastify.d.ts +2 -2
- package/fastify.js +34 -33
- package/lib/configValidator.js +196 -28
- package/lib/contentTypeParser.js +41 -48
- package/lib/error-handler.js +3 -3
- package/lib/errors.js +5 -0
- package/lib/handleRequest.js +13 -17
- package/lib/promise.js +23 -0
- package/lib/reply.js +17 -19
- package/lib/route.js +37 -3
- package/lib/server.js +36 -35
- package/lib/warnings.js +11 -1
- package/package.json +7 -7
- package/test/async-await.test.js +81 -134
- package/test/async_hooks.test.js +18 -37
- package/test/body-limit.test.js +51 -0
- package/test/buffer.test.js +22 -0
- package/test/case-insensitive.test.js +44 -65
- package/test/check.test.js +17 -21
- package/test/close-pipelining.test.js +24 -15
- package/test/constrained-routes.test.js +231 -0
- package/test/custom-http-server.test.js +7 -15
- package/test/custom-parser.0.test.js +267 -348
- package/test/custom-parser.1.test.js +141 -191
- package/test/custom-parser.2.test.js +34 -44
- package/test/custom-parser.3.test.js +56 -104
- package/test/custom-parser.4.test.js +106 -144
- package/test/custom-parser.5.test.js +56 -75
- package/test/custom-querystring-parser.test.js +51 -77
- package/test/decorator.test.js +76 -259
- package/test/delete.test.js +101 -110
- package/test/diagnostics-channel/404.test.js +7 -15
- package/test/diagnostics-channel/async-request.test.js +8 -16
- package/test/diagnostics-channel/error-request.test.js +7 -15
- package/test/diagnostics-channel/sync-request-reply.test.js +9 -16
- package/test/diagnostics-channel/sync-request.test.js +9 -16
- package/test/fastify-instance.test.js +1 -1
- package/test/header-overflow.test.js +18 -29
- package/test/helper.js +138 -134
- package/test/hooks-async.test.js +26 -32
- package/test/hooks.test.js +261 -447
- package/test/http-methods/copy.test.js +14 -19
- package/test/http-methods/get.test.js +131 -143
- package/test/http-methods/head.test.js +53 -84
- package/test/http-methods/mkcalendar.test.js +45 -72
- package/test/http-methods/move.test.js +6 -10
- package/test/http-methods/propfind.test.js +34 -44
- package/test/http-methods/unlock.test.js +5 -9
- package/test/http2/secure-with-fallback.test.js +3 -1
- package/test/https/custom-https-server.test.js +9 -13
- package/test/input-validation.js +139 -150
- package/test/internals/errors.test.js +50 -1
- package/test/internals/handle-request.test.js +29 -5
- package/test/internals/promise.test.js +63 -0
- package/test/internals/reply.test.js +277 -496
- package/test/plugin.1.test.js +40 -68
- package/test/plugin.2.test.js +40 -70
- package/test/plugin.3.test.js +25 -68
- package/test/promises.test.js +42 -63
- package/test/register.test.js +8 -18
- package/test/request-error.test.js +57 -100
- package/test/request-id.test.js +30 -49
- package/test/route-hooks.test.js +12 -16
- package/test/route-shorthand.test.js +9 -27
- package/test/route.1.test.js +74 -131
- package/test/route.8.test.js +9 -17
- package/test/router-options.test.js +450 -0
- package/test/schema-validation.test.js +30 -31
- package/test/server.test.js +143 -5
- package/test/stream.1.test.js +33 -50
- package/test/stream.4.test.js +18 -28
- package/test/stream.5.test.js +11 -19
- package/test/types/errors.test-d.ts +13 -1
- package/test/types/type-provider.test-d.ts +55 -0
- package/test/use-semicolon-delimiter.test.js +117 -59
- package/test/versioned-routes.test.js +39 -56
- package/types/errors.d.ts +11 -1
- package/types/hooks.d.ts +1 -1
- package/types/instance.d.ts +1 -1
- package/types/reply.d.ts +2 -2
package/test/helper.js
CHANGED
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
|
|
3
|
-
const sget = require('simple-get').concat
|
|
4
3
|
const dns = require('node:dns').promises
|
|
5
4
|
const stream = require('node:stream')
|
|
6
5
|
const { promisify } = require('node:util')
|
|
@@ -105,89 +104,85 @@ module.exports.payloadMethod = function (method, t, isSetErrorHandler = false) {
|
|
|
105
104
|
|
|
106
105
|
t.after(() => { fastify.close() })
|
|
107
106
|
|
|
108
|
-
test(`${upMethod} - correctly replies`, (t
|
|
107
|
+
test(`${upMethod} - correctly replies`, async (t) => {
|
|
109
108
|
t.plan(3)
|
|
110
|
-
|
|
109
|
+
|
|
110
|
+
const result = await fetch('http://localhost:' + fastify.server.address().port, {
|
|
111
111
|
method: upMethod,
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
}
|
|
116
|
-
json: true
|
|
117
|
-
}, (err, response, body) => {
|
|
118
|
-
t.assert.ifError(err)
|
|
119
|
-
t.assert.strictEqual(response.statusCode, 200)
|
|
120
|
-
t.assert.deepStrictEqual(body, { hello: 'world' })
|
|
121
|
-
testDone()
|
|
112
|
+
body: JSON.stringify({ hello: 'world' }),
|
|
113
|
+
headers: {
|
|
114
|
+
'Content-Type': 'application/json'
|
|
115
|
+
}
|
|
122
116
|
})
|
|
117
|
+
|
|
118
|
+
t.assert.ok(result.ok)
|
|
119
|
+
t.assert.strictEqual(result.status, 200)
|
|
120
|
+
t.assert.deepStrictEqual(await result.json(), { hello: 'world' })
|
|
123
121
|
})
|
|
124
122
|
|
|
125
|
-
test(`${upMethod} - correctly replies with very large body`, (t
|
|
123
|
+
test(`${upMethod} - correctly replies with very large body`, async (t) => {
|
|
126
124
|
t.plan(3)
|
|
127
125
|
|
|
128
126
|
const largeString = 'world'.repeat(13200)
|
|
129
|
-
|
|
127
|
+
const result = await fetch('http://localhost:' + fastify.server.address().port, {
|
|
130
128
|
method: upMethod,
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
t.assert.ifError(err)
|
|
136
|
-
t.assert.strictEqual(response.statusCode, 200)
|
|
137
|
-
t.assert.deepStrictEqual(body, { hello: largeString })
|
|
138
|
-
testDone()
|
|
129
|
+
body: JSON.stringify({ hello: largeString }),
|
|
130
|
+
headers: {
|
|
131
|
+
'Content-Type': 'application/json'
|
|
132
|
+
}
|
|
139
133
|
})
|
|
134
|
+
|
|
135
|
+
t.assert.ok(result.ok)
|
|
136
|
+
t.assert.strictEqual(result.status, 200)
|
|
137
|
+
t.assert.deepStrictEqual(await result.json(), { hello: largeString })
|
|
140
138
|
})
|
|
141
139
|
|
|
142
|
-
test(`${upMethod} - correctly replies if the content type has the charset`, (t
|
|
140
|
+
test(`${upMethod} - correctly replies if the content type has the charset`, async (t) => {
|
|
143
141
|
t.plan(3)
|
|
144
|
-
|
|
142
|
+
|
|
143
|
+
const result = await fetch('http://localhost:' + fastify.server.address().port, {
|
|
145
144
|
method: upMethod,
|
|
146
|
-
url: 'http://localhost:' + fastify.server.address().port,
|
|
147
145
|
body: JSON.stringify({ hello: 'world' }),
|
|
148
146
|
headers: {
|
|
149
147
|
'content-type': 'application/json; charset=utf-8'
|
|
150
148
|
}
|
|
151
|
-
}, (err, response, body) => {
|
|
152
|
-
t.assert.ifError(err)
|
|
153
|
-
t.assert.strictEqual(response.statusCode, 200)
|
|
154
|
-
t.assert.deepStrictEqual(body.toString(), JSON.stringify({ hello: 'world' }))
|
|
155
|
-
testDone()
|
|
156
149
|
})
|
|
150
|
+
|
|
151
|
+
t.assert.ok(result.ok)
|
|
152
|
+
t.assert.strictEqual(result.status, 200)
|
|
153
|
+
t.assert.deepStrictEqual(await result.text(), JSON.stringify({ hello: 'world' }))
|
|
157
154
|
})
|
|
158
155
|
|
|
159
|
-
test(`${upMethod} without schema - correctly replies`, (t
|
|
156
|
+
test(`${upMethod} without schema - correctly replies`, async (t) => {
|
|
160
157
|
t.plan(3)
|
|
161
|
-
|
|
158
|
+
|
|
159
|
+
const result = await fetch('http://localhost:' + fastify.server.address().port + '/missing', {
|
|
162
160
|
method: upMethod,
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
}
|
|
167
|
-
json: true
|
|
168
|
-
}, (err, response, body) => {
|
|
169
|
-
t.assert.ifError(err)
|
|
170
|
-
t.assert.strictEqual(response.statusCode, 200)
|
|
171
|
-
t.assert.deepStrictEqual(body, { hello: 'world' })
|
|
172
|
-
testDone()
|
|
161
|
+
body: JSON.stringify({ hello: 'world' }),
|
|
162
|
+
headers: {
|
|
163
|
+
'Content-Type': 'application/json'
|
|
164
|
+
}
|
|
173
165
|
})
|
|
166
|
+
|
|
167
|
+
t.assert.ok(result.ok)
|
|
168
|
+
t.assert.strictEqual(result.status, 200)
|
|
169
|
+
t.assert.deepStrictEqual(await result.json(), { hello: 'world' })
|
|
174
170
|
})
|
|
175
171
|
|
|
176
|
-
test(`${upMethod} with body and querystring - correctly replies`, (t
|
|
172
|
+
test(`${upMethod} with body and querystring - correctly replies`, async (t) => {
|
|
177
173
|
t.plan(3)
|
|
178
|
-
|
|
174
|
+
|
|
175
|
+
const result = await fetch('http://localhost:' + fastify.server.address().port + '/with-query?foo=hello', {
|
|
179
176
|
method: upMethod,
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
}
|
|
184
|
-
json: true
|
|
185
|
-
}, (err, response, body) => {
|
|
186
|
-
t.assert.ifError(err)
|
|
187
|
-
t.assert.strictEqual(response.statusCode, 200)
|
|
188
|
-
t.assert.deepStrictEqual(body, { hello: 'worldhello' })
|
|
189
|
-
testDone()
|
|
177
|
+
body: JSON.stringify({ hello: 'world' }),
|
|
178
|
+
headers: {
|
|
179
|
+
'Content-Type': 'application/json'
|
|
180
|
+
}
|
|
190
181
|
})
|
|
182
|
+
|
|
183
|
+
t.assert.ok(result.ok)
|
|
184
|
+
t.assert.strictEqual(result.status, 200)
|
|
185
|
+
t.assert.deepStrictEqual(await result.json(), { hello: 'worldhello' })
|
|
191
186
|
})
|
|
192
187
|
|
|
193
188
|
test(`${upMethod} with no body - correctly replies`, t => {
|
|
@@ -195,14 +190,13 @@ module.exports.payloadMethod = function (method, t, isSetErrorHandler = false) {
|
|
|
195
190
|
|
|
196
191
|
const { stepIn, patience } = waitForCb({ steps: 2 })
|
|
197
192
|
|
|
198
|
-
|
|
193
|
+
fetch('http://localhost:' + fastify.server.address().port + '/missing', {
|
|
199
194
|
method: upMethod,
|
|
200
|
-
url: 'http://localhost:' + fastify.server.address().port + '/missing',
|
|
201
195
|
headers: { 'Content-Length': '0' }
|
|
202
|
-
}
|
|
203
|
-
t.assert.
|
|
204
|
-
t.assert.strictEqual(response.
|
|
205
|
-
t.assert.strictEqual(
|
|
196
|
+
}).then(async (response) => {
|
|
197
|
+
t.assert.ok(response.ok)
|
|
198
|
+
t.assert.strictEqual(response.status, 200)
|
|
199
|
+
t.assert.strictEqual(await response.text(), '')
|
|
206
200
|
stepIn()
|
|
207
201
|
})
|
|
208
202
|
|
|
@@ -220,88 +214,95 @@ module.exports.payloadMethod = function (method, t, isSetErrorHandler = false) {
|
|
|
220
214
|
return patience
|
|
221
215
|
})
|
|
222
216
|
|
|
223
|
-
test(`${upMethod} returns 415 - incorrect media type if body is not json`, (t
|
|
217
|
+
test(`${upMethod} returns 415 - incorrect media type if body is not json`, async (t) => {
|
|
224
218
|
t.plan(2)
|
|
225
|
-
sget({
|
|
226
|
-
method: upMethod,
|
|
227
|
-
url: 'http://localhost:' + fastify.server.address().port + '/missing',
|
|
228
|
-
body: 'hello world'
|
|
229
219
|
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
220
|
+
const result = await fetch('http://localhost:' + fastify.server.address().port + '/missing', {
|
|
221
|
+
method: upMethod,
|
|
222
|
+
body: 'hello world',
|
|
223
|
+
headers: {
|
|
224
|
+
'Content-Type': undefined
|
|
225
|
+
}
|
|
234
226
|
})
|
|
227
|
+
|
|
228
|
+
t.assert.ok(!result.ok)
|
|
229
|
+
t.assert.strictEqual(result.status, 415)
|
|
235
230
|
})
|
|
236
231
|
|
|
237
232
|
if (loMethod === 'options') {
|
|
238
|
-
test('OPTIONS returns 415 - should return 415 if Content-Type is not json or plain text', (t
|
|
233
|
+
test('OPTIONS returns 415 - should return 415 if Content-Type is not json or plain text', async (t) => {
|
|
239
234
|
t.plan(2)
|
|
240
|
-
|
|
235
|
+
|
|
236
|
+
const result = await fetch('http://localhost:' + fastify.server.address().port + '/missing', {
|
|
241
237
|
method: upMethod,
|
|
242
|
-
url: 'http://localhost:' + fastify.server.address().port + '/missing',
|
|
243
238
|
body: 'hello world',
|
|
244
239
|
headers: {
|
|
245
240
|
'Content-Type': 'text/xml'
|
|
246
241
|
}
|
|
247
|
-
}, (err, response, body) => {
|
|
248
|
-
t.assert.ifError(err)
|
|
249
|
-
t.assert.strictEqual(response.statusCode, 415)
|
|
250
|
-
testDone()
|
|
251
242
|
})
|
|
243
|
+
|
|
244
|
+
t.assert.ok(!result.ok)
|
|
245
|
+
t.assert.strictEqual(result.status, 415)
|
|
252
246
|
})
|
|
253
247
|
}
|
|
254
248
|
|
|
255
249
|
test(`${upMethod} returns 400 - Bad Request`, t => {
|
|
256
|
-
|
|
250
|
+
const isOptions = upMethod === 'OPTIONS'
|
|
251
|
+
t.plan(isOptions ? 2 : 4)
|
|
257
252
|
|
|
258
|
-
const { stepIn, patience } = waitForCb({ steps: 2 })
|
|
253
|
+
const { stepIn, patience } = waitForCb({ steps: isOptions ? 1 : 2 })
|
|
259
254
|
|
|
260
|
-
|
|
255
|
+
fetch('http://localhost:' + fastify.server.address().port, {
|
|
261
256
|
method: upMethod,
|
|
262
|
-
url: 'http://localhost:' + fastify.server.address().port,
|
|
263
257
|
body: 'hello world',
|
|
264
258
|
headers: {
|
|
265
259
|
'Content-Type': 'application/json'
|
|
266
260
|
}
|
|
267
|
-
}
|
|
268
|
-
t.assert.
|
|
269
|
-
t.assert.strictEqual(response.
|
|
261
|
+
}).then((response) => {
|
|
262
|
+
t.assert.ok(!response.ok)
|
|
263
|
+
t.assert.strictEqual(response.status, 400)
|
|
270
264
|
stepIn()
|
|
271
265
|
})
|
|
272
266
|
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
267
|
+
if (!isOptions) {
|
|
268
|
+
fetch(`http://localhost:${fastify.server.address().port}`, {
|
|
269
|
+
method: upMethod,
|
|
270
|
+
headers: {
|
|
271
|
+
'Content-Type': 'application/json',
|
|
272
|
+
'Content-Length': '0'
|
|
273
|
+
}
|
|
274
|
+
}).then((response) => {
|
|
275
|
+
t.assert.ok(!response.ok)
|
|
276
|
+
t.assert.strictEqual(response.status, 400)
|
|
277
|
+
stepIn()
|
|
278
|
+
})
|
|
279
|
+
}
|
|
285
280
|
|
|
286
281
|
return patience
|
|
287
282
|
})
|
|
288
283
|
|
|
289
284
|
test(`${upMethod} returns 413 - Payload Too Large`, t => {
|
|
290
285
|
const isOptions = upMethod === 'OPTIONS'
|
|
291
|
-
t.plan(isOptions ?
|
|
286
|
+
t.plan(isOptions ? 3 : 5)
|
|
292
287
|
|
|
293
288
|
const { stepIn, patience } = waitForCb({ steps: isOptions ? 2 : 3 })
|
|
294
289
|
|
|
295
|
-
|
|
290
|
+
fetch(`http://localhost:${fastify.server.address().port}`, {
|
|
296
291
|
method: upMethod,
|
|
297
|
-
|
|
292
|
+
body: JSON.stringify({ w: 'w'.repeat(1024 * 1024 + 1) }),
|
|
298
293
|
headers: {
|
|
299
|
-
'Content-Type': 'application/json'
|
|
300
|
-
|
|
294
|
+
'Content-Type': 'application/json'
|
|
295
|
+
}
|
|
296
|
+
}).then((response) => {
|
|
297
|
+
t.assert.strictEqual(response.status, 413)
|
|
298
|
+
stepIn()
|
|
299
|
+
}).catch((err) => {
|
|
300
|
+
// Handle EPIPE error - server closed connection after sending 413
|
|
301
|
+
if (err.cause?.code === 'EPIPE' || err.message.includes('fetch failed')) {
|
|
302
|
+
t.assert.ok(true, 'Expected EPIPE error due to server closing connection on 413')
|
|
303
|
+
} else {
|
|
304
|
+
throw err
|
|
301
305
|
}
|
|
302
|
-
}, (err, response, body) => {
|
|
303
|
-
t.assert.ifError(err)
|
|
304
|
-
t.assert.strictEqual(response.statusCode, 413)
|
|
305
306
|
stepIn()
|
|
306
307
|
})
|
|
307
308
|
|
|
@@ -314,27 +315,33 @@ module.exports.payloadMethod = function (method, t, isSetErrorHandler = false) {
|
|
|
314
315
|
chunk = null
|
|
315
316
|
}
|
|
316
317
|
})
|
|
317
|
-
|
|
318
|
+
fetch('http://localhost:' + fastify.server.address().port, {
|
|
318
319
|
method: upMethod,
|
|
319
|
-
url: 'http://localhost:' + fastify.server.address().port,
|
|
320
320
|
headers: { 'Content-Type': 'application/json' },
|
|
321
|
-
body: largeStream
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
t.assert.
|
|
321
|
+
body: largeStream,
|
|
322
|
+
duplex: 'half'
|
|
323
|
+
}).then((response) => {
|
|
324
|
+
t.assert.ok(!response.ok)
|
|
325
|
+
t.assert.strictEqual(response.status, 413)
|
|
326
|
+
stepIn()
|
|
327
|
+
}).catch((err) => {
|
|
328
|
+
// Handle EPIPE error - server closed connection after sending 413
|
|
329
|
+
if (err.cause?.code === 'EPIPE' || err.message.includes('fetch failed')) {
|
|
330
|
+
t.assert.ok(true, 'Expected EPIPE error due to server closing connection on 413')
|
|
331
|
+
} else {
|
|
332
|
+
throw err
|
|
333
|
+
}
|
|
325
334
|
stepIn()
|
|
326
335
|
})
|
|
327
336
|
}
|
|
328
337
|
|
|
329
|
-
|
|
338
|
+
fetch(`http://localhost:${fastify.server.address().port}/with-limit`, {
|
|
330
339
|
method: upMethod,
|
|
331
|
-
url: `http://localhost:${fastify.server.address().port}/with-limit`,
|
|
332
340
|
headers: { 'Content-Type': 'application/json' },
|
|
333
|
-
body: {}
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
t.assert.
|
|
337
|
-
t.assert.strictEqual(response.statusCode, 413)
|
|
341
|
+
body: JSON.stringify({})
|
|
342
|
+
}).then((response) => {
|
|
343
|
+
t.assert.ok(!response.ok)
|
|
344
|
+
t.assert.strictEqual(response.status, 413)
|
|
338
345
|
stepIn()
|
|
339
346
|
})
|
|
340
347
|
|
|
@@ -364,15 +371,14 @@ module.exports.payloadMethod = function (method, t, isSetErrorHandler = false) {
|
|
|
364
371
|
})
|
|
365
372
|
})
|
|
366
373
|
|
|
367
|
-
|
|
374
|
+
fetch(`http://localhost:${fastify.server.address().port}`, {
|
|
368
375
|
method: upMethod,
|
|
369
|
-
url: `http://localhost:${fastify.server.address().port}`,
|
|
370
376
|
headers: {
|
|
371
377
|
'Content-Type': 'application/json'
|
|
372
378
|
}
|
|
373
|
-
}
|
|
374
|
-
t.assert.
|
|
375
|
-
t.assert.deepStrictEqual(
|
|
379
|
+
}).then(async (res) => {
|
|
380
|
+
t.assert.ok(!res.ok)
|
|
381
|
+
t.assert.deepStrictEqual(await res.json(), {
|
|
376
382
|
error: 'Bad Request',
|
|
377
383
|
code: 'FST_ERR_CTP_EMPTY_JSON_BODY',
|
|
378
384
|
message: 'Body cannot be empty when content-type is set to \'application/json\'',
|
|
@@ -399,16 +405,15 @@ module.exports.payloadMethod = function (method, t, isSetErrorHandler = false) {
|
|
|
399
405
|
stepIn()
|
|
400
406
|
})
|
|
401
407
|
|
|
402
|
-
|
|
408
|
+
fetch(`http://localhost:${fastify.server.address().port}`, {
|
|
403
409
|
method: upMethod,
|
|
404
|
-
url: `http://localhost:${fastify.server.address().port}`,
|
|
405
410
|
headers: {
|
|
406
411
|
'Content-Type': 'application/json'
|
|
407
412
|
},
|
|
408
|
-
|
|
409
|
-
}
|
|
410
|
-
t.assert.
|
|
411
|
-
t.assert.deepStrictEqual(
|
|
413
|
+
body: null
|
|
414
|
+
}).then(async (res) => {
|
|
415
|
+
t.assert.ok(!res.ok)
|
|
416
|
+
t.assert.deepStrictEqual(await res.json(), {
|
|
412
417
|
error: 'Bad Request',
|
|
413
418
|
code: 'FST_ERR_CTP_EMPTY_JSON_BODY',
|
|
414
419
|
message: 'Body cannot be empty when content-type is set to \'application/json\'',
|
|
@@ -435,16 +440,15 @@ module.exports.payloadMethod = function (method, t, isSetErrorHandler = false) {
|
|
|
435
440
|
stepIn()
|
|
436
441
|
})
|
|
437
442
|
|
|
438
|
-
|
|
443
|
+
fetch(`http://localhost:${fastify.server.address().port}`, {
|
|
439
444
|
method: upMethod,
|
|
440
|
-
url: `http://localhost:${fastify.server.address().port}`,
|
|
441
445
|
headers: {
|
|
442
446
|
'Content-Type': 'application/json'
|
|
443
447
|
},
|
|
444
|
-
|
|
445
|
-
}
|
|
446
|
-
t.assert.
|
|
447
|
-
t.assert.deepStrictEqual(
|
|
448
|
+
body: undefined
|
|
449
|
+
}).then(async (res) => {
|
|
450
|
+
t.assert.ok(!res.ok)
|
|
451
|
+
t.assert.deepStrictEqual(await res.json(), {
|
|
448
452
|
error: 'Bad Request',
|
|
449
453
|
code: 'FST_ERR_CTP_EMPTY_JSON_BODY',
|
|
450
454
|
message: 'Body cannot be empty when content-type is set to \'application/json\'',
|
package/test/hooks-async.test.js
CHANGED
|
@@ -2,7 +2,6 @@
|
|
|
2
2
|
|
|
3
3
|
const { Readable } = require('node:stream')
|
|
4
4
|
const { test, describe } = require('node:test')
|
|
5
|
-
const sget = require('simple-get').concat
|
|
6
5
|
const Fastify = require('../fastify')
|
|
7
6
|
const fs = require('node:fs')
|
|
8
7
|
const { sleep } = require('./helper')
|
|
@@ -10,8 +9,8 @@ const { waitForCb } = require('./toolkit')
|
|
|
10
9
|
|
|
11
10
|
process.removeAllListeners('warning')
|
|
12
11
|
|
|
13
|
-
test('async hooks', t => {
|
|
14
|
-
t.plan(
|
|
12
|
+
test('async hooks', async t => {
|
|
13
|
+
t.plan(20)
|
|
15
14
|
const fastify = Fastify({ exposeHeadRoutes: false })
|
|
16
15
|
fastify.addHook('onRequest', async function (request, reply) {
|
|
17
16
|
await sleep(1)
|
|
@@ -59,37 +58,32 @@ test('async hooks', t => {
|
|
|
59
58
|
reply.code(200).send({ hello: 'world' })
|
|
60
59
|
})
|
|
61
60
|
|
|
62
|
-
fastify.listen({ port: 0 }
|
|
63
|
-
|
|
64
|
-
t.after(() => { fastify.close() })
|
|
61
|
+
const fastifyServer = await fastify.listen({ port: 0 })
|
|
62
|
+
t.after(() => { fastify.close() })
|
|
65
63
|
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
method: 'DELETE',
|
|
86
|
-
url: 'http://localhost:' + fastify.server.address().port
|
|
87
|
-
}, (err, response, body) => {
|
|
88
|
-
t.assert.ifError(err)
|
|
89
|
-
t.assert.strictEqual(response.statusCode, 500)
|
|
90
|
-
completion.stepIn()
|
|
91
|
-
})
|
|
64
|
+
const response1 = await fetch(fastifyServer, {
|
|
65
|
+
method: 'GET'
|
|
66
|
+
})
|
|
67
|
+
t.assert.ok(response1.ok)
|
|
68
|
+
t.assert.strictEqual(response1.status, 200)
|
|
69
|
+
const body1 = await response1.text()
|
|
70
|
+
t.assert.strictEqual(response1.headers.get('content-length'), '' + body1.length)
|
|
71
|
+
t.assert.deepStrictEqual(JSON.parse(body1), { hello: 'world' })
|
|
72
|
+
completion.stepIn()
|
|
73
|
+
|
|
74
|
+
const response2 = await fetch(fastifyServer, {
|
|
75
|
+
method: 'HEAD'
|
|
76
|
+
})
|
|
77
|
+
t.assert.ok(!response2.ok)
|
|
78
|
+
t.assert.strictEqual(response2.status, 500)
|
|
79
|
+
completion.stepIn()
|
|
80
|
+
|
|
81
|
+
const response3 = await fetch(fastifyServer, {
|
|
82
|
+
method: 'DELETE'
|
|
92
83
|
})
|
|
84
|
+
t.assert.ok(!response3.ok)
|
|
85
|
+
t.assert.strictEqual(response3.status, 500)
|
|
86
|
+
completion.stepIn()
|
|
93
87
|
|
|
94
88
|
return completion.patience
|
|
95
89
|
})
|