fix(messaging): mask microservice URI authorization component in logs
MODIFY
packages/core/src/+internal/utils/spec/string.util.spec.ts
packages/core/src/+internal/utils/spec/string.util.spec.ts
-import { isString, trim, stringify, createUuid, trunc } from '../string.util';
+import { isString, trim, stringify, createUuid, trunc, maskUriComponent } from '../string.util';
describe('#isString', () => {
const cases: [any, boolean][] = [
@@ -52,3 +52,15 @@ test('#stringify stringifies given value', () => {
test('#createUuid creates unique identifier', () => {
expect(createUuid()).toBeDefined();
});
+
+describe('#maskUriComponent', () => {
+ test('masks "authorization" URI component', () => {
+ const mask = maskUriComponent('authorization');
+
+ expect(mask('amqp://some_user:some_pass@host:10000/vhost'))
+ .toEqual('amqp://[user]:[pass]@host:10000/vhost');
+
+ expect(mask('amqp://host:10000/vhost'))
+ .toEqual('amqp://host:10000/vhost');
+ })
+})

MODIFY
packages/core/src/+internal/utils/string.util.ts
packages/core/src/+internal/utils/string.util.ts
@@ -25,3 +25,12 @@ export const stringify = (value: any): string =>
: JSON.stringify(value);
export const createUuid = () => uuid();
+
+export const maskUriComponent = (type: 'authorization') => (uri: string): string => {
+ switch (type) {
+ case 'authorization':
+ return uri.replace(/\/\/(.*)\@/, '//[user]:[pass]@');
+ default:
+ return uri;
+ }
+}

MODIFY
packages/messaging/src/server/messaging.server.ts
packages/messaging/src/server/messaging.server.ts
@@ -4,7 +4,7 @@ import { identity } from 'fp-ts/lib/function';
import { Subject } from 'rxjs';
import { takeWhile, takeUntil, take } from 'rxjs/operators';
import { bindTo, createEffectContext, combineEffects, ServerIO, lookup, logContext, LoggerTag, contextFactory } from '@marblejs/core';
-import { throwException } from '@marblejs/core/dist/+internal/utils';
+import { throwException, maskUriComponent } from '@marblejs/core/dist/+internal/utils';
import { provideTransportLayer } from '../transport/transport.provider';
import { statusLogger$ } from '../middlewares/messaging.statusLogger.middleware';
import { TransportLayerConnection } from '../transport/transport.interface';
@@ -55,15 +55,25 @@ export const createMicroservice = async (config: CreateMicroserviceConfig) => {
connection.status$
.pipe(takeUntil(connection.close$))
- .subscribe(type => serverEventsSubject.next(ServerEvent.status(host, channel, type)));
+ .subscribe(type => pipe(
+ maskUriComponent('authorization')(host),
+ host => ServerEvent.status(host, channel, type),
+ event => serverEventsSubject.next(event),
+ ));
connection.close$
.pipe(take(1))
- .subscribe(() => serverEventsSubject.next(ServerEvent.close()));
+ .subscribe(() => pipe(
+ ServerEvent.close(),
+ event => serverEventsSubject.next(event),
+ ));
connection.error$
.pipe(takeUntil(connection.close$))
- .subscribe(error => serverEventsSubject.next(ServerEvent.error(error)));
+ .subscribe(error => pipe(
+ ServerEvent.error(error),
+ event => serverEventsSubject.next(event),
+ ));
return connection;
};

fix(messaging): mask microservice URI authorization component in logs