Add GCP logging extender (#503)

* Add GCP logging extender

* Minor version bump for new API

* Update packages/logger/src/logger.ts

Co-Authored-By: kylecarbs <kyle@kwc.io>
This commit is contained in:
Kyle Carberry 2019-04-17 13:41:10 -05:00 committed by GitHub
parent e907dbe7e6
commit 8a4da542ae
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 104 additions and 3 deletions

View File

@ -5,9 +5,12 @@
"build": "tsc -p tsconfig.build.json && cp ./out/packages/logger/src/* ./out && rm -rf out/packages && ../../node_modules/.bin/webpack --config ./webpack.config.js",
"postinstall": "if [ ! -d out ];then npm run build; fi"
},
"version": "1.0.3",
"version": "1.1.0",
"main": "out/main.js",
"types": "out/index.d.ts",
"author": "Coder",
"license": "MIT"
"license": "MIT",
"dependencies": {
"@google-cloud/logging": "^4.5.2"
}
}

View File

@ -0,0 +1,12 @@
import { field, logger } from "./logger";
import { createStackdriverExtender } from "./extender";
describe("Extender", () => {
it("should add stackdriver extender", () => {
logger.extend(createStackdriverExtender("coder-dev-1", "logging-package-tests"));
});
it("should log", async () => {
logger.debug("Bananas!", field("frog", { hi: "wow" }));
});
});

View File

@ -0,0 +1,63 @@
import * as gcl from "@google-cloud/logging";
import { Extender, logger, field } from "./logger";
export const createStackdriverExtender = (projectId: string, logId: string): Extender => {
enum GcpLogSeverity {
DEFAULT = 0,
DEBUG = 100,
INFO = 200,
NOTICE = 300,
WARNING = 400,
ERROR = 500,
CRITICAL = 600,
ALERT = 700,
EMERGENCY = 800,
}
const logging = new gcl.Logging({
autoRetry: true,
projectId,
});
const log = logging.log(logId);
const convertSeverity = (severity: "trace" | "info" | "warn" | "debug" | "error"): GcpLogSeverity => {
switch (severity) {
case "trace":
case "debug":
return GcpLogSeverity.DEBUG;
case "info":
return GcpLogSeverity.INFO;
case "error":
return GcpLogSeverity.ERROR;
case "warn":
return GcpLogSeverity.WARNING;
}
};
return (options): void => {
const severity = convertSeverity(options.type);
// tslint:disable-next-line:no-any
const metadata = {} as any;
if (options.fields) {
options.fields.forEach((f) => {
if (!f) {
return;
}
metadata[f.identifier] = f.value;
});
}
const entry = log.entry({
// tslint:disable-next-line:no-any
severity: severity as any,
}, {
...metadata,
message: options.message,
});
log.write(entry).catch((ex) => {
logger.named("GCP").error("Failed to log", field("error", ex));
});
};
};

View File

@ -59,6 +59,14 @@ export const field = <T>(name: string, value: T): Field<T> => {
return new Field(name, value);
};
export type Extender = (msg: {
message: string,
level: Level,
type: "trace" | "info" | "warn" | "debug" | "error",
fields?: FieldArray,
section?: string,
}) => void;
/**
* This formats & builds text for logging.
* It should only be used to build one log item at a time since it stores the
@ -221,6 +229,7 @@ export class Logger {
private _formatter: Formatter,
private readonly name?: string,
private readonly defaultFields?: FieldArray,
private readonly extenders: Extender[] = [],
) {
if (name) {
this.nameColor = this.hashStringToColor(name);
@ -248,6 +257,10 @@ export class Logger {
this.muted = true;
}
public extend(extender: Extender): void {
this.extenders.push(extender);
}
/**
* Outputs information.
*/
@ -328,7 +341,7 @@ export class Logger {
* Each name is deterministically generated a color.
*/
public named(name: string, ...fields: FieldArray): Logger {
const l = new Logger(this._formatter, name, fields);
const l = new Logger(this._formatter, name, fields, this.extenders);
if (this.muted) {
l.mute();
}
@ -393,6 +406,16 @@ export class Logger {
console.log(...this._formatter.flush());
}
// tslint:enable no-console
this.extenders.forEach((extender) => {
extender({
section: this.name,
fields: options.fields,
level: options.level,
message: options.message as string,
type: options.type,
});
});
}
/**