From c6188a8345769cf45c501c5b163eec370e1f3133 Mon Sep 17 00:00:00 2001 From: Robin Date: Mon, 22 Jun 2026 11:59:16 +0200 Subject: [PATCH] Improve test coverage --- src/AppBar.test.tsx | 32 +++++++++----- src/__snapshots__/AppBar.test.tsx.snap | 53 +++++++++++++++++++++++ src/room/RingingAudioRenderer.test.tsx | 59 ++++++++++++++++++++++++++ 3 files changed, 134 insertions(+), 10 deletions(-) create mode 100644 src/room/RingingAudioRenderer.test.tsx diff --git a/src/AppBar.test.tsx b/src/AppBar.test.tsx index a2cce6832..29380b97f 100644 --- a/src/AppBar.test.tsx +++ b/src/AppBar.test.tsx @@ -5,21 +5,33 @@ SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial Please see LICENSE in the repository root for full details. */ +import { type FC, type ReactNode } from "react"; import { render } from "@testing-library/react"; import { describe, expect, it } from "vitest"; import { TooltipProvider } from "@vector-im/compound-web"; -import { AppBar } from "./AppBar"; +import { AppBar, useAppBarSubtitle, useAppBarTitle } from "./AppBar"; + +const content =

This is the content.

; + +function snapshotAppBar(content: ReactNode): void { + const { container } = render( + + {content} + , + ); + expect(container).toMatchSnapshot(); +} describe("AppBar", () => { - it("renders", () => { - const { container } = render( - - -

This is the content.

-
-
, - ); - expect(container).toMatchSnapshot(); + it("renders", () => snapshotAppBar(content)); + + it("renders with title and subtitle", () => { + const TestComponent: FC = () => { + useAppBarTitle("Title"); + useAppBarSubtitle("Subtitle"); + return content; + }; + snapshotAppBar(); }); }); diff --git a/src/__snapshots__/AppBar.test.tsx.snap b/src/__snapshots__/AppBar.test.tsx.snap index f56c12b8c..482189481 100644 --- a/src/__snapshots__/AppBar.test.tsx.snap +++ b/src/__snapshots__/AppBar.test.tsx.snap @@ -42,3 +42,56 @@ exports[`AppBar > renders 1`] = `

`; + +exports[`AppBar > renders with title and subtitle 1`] = ` +
+
+
+ +

+ Title +

+ + Subtitle + +
+
+
+

+ This is the content. +

+
+`; diff --git a/src/room/RingingAudioRenderer.test.tsx b/src/room/RingingAudioRenderer.test.tsx new file mode 100644 index 000000000..4d95ffacb --- /dev/null +++ b/src/room/RingingAudioRenderer.test.tsx @@ -0,0 +1,59 @@ +/* +Copyright 2026 Element Creations Ltd. + +SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial +Please see LICENSE in the repository root for full details. +*/ + +import { expect, type MockedFunction, test, vi } from "vitest"; +import { act, render } from "@testing-library/react"; +import { BehaviorSubject } from "rxjs"; + +import { useAudioContext } from "../useAudioContext"; +import { createRingingMedia } from "../state/media/RingingMediaViewModel"; +import { alice, aliceId } from "../utils/test-fixtures"; +import { constant } from "../state/Behavior"; +import { RingingAudioRenderer } from "./RingingAudioRenderer"; +import { prefetchSounds } from "../soundUtils"; + +vi.mock("../useAudioContext"); +vi.mock("../soundUtils"); + +test("ringtone plays on loop while ringing", () => { + (prefetchSounds as MockedFunction).mockResolvedValue({ + sound: new ArrayBuffer(0), + }); + const endSoundLooping = vi.fn().mockReturnValue(Promise.resolve()); + const playSoundLooping = vi.fn().mockReturnValue(endSoundLooping); + (useAudioContext as MockedFunction).mockReturnValue({ + playSound: vi.fn(), + playSoundLooping, + soundDuration: {}, + }); + + const pickupState$ = new BehaviorSubject<"ringing" | "timeout" | "decline">( + "ringing", + ); + const vm = createRingingMedia({ + id: aliceId, + userId: alice.userId, + displayName$: constant("Alice"), + mxcAvatarUrl$: constant(undefined), + intent: "audio", + pickupState$, + }); + + // Begin ringing + render(); + expect(playSoundLooping).toHaveBeenCalledExactlyOnceWith( + "ringtone", + expect.any(Number), + ); + expect(endSoundLooping).not.toHaveBeenCalled(); + vi.clearAllMocks(); + + // End ringing + act(() => pickupState$.next("decline")); + expect(playSoundLooping).not.toHaveBeenCalled(); + expect(endSoundLooping).toHaveBeenCalledExactlyOnceWith(); +});