Skip to content

Commit

Permalink
feat(APIM-344): changed redaction in crashed bootstrap and changed re…
Browse files Browse the repository at this point in the history
…daction in recovered bootstrap
  • Loading branch information
avaitonis committed Jul 19, 2023
1 parent 9f3442a commit 3a3b646
Show file tree
Hide file tree
Showing 7 changed files with 142 additions and 5 deletions.
2 changes: 2 additions & 0 deletions src/constants/redact-strings-paths.constant.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,4 +7,6 @@ export const REDACT_STRING_PATHS = [
'stack',
'originalError.message',
'originalError.stack',
'err.message',
'err.stack',
];
96 changes: 96 additions & 0 deletions src/helpers/redact-strings-in-log-args.helper.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@
import { REDACT_STRING_PATHS } from '@ukef/constants';
import { RandomValueGenerator } from '@ukef-test/support/generator/random-value-generator';

import { redactStringsInLogArgs } from './redact-strings-in-log-args.helper';

describe('Redact errors helper', () => {
const valueGenerator = new RandomValueGenerator();

describe('redactStringsInLogArgs', () => {
const domain = valueGenerator.httpsUrl();
const otherSensitivefield = valueGenerator.word();
const message = `ConnectionError: Failed to connect to ${domain}, ${otherSensitivefield}`;
const redactedMessage = `ConnectionError: Failed to connect to [RedactedDomain], [Redacted]`;
const redactStrings = [
{ searchValue: domain, replaceValue: '[RedactedDomain]' },
{ searchValue: otherSensitivefield, replaceValue: '[Redacted]' },
];
const args = [
{
message: message,
stack: message,
originalError: {
message: message,
stack: message,
safe: 'Nothing sensitive',
},
driverError: {
message: message,
stack: message,
originalError: {
message: message,
stack: message,
safe: 'Nothing sensitive',
},
},
},
];
const expectedResult = [
{
message: redactedMessage,
stack: redactedMessage,
originalError: {
message: redactedMessage,
stack: redactedMessage,
safe: 'Nothing sensitive',
},
driverError: {
message: redactedMessage,
stack: redactedMessage,
originalError: {
message: redactedMessage,
stack: redactedMessage,
safe: 'Nothing sensitive',
},
},
},
];

it('replaces sensitive data in input object', () => {
const redacted = redactStringsInLogArgs(true, REDACT_STRING_PATHS, redactStrings, args);

expect(redacted).toStrictEqual(expectedResult);
});

it('returns original input if redactLogs is set to false', () => {
const redacted = redactStringsInLogArgs(false, REDACT_STRING_PATHS, redactStrings, args);

expect(redacted).toStrictEqual(args);
});

it('replaces sensitive data in different input object', () => {
const args = [
{
field1: message,
field2: {
field3: message,
safe: 'Nothing sensitive',
},
},
];
const expectedResult = [
{
field1: redactedMessage,
field2: {
field3: redactedMessage,
safe: 'Nothing sensitive',
},
},
];
const redactPaths = ['field1', 'field2.field3'];
const redacted = redactStringsInLogArgs(true, redactPaths, redactStrings, args);

expect(redacted).toStrictEqual(expectedResult);
});
});
});
31 changes: 31 additions & 0 deletions src/helpers/redact-strings-in-log-args.helper.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import { get, set } from 'lodash';

// This helper function is used to redact sensitive data in Error object strings.
export const redactStringsInLogArgs = (
redactLogs: boolean,
redactPaths: string[],
redactStrings: { searchValue: string | RegExp; replaceValue: string }[],
args: any,
): any => {
if (!redactLogs) {
return args;
}
args.forEach((arg, index) => {
redactPaths.forEach((path) => {
const value: string = get(arg, path);
if (value) {
const safeValue = redactString(redactStrings, value);
set(args[index], path, safeValue);

Check warning on line 18 in src/helpers/redact-strings-in-log-args.helper.ts

View workflow job for this annotation

GitHub Actions / Scanning 🎨

Function Call Object Injection Sink
}
});
});
return args;
};

const redactString = (redactStrings: { searchValue: string | RegExp; replaceValue: string }[], string: string): string => {
let safeString: string = string;
redactStrings.forEach((redact) => {
safeString = safeString.replaceAll(redact.searchValue, redact.replaceValue);
});
return safeString;
};
10 changes: 8 additions & 2 deletions src/logging/console-logger-with-redact.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,12 +9,18 @@ export class ConsoleLoggerWithRedact extends ConsoleLogger {
}

error(message: any, stack?: string, context?: string) {
let cleanMessage = message;
let cleanStack = stack;
if (typeof message == 'string') {
this.stringPatternsToRedact.forEach((redact) => {
cleanMessage = cleanMessage.replace(redact.searchValue, redact.replaceValue);
});
}
if (typeof stack == 'string') {
this.stringPatternsToRedact.forEach((redact) => {
cleanStack = stack.replace(redact.searchValue, redact.replaceValue);
cleanStack = cleanStack.replace(redact.searchValue, redact.replaceValue);
});
}
super.error(message, cleanStack, context);
super.error(cleanMessage, cleanStack, context);
}
}
2 changes: 1 addition & 1 deletion src/main.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ import { LoggingInterceptor } from './logging/logging-interceptor.helper';
},
},
hooks: {
logMethod(inputArgs, method) {
logMethod(inputArgs: any, method) {
return method.apply(this, redactStringsInLogArgs(config.get<boolean>('app.redactLogs'), REDACT_STRING_PATHS, REDACT_STRINGS, inputArgs));
},
},
Expand Down
4 changes: 3 additions & 1 deletion src/main.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,10 @@ import { REDACT_STRINGS } from './constants';
import { ConsoleLoggerWithRedact } from './logging/console-logger-with-redact';

const main = async () => {
// ConsoleLoggerWithRedact is used just if NestFactory.create is fails completely.
// Buffered logs are passed to PinoLogger if NestFactory.create is successfull, ConsoleLoggerWithRedact is not used.
const logger = new ConsoleLoggerWithRedact(REDACT_STRINGS);
const nestApp: NestApplication = await NestFactory.create(MainModule, { logger, bufferLogs: false });
const nestApp: NestApplication = await NestFactory.create(MainModule, { logger, bufferLogs: true });
const app = new App(nestApp);

logger.log(`==========================================================`);
Expand Down
2 changes: 1 addition & 1 deletion src/modules/markets/markets.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ export class MarketsService {
}));

return mappedResults;
} catch (err: any) {
} catch (err) {
this.logger.error(err);
throw new InternalServerErrorException();
}
Expand Down

0 comments on commit 3a3b646

Please sign in to comment.