From d3713087cc2f7d2f96140c771b7fc7646cd30df8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tyll=20Wei=C3=9F?= Date: Fri, 13 Nov 2020 10:47:53 +0100 Subject: [PATCH] feat: provide controller result to PostProcessor functions --- src/decorators/services.ts | 6 +++--- src/server/model/metadata.ts | 10 +++++----- src/server/model/server-types.ts | 3 ++- src/server/service-invoker.ts | 12 ++++++------ test/integration/postprocessor.spec.ts | 12 ++++++++++++ 5 files changed, 28 insertions(+), 15 deletions(-) diff --git a/src/decorators/services.ts b/src/decorators/services.ts index 1e395f7..a8fd6ea 100644 --- a/src/decorators/services.ts +++ b/src/decorators/services.ts @@ -3,7 +3,7 @@ import * as _ from 'lodash'; import 'reflect-metadata'; import { ServiceClass, ServiceMethod } from '../server/model/metadata'; -import { ParserType, ServiceProcessor } from '../server/model/server-types'; +import { ParserType, ServicePostProcessor, ServicePreProcessor } from '../server/model/server-types'; import { ServerContainer } from '../server/server-container'; /** @@ -108,7 +108,7 @@ export function Security(roles?: string | Array, name?: string) { * } * ``` */ -export function PreProcessor(preprocessor: ServiceProcessor) { +export function PreProcessor(preprocessor: ServicePreProcessor) { return new ProcessorServiceDecorator('PreProcessor') .withArrayProperty('preProcessors', preprocessor, true) .createDecorator(); @@ -140,7 +140,7 @@ export function PreProcessor(preprocessor: ServiceProcessor) { * } * ``` */ -export function PostProcessor(postprocessor: ServiceProcessor) { +export function PostProcessor(postprocessor: ServicePostProcessor) { return new ProcessorServiceDecorator('PostProcessor') .withArrayProperty('postProcessors', postprocessor, true) .createDecorator(); diff --git a/src/server/model/metadata.ts b/src/server/model/metadata.ts index 122208b..53da2f5 100644 --- a/src/server/model/metadata.ts +++ b/src/server/model/metadata.ts @@ -1,6 +1,6 @@ 'use strict'; -import { HttpMethod, ParserType, ServiceProcessor } from './server-types'; +import { HttpMethod, ParserType, ServicePreProcessor, ServicePostProcessor } from './server-types'; export interface ServiceProperty { type: ParamType; @@ -18,8 +18,8 @@ export class ServiceClass { public path: string; public roles: Array; public authenticator: string; - public preProcessors: Array; - public postProcessors: Array; + public preProcessors: Array; + public postProcessors: Array; public methods: Map; public bodyParserOptions: any; public bodyParserType: ParserType; @@ -67,8 +67,8 @@ export class ServiceMethod { public accepts: Array; public resolvedLanguages: Array; public resolvedAccepts: Array; - public preProcessors: Array; - public postProcessors: Array; + public preProcessors: Array; + public postProcessors: Array; public ignoreNextMiddlewares: boolean = false; } diff --git a/src/server/model/server-types.ts b/src/server/model/server-types.ts index a2f80f1..367171d 100644 --- a/src/server/model/server-types.ts +++ b/src/server/model/server-types.ts @@ -114,7 +114,8 @@ export interface ServiceAuthenticator { getMiddleware(): express.RequestHandler; } -export type ServiceProcessor = (req: express.Request, res?: express.Response) => void; +export type ServicePreProcessor = (req: express.Request, res?: express.Response) => void; +export type ServicePostProcessor = (req: express.Request, res?: express.Response, result?: any) => void; export type ParameterConverter = (paramValue: any) => any; /** diff --git a/src/server/service-invoker.ts b/src/server/service-invoker.ts index 95f0099..bb09da5 100644 --- a/src/server/service-invoker.ts +++ b/src/server/service-invoker.ts @@ -6,15 +6,15 @@ import * as _ from 'lodash'; import { Errors } from '../typescript-rest'; import { ServiceClass, ServiceMethod, ServiceProperty } from './model/metadata'; import { DownloadBinaryData, DownloadResource, NoResponse } from './model/return-types'; -import { HttpMethod, ReferencedResource, ServiceContext, ServiceProcessor } from './model/server-types'; +import { HttpMethod, ReferencedResource, ServiceContext, ServicePostProcessor, ServicePreProcessor } from './model/server-types'; import { ParameterProcessor } from './parameter-processor'; import { ServerContainer } from './server-container'; export class ServiceInvoker { private serviceClass: ServiceClass; private serviceMethod: ServiceMethod; - private preProcessors: Array; - private postProcessors: Array; + private preProcessors: Array; + private postProcessors: Array; private debugger = debug('typescript-rest:service-invoker:runtime'); constructor(serviceClass: ServiceClass, serviceMethod: ServiceMethod) { @@ -50,10 +50,10 @@ export class ServiceInvoker { } } - private async runPostProcessors(context: ServiceContext): Promise { + private async runPostProcessors(context: ServiceContext, result: any): Promise { this.debugger('Running postprocessors'); for (const processor of this.postProcessors) { - await Promise.resolve(processor(context.request, context.response)); + await Promise.resolve(processor(context.request, context.response, result)); } } @@ -71,7 +71,7 @@ export class ServiceInvoker { } const result = await toCall.apply(serviceObject, args); if (this.postProcessors.length) { - await this.runPostProcessors(context); + await this.runPostProcessors(context, result); } this.processResponseHeaders(context); await this.sendValue(result, context); diff --git a/test/integration/postprocessor.spec.ts b/test/integration/postprocessor.spec.ts index 58f5bbb..8df49ec 100644 --- a/test/integration/postprocessor.spec.ts +++ b/test/integration/postprocessor.spec.ts @@ -5,9 +5,11 @@ import * as express from 'express'; import * as _ from 'lodash'; import 'mocha'; import * as request from 'request'; +import * as sinon from 'sinon'; import { Path, POST, PostProcessor, Server } from '../../src/typescript-rest'; const expect = chai.expect; +const postprocessorSpy = sinon.spy(); @Path('postprocessor') @PostProcessor(postprocessor1) @@ -15,6 +17,7 @@ export class PostProcessedService { @Path('test') @POST @PostProcessor(postprocessor2) + @PostProcessor(postprocessorSpy) public test() { return 'OK'; } @@ -65,6 +68,15 @@ describe('Postprocessor Tests', () => { done(); }); }); + it('should pass the controller result to the processor', (done) => { + request.post({ + headers: { 'content-type': 'application/json' }, + url: 'http://localhost:5674/postprocessor/test' + }, (error, response, body) => { + expect(postprocessorSpy).to.be.calledWith(sinon.match({}), sinon.match({}) , 'OK'); + done(); + }); + }); }); describe('Assynchronous Postprocessors', () => {