export type MiddlewareExchange = (req: T) => Promise; export type RequestMiddleware = (req: T) => Promise; export type ResultMiddleware = (res: T) => Promise; export class MiddlewareChain { middlewareChain: MiddlewareExchange; constructor(requestChain: MiddlewareExchange) { this.middlewareChain = requestChain; } prepend(middleware: RequestMiddleware): void { this.middlewareChain = ((prev) => async (req: T) => { return prev(await middleware(req)); })(this.middlewareChain); } append(middleware: ResultMiddleware): void { this.middlewareChain = ((next) => async (req: T) => { return middleware(await next(req)); })(this.middlewareChain); } async request(req: T): Promise { return this.middlewareChain(req); } }