From feeeaa6ef9f76d67f85b25f4d243b27ceb00360b Mon Sep 17 00:00:00 2001 From: fergusean Date: Thu, 2 May 2024 03:52:26 -0400 Subject: [PATCH] fix(http): support for JSON array payloads (#564) --- packages/http/src/request-parser.ts | 9 ++++++++- packages/http/tests/router.spec.ts | 12 ++++++++++++ 2 files changed, 20 insertions(+), 1 deletion(-) diff --git a/packages/http/src/request-parser.ts b/packages/http/src/request-parser.ts index 896835eed..12de43233 100644 --- a/packages/http/src/request-parser.ts +++ b/packages/http/src/request-parser.ts @@ -39,7 +39,14 @@ function parseBody( if (err) { reject(err); } else { - for (const [name, file] of Object.entries(files) as any) { + const fileEntries = Object.entries(files); + + // formidable turns JSON arrays into numerically keyed objects, so we convert them back + if ('0' in fields && fileEntries.length === 0 && Object.keys(fields).every((key, idx) => parseInt(key) === idx)) { + return resolve(Object.values(fields)); + } + + for (const [name, file] of fileEntries as any) { if (!file.filepath || 'string' !== typeof file.filepath) continue; if (!file.size || 'number' !== typeof file.size) continue; if (file.lastModifiedDate && !(file.lastModifiedDate instanceof Date)) continue; diff --git a/packages/http/tests/router.spec.ts b/packages/http/tests/router.spec.ts index a0312a15e..8c5bd4f65 100644 --- a/packages/http/tests/router.spec.ts +++ b/packages/http/tests/router.spec.ts @@ -945,6 +945,15 @@ test('BodyValidation', async () => { throw new HttpBadRequestError('Invalid: ' + user.error.getErrorMessageForPath('username')); } + + @http.POST('/action4') + action4(users: HttpBodyValidation): User[] { + if (users.valid()) { + return users.value; + } + + throw new HttpBadRequestError('Invalid: ' + users.error.getErrorMessageForPath('0.username')); + } } const httpKernel = createHttpKernel([Controller]); @@ -958,6 +967,9 @@ test('BodyValidation', async () => { expect((await httpKernel.request(HttpRequest.POST('/action3').json({ username: 'Peter' }))).json).toEqual({ username: 'Peter' }); expect((await httpKernel.request(HttpRequest.POST('/action3').json({ username: 'Pe' }))).json.message).toEqual('Invalid: username(minLength): Min length is 3 caused by value "Pe"'); + + expect((await httpKernel.request(HttpRequest.POST('/action4').json([{ username: 'Peter' }]))).json).toEqual([{ username: 'Peter' }]); + expect((await httpKernel.request(HttpRequest.POST('/action4').json([{ username: 'Pe' }]))).json.message).toEqual('Invalid: 0.username(minLength): Min length is 3 caused by value "Pe"'); }); test('unpopulated entity without type information', async () => {