Skip to content

Commit 4d8c23d

Browse files
committed
request logger
1 parent 0f8e49f commit 4d8c23d

File tree

4 files changed

+81
-0
lines changed

4 files changed

+81
-0
lines changed

packages/logger/package.json

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,16 @@
2929
"default": "./dist/index.js"
3030
}
3131
},
32+
"./request": {
33+
"require": {
34+
"types": "./dist/request.d.cts",
35+
"default": "./dist/request.cjs"
36+
},
37+
"import": {
38+
"types": "./dist/request.d.ts",
39+
"default": "./dist/request.js"
40+
}
41+
},
3242
"./package.json": "./package.json"
3343
},
3444
"files": [

packages/logger/src/Logger.ts

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,14 +66,29 @@ export class Logger implements LogWriter {
6666
this.#writers = opts.writers ?? [new ConsoleLogWriter()];
6767
}
6868

69+
/** The prefix that's prepended to each log message. */
6970
public get prefix() {
7071
return this.#prefix;
7172
}
7273

74+
/**
75+
* The attributes that are added to each log. If the log itself contains
76+
* attributes with keys existing in {@link attrs}, the log's attributes will
77+
* override.
78+
*/
79+
public get attrs() {
80+
return this.#attrs;
81+
}
82+
83+
/** The current {@link LogLevel} of the logger. You can change the level using the {@link setLevel} method. */
7384
public get level() {
7485
return typeof this.#level === 'function' ? this.#level() : this.#level;
7586
}
7687

88+
/**
89+
* Sets the new {@link LogLevel} of the logger. All subsequent logs, and {@link child child loggers} whose
90+
* level did not change, will respect the new level.
91+
*/
7792
public setLevel(level: MaybeLazy<LogLevel | false>) {
7893
this.#level = level;
7994
}

packages/logger/src/request.ts

Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
import { Logger } from './Logger';
2+
3+
// TODO: write tests
4+
5+
export const requestIdByRequest = new WeakMap<Request, string>();
6+
7+
/** The getter function that extracts the requestID from the {@link request} or creates a new one if none-exist. */
8+
export type GetRequestID = (request: Request) => string;
9+
10+
/**
11+
* Creates a child {@link Logger} under the {@link log given logger} for the {@link request}.
12+
*
13+
* Request's ID will be stored in the {@link requestIdByRequest} weak map; meaning, all
14+
* subsequent calls to this function with the same {@link request} will return the same ID.
15+
*
16+
* The {@link getId} argument will be used to create a new ID if the {@link request} does not
17+
* have one. The convention is to the `X-Request-ID` header or create a new ID which is an
18+
* UUID v4.
19+
*
20+
* On the other hand, if the {@link getId} argument is omitted, the {@link requestIdByRequest} weak
21+
* map will be looked up, and if there is no ID stored for the {@link request} - the function
22+
* will not attempt to create a new ID and will just return the same {@link log logger}.
23+
*
24+
* The request ID will be added to the logger attributes under the `requestId` key and
25+
* will be logged in every subsequent log.
26+
*/
27+
export function loggerForRequest(log: Logger, request: Request): Logger;
28+
export function loggerForRequest(
29+
log: Logger,
30+
request: Request,
31+
getId: GetRequestID,
32+
): Logger;
33+
export function loggerForRequest(
34+
log: Logger,
35+
request: Request,
36+
getId?: GetRequestID,
37+
): Logger {
38+
let requestId = requestIdByRequest.get(request);
39+
if (!requestId) {
40+
if (getId === undefined) {
41+
return log;
42+
}
43+
requestId = getId(request);
44+
requestIdByRequest.set(request, requestId);
45+
}
46+
if (
47+
log.attrs &&
48+
'requestId' in log.attrs &&
49+
log.attrs['requestId'] === requestId
50+
) {
51+
// this logger is already a child that contains this request id, no need to create a new one
52+
return log;
53+
}
54+
return log.child({ requestId });
55+
}

tsconfig.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,7 @@
6262
"@graphql-tools/wrap": ["./packages/wrap/src/index.ts"],
6363
"@graphql-tools/executor-*": ["./packages/executors/*/src/index.ts"],
6464
"@graphql-hive/logger": ["./packages/logger/src/index.ts"],
65+
"@graphql-hive/logger/request": ["./packages/logger/src/request.ts"],
6566
"@graphql-hive/logger-json": ["./packages/logger-json/src/index.ts"],
6667
"@graphql-hive/logger-winston": [
6768
"./packages/logger-winston/src/index.ts"

0 commit comments

Comments
 (0)