From fda6664e72bc18b9463f6c46ee73d598f40fb538 Mon Sep 17 00:00:00 2001 From: Luca Becker Date: Sun, 7 Feb 2021 10:08:53 +0100 Subject: [PATCH] feat(platform-express): Allowing pipes for FileInterceptor https://github.com/nestjs/nest/issues/4752 --- .../multer/interceptors/file.interceptor.ts | 17 ++++++++++ .../interceptors/file.interceptor.spec.ts | 33 ++++++++++++++++++- 2 files changed, 49 insertions(+), 1 deletion(-) diff --git a/packages/platform-express/multer/interceptors/file.interceptor.ts b/packages/platform-express/multer/interceptors/file.interceptor.ts index 6261c23cb06..b94f1c11038 100644 --- a/packages/platform-express/multer/interceptors/file.interceptor.ts +++ b/packages/platform-express/multer/interceptors/file.interceptor.ts @@ -5,6 +5,7 @@ import { mixin, NestInterceptor, Optional, + PipeTransform, Type, } from '@nestjs/common'; import * as multer from 'multer'; @@ -19,6 +20,7 @@ type MulterInstance = any; export function FileInterceptor( fieldName: string, localOptions?: MulterOptions, + ...pipes: (Type | PipeTransform)[] ): Type { class MixinInterceptor implements NestInterceptor { protected multer: MulterInstance; @@ -49,6 +51,21 @@ export function FileInterceptor( const error = transformException(err); return reject(error); } + + if (pipes.length > 0) { + const request = ctx.getRequest(); + request.file = pipes.reduce( + (previousFile, Pipe: Type | PipeTransform) => { + const pipeInstance: PipeTransform = + typeof Pipe === 'function' ? new Pipe() : Pipe; + return pipeInstance.transform(previousFile, { + type: 'custom', + }); + }, + request.file, + ); + } + resolve(); }, ), diff --git a/packages/platform-express/test/multer/interceptors/file.interceptor.spec.ts b/packages/platform-express/test/multer/interceptors/file.interceptor.spec.ts index 39f003e1465..0a125c1201c 100644 --- a/packages/platform-express/test/multer/interceptors/file.interceptor.spec.ts +++ b/packages/platform-express/test/multer/interceptors/file.interceptor.spec.ts @@ -1,10 +1,14 @@ -import { CallHandler } from '@nestjs/common'; +import { CallHandler, PipeTransform } from '@nestjs/common'; import { ExecutionContextHost } from '@nestjs/core/helpers/execution-context-host'; import { expect } from 'chai'; import { of } from 'rxjs'; import * as sinon from 'sinon'; import { FileInterceptor } from '../../../multer/interceptors/file.interceptor'; +const createFilePipe = (): PipeTransform => ({ + transform: (): any => undefined, +}); + describe('FileInterceptor', () => { it('should return metatype with expected structure', async () => { const targetClass = FileInterceptor('file'); @@ -42,5 +46,32 @@ describe('FileInterceptor', () => { error => expect(error).to.not.be.undefined, ); }); + it('should accept pipes and call them', async () => { + const fieldName = 'file'; + const pipe = createFilePipe(); + const secondPipe = createFilePipe(); + const myFakeFile: any = {}; + const transformSpy = sinon.stub(pipe, 'transform').returns(myFakeFile); + const secondTransformSpy = sinon + .stub(secondPipe, 'transform') + .returns(undefined); + const target = new (FileInterceptor( + fieldName, + undefined, + pipe, + secondPipe, + ))(); + const callback = (req, res, next) => next(); + sinon.stub((target as any).multer, 'single').returns(callback); + + await target.intercept( + new ExecutionContextHost([{ file: myFakeFile }]), + handler, + ); + + expect(transformSpy.called).to.be.true; + expect(transformSpy.calledWith(myFakeFile)).to.be.true; + expect(secondTransformSpy.called).to.be.true; + }); }); });