/* Copyright 2024 New Vector Ltd. Copyright 2023 The Matrix.org Foundation C.I.C. SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only Please see LICENSE files in the repository root for full details. */ import fetchMock from "fetch-mock-jest"; import { mocked } from "jest-mock"; import { TokenRefresher } from "../../../../src/utils/oidc/TokenRefresher"; import { persistAccessTokenInStorage, persistRefreshTokenInStorage } from "../../../../src/utils/tokens/tokens"; import { mockPlatformPeg } from "../../../test-utils"; import { makeDelegatedAuthConfig } from "../../../test-utils/oidc"; jest.mock("../../../../src/utils/tokens/tokens", () => ({ persistAccessTokenInStorage: jest.fn(), persistRefreshTokenInStorage: jest.fn(), })); describe("TokenRefresher", () => { const clientId = "test-client-id"; const issuer = "https://auth.com/"; const redirectUri = "https://test.com"; const deviceId = "test-device-id"; const userId = "@alice:server.org"; const accessToken = "test-access-token"; const refreshToken = "test-refresh-token"; const authConfig = makeDelegatedAuthConfig(issuer); const idTokenClaims = { aud: "123", iss: issuer, sub: "123", exp: 123, iat: 456, }; beforeEach(() => { fetchMock.get(`${issuer}.well-known/openid-configuration`, authConfig.metadata); fetchMock.get(`${issuer}jwks`, { status: 200, headers: { "Content-Type": "application/json", }, keys: [], }); mocked(persistAccessTokenInStorage).mockResolvedValue(undefined); mocked(persistRefreshTokenInStorage).mockResolvedValue(undefined); }); afterEach(() => { jest.restoreAllMocks(); }); it("should persist tokens with a pickle key", async () => { const pickleKey = "test-pickle-key"; const getPickleKey = jest.fn().mockResolvedValue(pickleKey); mockPlatformPeg({ getPickleKey }); const refresher = new TokenRefresher(issuer, clientId, redirectUri, deviceId, idTokenClaims, userId); await refresher.oidcClientReady; await refresher.persistTokens({ accessToken, refreshToken }); expect(getPickleKey).toHaveBeenCalledWith(userId, deviceId); expect(persistAccessTokenInStorage).toHaveBeenCalledWith(accessToken, pickleKey); expect(persistRefreshTokenInStorage).toHaveBeenCalledWith(refreshToken, pickleKey); }); it("should persist tokens without a pickle key", async () => { const getPickleKey = jest.fn().mockResolvedValue(null); mockPlatformPeg({ getPickleKey }); const refresher = new TokenRefresher(issuer, clientId, redirectUri, deviceId, idTokenClaims, userId); await refresher.oidcClientReady; await refresher.persistTokens({ accessToken, refreshToken }); expect(getPickleKey).toHaveBeenCalledWith(userId, deviceId); expect(persistAccessTokenInStorage).toHaveBeenCalledWith(accessToken, undefined); expect(persistRefreshTokenInStorage).toHaveBeenCalledWith(refreshToken, undefined); }); });