Skip to content

Commit

Permalink
feat: durable logger
Browse files Browse the repository at this point in the history
  • Loading branch information
michael-0acf4 committed Nov 28, 2024
1 parent 91e9e18 commit 890c8fb
Show file tree
Hide file tree
Showing 3 changed files with 60 additions and 0 deletions.
49 changes: 49 additions & 0 deletions src/typegate/src/runtimes/substantial/deno_context.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,10 +14,12 @@ export class Context {
private id = 0;
public kwargs = {};
gql: ReturnType<typeof createGQLClient>;
logger: SubLogger;

constructor(private run: Run, private internal: TaskContext) {
this.gql = createGQLClient(internal);
this.kwargs = getKwargsCopy(run);
this.logger = new SubLogger(this);
}

#nextId() {
Expand Down Expand Up @@ -414,6 +416,53 @@ class RetryStrategy {
}
}


class SubLogger {
constructor(private ctx: Context) {}

async #log(kind: "warn" | "error" | "info", ...args: unknown[]) {
await this.ctx.save(() => {
const prefix = `[${kind.toUpperCase()}: ${this.ctx.getRun().run_id}]`;
switch(kind) {
case "warn": {
console.warn(prefix, ...args);
break;
}
case "error": {
console.error(prefix,...args);
break;
}
default: {
console.info(prefix, ...args);
break;
}
}

const message = args.map((arg) => {
try {
return JSON.stringify(arg);
} catch(_) {
return String(arg);
}
}).join(" ");

return `${prefix}: ${message}`;
});
}

async warn(...payload: unknown[]) {
await this.#log("warn", ...payload);
}

async info(...payload: unknown[]) {
await this.#log("info", ...payload);
}

async error(...payload: unknown[]) {
await this.#log("error", ...payload);
}
}

function createGQLClient(internal: TaskContext) {
const tgLocal = new URL(internal.meta.url);
if (testBaseUrl) {
Expand Down
8 changes: 8 additions & 0 deletions tests/runtimes/substantial/imports/common_types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,14 @@ export interface Context {
createWorkflowHandle(
handleDef: SerializableWorkflowHandle,
): ChildWorkflowHandle;

logger: SubLogger
}

interface SubLogger {
warn: (...args: unknown[]) => Promise<void>;
info: (...args: unknown[]) => Promise<void>;
error: (...args: unknown[]) => Promise<void>;
}

export type TaskCtx = {
Expand Down
3 changes: 3 additions & 0 deletions tests/runtimes/substantial/workflow.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,11 +14,14 @@ export const eventsAndExceptionExample: Workflow<string> = async (
) => {
const { to } = ctx.kwargs;
const messageDialog = await ctx.save(() => sendSubscriptionEmail(to));
await ctx.logger.info("Will send to", to);
await ctx.logger.warn("Will now wait on an event");

// This will wait until a `confirmation` event is sent to THIS workflow
const confirmation = ctx.receive<boolean>("confirmation");

if (!confirmation) {
await ctx.logger.error("Denial", to);
throw new Error(`${to} has denied the subscription`);
}

Expand Down

0 comments on commit 890c8fb

Please sign in to comment.