Skip to content

Commit

Permalink
Merge pull request #202 from LenKlose/feature/on-prem-middleware
Browse files Browse the repository at this point in the history
Add contextMiddlewareFactoryWithFixedSystemBaseUri-function
  • Loading branch information
LenKlose authored Jun 7, 2024
2 parents b0b9d83 + e28a5c5 commit 962ace3
Show file tree
Hide file tree
Showing 3 changed files with 175 additions and 74 deletions.
2 changes: 1 addition & 1 deletion packages/express-utils/package.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
{
"name": "@dvelop-sdk/express-utils",
"description": "This package contains middleware-functions for the express-framework and d.velop app-building.",
"version": "1.1.8",
"version": "1.2.0",
"license": "Apache-2.0",
"main": "lib/index.js",
"types": "lib/index.d.ts",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,44 +30,110 @@ describe("contextMiddlewareFactory", () => {
mockRes = {} as unknown as Response;
});

it("should set context", () => {
describe("dvelopContext", () => {
it("should set context from headers on no systemBaseUri", () => {

const systemBaseUri: string = "HiItsMeSystemBaseUri";
const tenantId: string = "HiItsMeTenantId";
const requestId: string = "HiItsMeRequestId";
const requestSignature: string = "HiItsMeRequestSignature";
const systemBaseUri: string = "HiItsMeSystemBaseUri";
const tenantId: string = "HiItsMeTenantId";
const requestId: string = "HiItsMeRequestId";
const requestSignature: string = "HiItsMeRequestSignature";

(mockReq.header as jest.Mock).mockImplementation((header: string) => {
switch (header) {
case DVELOP_SYSTEM_BASE_URI_HEADER:
return systemBaseUri;
(mockReq.header as jest.Mock).mockImplementation((header: string) => {
switch (header) {
case DVELOP_SYSTEM_BASE_URI_HEADER:
return systemBaseUri;

case DVELOP_TENANT_ID_HEADER:
return tenantId;
case DVELOP_TENANT_ID_HEADER:
return tenantId;

case DVELOP_REQUEST_ID_HEADER:
return requestId;
case DVELOP_REQUEST_ID_HEADER:
return requestId;

case DVELOP_REQUEST_SIGNATURE_HEADER:
return requestSignature;
case DVELOP_REQUEST_SIGNATURE_HEADER:
return requestSignature;

case TRACEPARENT_HEADER:
return undefined;
case TRACEPARENT_HEADER:
return undefined;

default:
throw "No other should be requested";
}
});

contextMiddlewareFactory(mockParseTraceparentHeader, mockGenerateTraceContext)(mockReq, mockRes, mockNext);

default:
throw "No other should be requested";
}
expect(mockReq.dvelopContext).toEqual(expect.objectContaining({
systemBaseUri: systemBaseUri,
tenantId: tenantId,
requestId: requestId,
requestSignature: requestSignature,
traceContext: undefined
}));
});

contextMiddlewareFactory(mockParseTraceparentHeader, mockGenerateTraceContext)(mockReq, mockRes, mockNext);
it("should not set systemBaseUri and tenantId from input if provided", () => {

const systemBaseUri: string = "HiItsMeSystemBaseUri";
const tenantId: string = "HiItsMeTenantId";
const requestId: string = "HiItsMeRequestId";

(mockReq.header as jest.Mock).mockImplementation((header: string) => {
switch (header) {

case DVELOP_REQUEST_ID_HEADER:
return requestId;

case TRACEPARENT_HEADER:
return undefined;

default:
throw "No other should be requested";
}
});

contextMiddlewareFactory(mockParseTraceparentHeader, mockGenerateTraceContext, systemBaseUri, tenantId)(mockReq, mockRes, mockNext);

expect(mockReq.dvelopContext).toEqual(expect.objectContaining({
systemBaseUri: systemBaseUri,
tenantId: tenantId,
requestId: requestId,
traceContext: undefined
}));
});

it("should set systemBaseUri from input and tenantId from headers if only systemBaseUri is provided", () => {

const systemBaseUri: string = "HiItsMeSystemBaseUri";
const tenantId: string = "HiItsMeTenantId";
const requestId: string = "HiItsMeRequestId";
const requestSignature: string = "HiItsMeRequestSignature";

(mockReq.header as jest.Mock).mockImplementation((header: string) => {
switch (header) {

case DVELOP_TENANT_ID_HEADER:
return tenantId;

case DVELOP_REQUEST_ID_HEADER:
return requestId;

case TRACEPARENT_HEADER:
return undefined;

expect(mockReq.dvelopContext).toEqual(expect.objectContaining({
systemBaseUri: systemBaseUri,
tenantId: tenantId,
requestId: requestId,
requestSignature: requestSignature,
traceContext: undefined
}));
default:
throw "No other should be requested";
}
});

contextMiddlewareFactory(mockParseTraceparentHeader, mockGenerateTraceContext, systemBaseUri)(mockReq, mockRes, mockNext);

expect(mockReq.dvelopContext).toEqual(expect.objectContaining({
systemBaseUri: systemBaseUri,
tenantId: tenantId,
requestId: requestId,
traceContext: undefined
}));
});
});

describe("traceContext", () => {
Expand All @@ -79,10 +145,10 @@ describe("contextMiddlewareFactory", () => {

(mockReq.header as jest.Mock).mockImplementation((header: string) => {
switch (header) {
case TRACEPARENT_HEADER:
return traceparentHeader;
default:
return "HiItsMeHeader";
case TRACEPARENT_HEADER:
return traceparentHeader;
default:
return "HiItsMeHeader";
}
});

Expand All @@ -92,52 +158,53 @@ describe("contextMiddlewareFactory", () => {
expect(mockParseTraceparentHeader).toHaveBeenCalledWith(traceparentHeader);
expect(mockGenerateTraceContext).toHaveBeenCalledTimes(0);
});
});

it("should generate traceContext on no traceparent-header", () => {
it("should generate traceContext on no traceparent-header", () => {

const traceContext: TraceContext = { traceId: "traceId" } as TraceContext;
mockGenerateTraceContext.mockReturnValue(traceContext);

(mockReq.header as jest.Mock).mockImplementation((header: string) => {
switch (header) {
case TRACEPARENT_HEADER:
return undefined;
default:
return "HiItsMeHeader";
}
});

const traceContext: TraceContext = { traceId: "traceId" } as TraceContext;
mockGenerateTraceContext.mockReturnValue(traceContext);
contextMiddlewareFactory(mockParseTraceparentHeader, mockGenerateTraceContext)(mockReq, mockRes, mockNext);

(mockReq.header as jest.Mock).mockImplementation((header: string) => {
switch (header) {
case TRACEPARENT_HEADER:
return undefined;
default:
return "HiItsMeHeader";
}
expect(mockReq.dvelopContext.traceContext).toEqual(traceContext);
expect(mockParseTraceparentHeader).toHaveBeenCalledTimes(0);
expect(mockGenerateTraceContext).toHaveBeenCalledTimes(1);
});

contextMiddlewareFactory(mockParseTraceparentHeader, mockGenerateTraceContext)(mockReq, mockRes, mockNext);
it("should generate traceContext on traceparent-header parsing error", () => {

expect(mockReq.dvelopContext.traceContext).toEqual(traceContext);
expect(mockParseTraceparentHeader).toHaveBeenCalledTimes(0);
expect(mockGenerateTraceContext).toHaveBeenCalledTimes(1);
});
const traceparentHeader: string = "HiItsMeTraceparentHeader";
mockParseTraceparentHeader.mockImplementation((_: string) => { throw new TraceContextError(""); });

it("should generate traceContext on traceparent-header parsing error", () => {
const traceContext: TraceContext = { traceId: "traceId" } as TraceContext;
mockGenerateTraceContext.mockReturnValue(traceContext);

const traceparentHeader: string = "HiItsMeTraceparentHeader";
mockParseTraceparentHeader.mockImplementation((_: string) => { throw new TraceContextError(""); });
(mockReq.header as jest.Mock).mockImplementation((header: string) => {
switch (header) {
case TRACEPARENT_HEADER:
return traceparentHeader;
default:
return "HiItsMeHeader";
}
});

const traceContext: TraceContext = { traceId: "traceId" } as TraceContext;
mockGenerateTraceContext.mockReturnValue(traceContext);
contextMiddlewareFactory(mockParseTraceparentHeader, mockGenerateTraceContext)(mockReq, mockRes, mockNext);

(mockReq.header as jest.Mock).mockImplementation((header: string) => {
switch (header) {
case TRACEPARENT_HEADER:
return traceparentHeader;
default:
return "HiItsMeHeader";
}
expect(mockReq.dvelopContext.traceContext).toEqual(traceContext);
expect(mockParseTraceparentHeader).toHaveBeenCalledTimes(1);
expect(mockParseTraceparentHeader).toHaveBeenCalledWith(traceparentHeader);
expect(mockGenerateTraceContext).toHaveBeenCalledTimes(1);
});

contextMiddlewareFactory(mockParseTraceparentHeader, mockGenerateTraceContext)(mockReq, mockRes, mockNext);

expect(mockReq.dvelopContext.traceContext).toEqual(traceContext);
expect(mockParseTraceparentHeader).toHaveBeenCalledTimes(1);
expect(mockParseTraceparentHeader).toHaveBeenCalledWith(traceparentHeader);
expect(mockGenerateTraceContext).toHaveBeenCalledTimes(1);
});

});
Original file line number Diff line number Diff line change
Expand Up @@ -18,17 +18,27 @@ import { Request, Response, NextFunction } from "express";
*/
export function contextMiddlewareFactory(
parseTraceparentHeader: (traceparentHeader: string) => TraceContext,
generateTraceContext: () => TraceContext
generateTraceContext: () => TraceContext,
systemBaseUri?: string,
tenantId?: string
): (req: Request, _: Response, next: NextFunction) => void {

return (req: Request, _: Response, next: NextFunction) => {

req.dvelopContext = {
systemBaseUri: req.header(DVELOP_SYSTEM_BASE_URI_HEADER),
tenantId: req.header(DVELOP_TENANT_ID_HEADER),
requestId: req.header(DVELOP_REQUEST_ID_HEADER),
requestSignature: req.header(DVELOP_REQUEST_SIGNATURE_HEADER),
};
if (systemBaseUri) {
req.dvelopContext = {
systemBaseUri: systemBaseUri,
tenantId: tenantId || req.header(DVELOP_TENANT_ID_HEADER),
requestId: req.header(DVELOP_REQUEST_ID_HEADER)
}
} else {
req.dvelopContext = {
systemBaseUri: req.header(DVELOP_SYSTEM_BASE_URI_HEADER),
tenantId: req.header(DVELOP_TENANT_ID_HEADER),
requestId: req.header(DVELOP_REQUEST_ID_HEADER),
requestSignature: req.header(DVELOP_REQUEST_SIGNATURE_HEADER),
};
}

const traceparentHeader = req.header(TRACEPARENT_HEADER);

Expand Down Expand Up @@ -66,3 +76,27 @@ export function contextMiddlewareFactory(
export function contextMiddleware(req: Request, _: Response, next: NextFunction): void {
return contextMiddlewareFactory(parseTraceparentHeader, generateTraceContext)(req, _, next);
}

/**
* Sets a {@link DvelopContext} to the express-request-object. Accessable via the ```req.dvelopContext```-property.
* This is a version with a fixed systemBaseUri, primarily used on premise.
*
* ```typescript
* import { contextMiddlewareFactoryWithFixedSystemBaseUri } from "@dvelop-sdk/express-utils";
*
* app.use(contextMiddlewareFactoryWithFixedSystemBaseUri("https://my.local.baseuri")); //could optionally supply a tenantId (default: 0)
*
* app.use((req: Request, _: Response, next: NextFunction) => {
* console.log(req.dvelopContext);
* next();
* });
* ```
*
* @category Middleware
*/
/* istanbul ignore next */
export function contextMiddlewareFactoryWithFixedSystemBaseUri(systemBaseUri: string, tenantId: string = "0") {
return (req: Request, _: Response, next: NextFunction) => {
return contextMiddlewareFactory(parseTraceparentHeader, generateTraceContext, systemBaseUri, tenantId)(req, _, next);
}
}

0 comments on commit 962ace3

Please sign in to comment.