diff --git a/mod.ts b/mod.ts index 2d482b4..74e1947 100644 --- a/mod.ts +++ b/mod.ts @@ -31,6 +31,11 @@ export interface SessionFlavor { */ get session(): S; set session(session: S | undefined); + /** + * Used by the session plugin to store the current session key, if it + * exists. + */ + sessionKey: string | undefined; } /** * A lazy session flavor is a context flavor that holds a promise of some @@ -166,6 +171,15 @@ type MultiSessionOptionsRecord< [K in keyof S]: SessionOptions; }; +function setSessionKey(ctx: Context, key?: string) { + Object.defineProperty(ctx, "sessionKey", { + value: key, + writable: false, + configurable: false, + enumerable: true, + }); +} + /** * Session middleware provides a persistent data storage for your bot. You can * use it to let your bot remember any data you want, for example the messages @@ -233,6 +247,7 @@ function strictSingleSession( initial, ); const key = await getSessionKey(ctx); + setSessionKey(ctx, key); await propSession.init(key, { custom, lazy: false }); await next(); // no catch: do not write back if middleware throws await propSession.finish(); @@ -257,6 +272,7 @@ function strictMultiSession( initial, ); const key = await getSessionKey(ctx); + setSessionKey(ctx, key); await s.init(key, { custom, lazy: false }); return s; })); @@ -314,6 +330,7 @@ export function lazySession( initial, ); const key = await getSessionKey(ctx); + setSessionKey(ctx, key); await propSession.init(key, { custom, lazy: true }); await next(); // no catch: do not write back if middleware throws await propSession.finish(); diff --git a/test/mod.test.ts b/test/mod.test.ts index 2323a12..58d44aa 100644 --- a/test/mod.test.ts +++ b/test/mod.test.ts @@ -253,6 +253,23 @@ describe("session", () => { assertEquals(storage.write.calls.length, 4); assertEquals(storage.delete.calls.length, 1); }); + + it("should set ctx.sessionKey", async () => { + const storage = { + read: () => Promise.resolve(), + write: () => {}, + delete: () => {}, + }; + + const initial = () => ({}); + type C = Context & SessionFlavor; + const composer = new Composer(); + const ctx = { chatId: 42 } as C; + composer.use(session({ storage, initial })); + + await composer.middleware()(ctx, next); + assertEquals(ctx.sessionKey, "42"); + }); }); describe("multi session", () => { @@ -471,6 +488,34 @@ describe("multi session", () => { assertEquals(storage1.write.calls.length, 4); assertEquals(storage1.delete.calls.length, 1); }); + + it("should set ctx.sessionKey", async () => { + const val = {}; + const storage = { + read: () => Promise.resolve(val), + write: () => {}, + delete: () => {}, + }; + + const initial = () => ({}); + type SessionData = { + prop0: Record; + prop1: Record; + }; + type C = Context & SessionFlavor; + const composer = new Composer(); + const ctx = { chatId: 42 } as C; + composer.use( + session({ + type: "multi", + prop0: { storage, initial }, + prop1: { storage, initial }, + }), + ); + + await composer.middleware()(ctx, next); + assertEquals(ctx.sessionKey, "42"); + }); }); describe("lazy session", () => { @@ -757,6 +802,17 @@ describe("lazy session", () => { assert(done); await p; }); + + it("should set ctx.sessionKey", async () => { + type C = Context & SessionFlavor; + const composer = new Composer(); + const ctx = { chatId: 42 } as C; + composer.use(lazySession()); + + await composer.middleware()(ctx, next); + + assertEquals(ctx.sessionKey, "42"); + }); }); describe("enhanceStorage", () => {