litellm/ui/litellm-dashboard/e2e_tests/tests/proxy-admin/license.spec.ts
ryan-crabbe-berri 07bcd2c19e
test(e2e): forward LITELLM_LICENSE to UI e2e proxy (#28398)
* test(e2e): forward LITELLM_LICENSE to UI e2e proxy

The UI e2e job ran without LITELLM_LICENSE, so premium_user was always
false in the issued login JWT and premium-gated UI surfaces (Team-BYOK
Model switch, etc.) couldn't be driven through the UI. Forward the env
var from run_e2e.sh and the CircleCI e2e_ui_testing job, and add a
sanity test that decodes the admin storage state token and asserts
premium_user=true so the wiring fails loudly if it ever regresses.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>

* Update ui/litellm-dashboard/e2e_tests/tests/proxy-admin/license.spec.ts

Co-authored-by: greptile-apps[bot] <165735046+greptile-apps[bot]@users.noreply.github.com>

---------

Co-authored-by: Claude Opus 4.7 <noreply@anthropic.com>
Co-authored-by: greptile-apps[bot] <165735046+greptile-apps[bot]@users.noreply.github.com>
2026-05-21 18:17:03 -07:00

38 lines
1.6 KiB
TypeScript

import { test, expect } from "@playwright/test";
import * as fs from "fs";
import { ADMIN_STORAGE_PATH } from "../../constants";
/**
* Sanity check that LITELLM_LICENSE is being forwarded to the proxy when set
* in the environment (e.g. CircleCI's `e2e_ui_testing` job). The login JWT's
* `premium_user` claim is the same value the dashboard reads to enable
* premium-gated UI surfaces (Team-BYOK switch, etc.), so asserting it here
* catches any future regression where the env var stops being plumbed
* through `run_e2e.sh` / `.circleci/config.yml`.
*
* Skips locally when no license is configured.
*/
test.describe("Premium license wiring", () => {
test("admin session JWT carries premium_user=true when LITELLM_LICENSE is set", () => {
test.skip(
!process.env.LITELLM_LICENSE,
"LITELLM_LICENSE not set in test env — proxy is running unlicensed",
);
const storage = JSON.parse(fs.readFileSync(ADMIN_STORAGE_PATH, "utf-8"));
const tokenCookie = storage.cookies?.find((c: { name: string }) => c.name === "token");
expect(tokenCookie, "token cookie missing from admin storage state").toBeDefined();
// Decode the JWT payload (no signature check — we trust globalSetup ran
// against our own proxy). Payload is the middle base64url segment.
const jwtParts = tokenCookie.value.split(".");
expect(jwtParts.length, "token cookie is not a 3-part JWT").toBe(3);
const [, payloadB64] = jwtParts;
const payload = JSON.parse(
Buffer.from(payloadB64, "base64url").toString("utf-8"),
);
expect(payload.premium_user).toBe(true);
});
});