Move SFU authentication into livekit/auth and choose the endpoint by role

The OpenID flow moves to src/livekit/auth/openID.ts with the SFU config
types in a sibling file, takes an options object, and replaces the
MatrixRTC mode with the role we take on the transport plus the session's
slot ID instead of a hard-coded m.call#ROOM.

This changes behaviour: publishers on a livekit_service_url transport
always use the legacy /sfu/get endpoint, so that subscribers can predict
their user:device participant identity, and subscribers always use the
default /get_token endpoint. The MatrixRTC mode no longer influences which
endpoint is used.
This commit is contained in:
Robin
2026-10-12 10:17:39 +02:00
committed by Johannes Marbach
parent f260755f46
commit 17c3223883
21 changed files with 708 additions and 804 deletions
@@ -66,7 +66,7 @@ import { type Publisher } from "./Publisher";
import { initializeWidget } from "../../../widget";
import { nullHostBridge } from "../../../HostBridge";
import { type LocalTransport } from "./LocalTransport";
import * as openIDSFU from "../../../livekit/openIDSFU";
import * as livekitAuth from "../../../livekit/auth";
initializeWidget();
@@ -237,7 +237,6 @@ describe("LocalMembership", () => {
ownMembershipIdentity: ownMemberMock,
client: mockedClient,
delayId$: constant(null),
matrixRTCMode: MATRIX_RTC_MODE,
};
beforeEach(() => {
@@ -306,6 +305,7 @@ describe("LocalMembership", () => {
scope,
...defaultCreateLocalMemberValues,
matrixRTCSession: {
slotId: "m.call#ROOM",
updateCallIntent: vi.fn().mockImplementation(reject),
leave: vi.fn(),
},
@@ -359,7 +359,7 @@ describe("LocalMembership", () => {
} as unknown as Connection;
const authCallSpy = vi
.spyOn(openIDSFU, "getSFUConfigWithOpenID")
.spyOn(livekitAuth, "getSFUConfig")
.mockImplementation(() => mockedClient.getOpenIdToken());
afterEach(() => authCallSpy.mockClear());
@@ -412,18 +412,16 @@ describe("LocalMembership", () => {
// Delegation is supported in this test case, so go on to check that
// LocalMember actually performs delegation
const expectDelegation = (delayId: string) =>
expect(authCallSpy).toHaveBeenLastCalledWith(
mockedClient,
ownMemberMock,
"a",
"!test-room-id:example.org",
{
matrixRTCMode: MATRIX_RTC_MODE,
delayEndpointBaseUrl: "https://matrix.example.org",
delayId,
},
expect.anything(),
);
expect(authCallSpy).toHaveBeenLastCalledWith({
client: mockedClient,
membership: ownMemberMock,
serviceUrl: "a",
roomId: "!test-room-id:example.org",
role: "publisher",
delayEndpointBaseUrl: "https://matrix.example.org",
delayId,
logger: expect.anything(),
});
expectDelegation("leave1");
delayId$.next("leave2"); // Can change delegated leaves