From e81225a3587f9212d4ffeb4a7d79fedc0e297e8c Mon Sep 17 00:00:00 2001 From: Koosha Owji Date: Tue, 29 Jul 2025 01:42:19 +1000 Subject: [PATCH 1/3] feat: add configurable session cookie expiry via KINDE_SESSION_MAX_AGE --- src/lib/hooks/sessionHooks.ts | 2 +- src/tests/hooks.spec.ts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/lib/hooks/sessionHooks.ts b/src/lib/hooks/sessionHooks.ts index d1a741a..a767251 100644 --- a/src/lib/hooks/sessionHooks.ts +++ b/src/lib/hooks/sessionHooks.ts @@ -16,7 +16,7 @@ export async function sessionHooks({ event }: { event: EventHandler }) { secure: process.env.NODE_ENV === "production", sameSite: "lax", httpOnly: true, - maxAge: 29 * 24 * 60 * 60, + maxAge: +(process.env.KINDE_SESSION_MAX_AGE ?? '') || 29 * 24 * 60 * 60, }, ); }; diff --git a/src/tests/hooks.spec.ts b/src/tests/hooks.spec.ts index bde6bbb..a5c35a9 100644 --- a/src/tests/hooks.spec.ts +++ b/src/tests/hooks.spec.ts @@ -175,7 +175,7 @@ describe("sessionHooks", () => { "kinde_testKey", "testValue", expect.objectContaining({ - maxAge: 29 * 24 * 60 * 60, + maxAge: +(process.env.KINDE_SESSION_MAX_AGE ?? '') || 29 * 24 * 60 * 60, domain: process.env.KINDE_COOKIE_DOMAIN, path: "/", secure: process.env.NODE_ENV === "production", From e3adcc6b9dd8d9fe3f407a5dfad09ff547839ac3 Mon Sep 17 00:00:00 2001 From: Koosha Owji Date: Tue, 29 Jul 2025 03:32:48 +1000 Subject: [PATCH 2/3] test: improve session cookie maxAge configuration test coverage --- src/tests/hooks.spec.ts | 126 +++++++++++++++++++++++++++++++--------- 1 file changed, 100 insertions(+), 26 deletions(-) diff --git a/src/tests/hooks.spec.ts b/src/tests/hooks.spec.ts index a5c35a9..867d724 100644 --- a/src/tests/hooks.spec.ts +++ b/src/tests/hooks.spec.ts @@ -1,5 +1,5 @@ import { sessionHooks } from "$lib/index.js"; -import { describe, it, expect, vi } from "vitest"; +import { describe, it, expect, vi, afterEach } from "vitest"; describe("sessionHooks", () => { it("should add setSessionItem and getSessionItem methods to event.request", async () => { @@ -155,33 +155,107 @@ describe("sessionHooks", () => { expect(retrievedValue2).toBeUndefined(); }); - it("should set cookies with 29-day expiry", async () => { - // Arrange - const event = { - request: {}, - cookies: { - set: vi.fn(), - get: vi.fn(), - }, - }; + describe("cookie maxAge configuration", () => { + const originalEnv = process.env.KINDE_SESSION_MAX_AGE; - await sessionHooks({ event }); + afterEach(() => { + if (originalEnv !== undefined) { + process.env.KINDE_SESSION_MAX_AGE = originalEnv; + } else { + delete process.env.KINDE_SESSION_MAX_AGE; + } + }); - // Act - await event.request.setSessionItem("testKey", "testValue"); + it("should use default 29 days when KINDE_SESSION_MAX_AGE is not set", async () => { + delete process.env.KINDE_SESSION_MAX_AGE; - // Assert - expect(event.cookies.set).toHaveBeenCalledWith( - "kinde_testKey", - "testValue", - expect.objectContaining({ - maxAge: +(process.env.KINDE_SESSION_MAX_AGE ?? '') || 29 * 24 * 60 * 60, - domain: process.env.KINDE_COOKIE_DOMAIN, - path: "/", - secure: process.env.NODE_ENV === "production", - sameSite: "lax", - httpOnly: true, - }), - ); + const event = { + request: {}, + cookies: { + set: vi.fn(), + get: vi.fn(), + }, + }; + + await sessionHooks({ event }); + await event.request.setSessionItem("testKey", "testValue"); + + expect(event.cookies.set).toHaveBeenCalledWith( + "kinde_testKey", + "testValue", + expect.objectContaining({ + maxAge: 29 * 24 * 60 * 60, + }), + ); + }); + + it("should use custom maxAge when KINDE_SESSION_MAX_AGE is set", async () => { + process.env.KINDE_SESSION_MAX_AGE = "3600"; // 1 hour + + const event = { + request: {}, + cookies: { + set: vi.fn(), + get: vi.fn(), + }, + }; + + await sessionHooks({ event }); + await event.request.setSessionItem("testKey", "testValue"); + + expect(event.cookies.set).toHaveBeenCalledWith( + "kinde_testKey", + "testValue", + expect.objectContaining({ + maxAge: 3600, + }), + ); + }); + + it("should fallback to default when KINDE_SESSION_MAX_AGE is zero", async () => { + process.env.KINDE_SESSION_MAX_AGE = "0"; + + const event = { + request: {}, + cookies: { + set: vi.fn(), + get: vi.fn(), + }, + }; + + await sessionHooks({ event }); + await event.request.setSessionItem("testKey", "testValue"); + + expect(event.cookies.set).toHaveBeenCalledWith( + "kinde_testKey", + "testValue", + expect.objectContaining({ + maxAge: 29 * 24 * 60 * 60, + }), + ); + }); + + it("should fallback to default when KINDE_SESSION_MAX_AGE is invalid", async () => { + process.env.KINDE_SESSION_MAX_AGE = "invalid"; + + const event = { + request: {}, + cookies: { + set: vi.fn(), + get: vi.fn(), + }, + }; + + await sessionHooks({ event }); + await event.request.setSessionItem("testKey", "testValue"); + + expect(event.cookies.set).toHaveBeenCalledWith( + "kinde_testKey", + "testValue", + expect.objectContaining({ + maxAge: 29 * 24 * 60 * 60, + }), + ); + }); }); }); From dc993113d6da29cc67397cb5e0dea11ece4eb43d Mon Sep 17 00:00:00 2001 From: Koosha Owji Date: Tue, 29 Jul 2025 03:34:36 +1000 Subject: [PATCH 3/3] chore: fix prettier formatting issues --- src/lib/hooks/sessionHooks.ts | 2 +- src/tests/hooks.spec.ts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/lib/hooks/sessionHooks.ts b/src/lib/hooks/sessionHooks.ts index a767251..8a63d3d 100644 --- a/src/lib/hooks/sessionHooks.ts +++ b/src/lib/hooks/sessionHooks.ts @@ -16,7 +16,7 @@ export async function sessionHooks({ event }: { event: EventHandler }) { secure: process.env.NODE_ENV === "production", sameSite: "lax", httpOnly: true, - maxAge: +(process.env.KINDE_SESSION_MAX_AGE ?? '') || 29 * 24 * 60 * 60, + maxAge: +(process.env.KINDE_SESSION_MAX_AGE ?? "") || 29 * 24 * 60 * 60, }, ); }; diff --git a/src/tests/hooks.spec.ts b/src/tests/hooks.spec.ts index 867d724..181d060 100644 --- a/src/tests/hooks.spec.ts +++ b/src/tests/hooks.spec.ts @@ -212,7 +212,7 @@ describe("sessionHooks", () => { ); }); - it("should fallback to default when KINDE_SESSION_MAX_AGE is zero", async () => { + it("should fallback to default when KINDE_SESSION_MAX_AGE is zero", async () => { process.env.KINDE_SESSION_MAX_AGE = "0"; const event = {