mirror of
https://github.com/meshtastic/web.git
synced 2026-08-01 23:47:23 -04:00
Ran pnpm oxfmt . This should get the web repo aligned so that we can better enforce oxfmt going forward.
135 lines
4.5 KiB
TypeScript
135 lines
4.5 KiB
TypeScript
import { create } from "@bufbuild/protobuf";
|
|
import * as Protobuf from "@meshtastic/protobufs";
|
|
import { ChannelNumber, MeshRegistry } from "@meshtastic/sdk";
|
|
import { createFakeTransport } from "@meshtastic/sdk/testing";
|
|
import { act, renderHook, waitFor } from "@testing-library/react";
|
|
import { describe, expect, it } from "vitest";
|
|
import {
|
|
MeshRegistryProvider,
|
|
useChannels,
|
|
useMeshDevice,
|
|
useNode,
|
|
useNodes,
|
|
} from "../mod.ts";
|
|
|
|
function makeRegistry(deviceCount: number) {
|
|
const registry = new MeshRegistry();
|
|
const handles: ReturnType<typeof createFakeTransport>[] = [];
|
|
for (let i = 0; i < deviceCount; i++) {
|
|
const handle = createFakeTransport();
|
|
handles.push(handle);
|
|
registry.create(i + 1, { transport: handle.transport });
|
|
}
|
|
return { registry, handles };
|
|
}
|
|
|
|
describe("sdk-react under MeshRegistryProvider", () => {
|
|
it("useMeshDevice resolves through the registry's active client", async () => {
|
|
const { registry, handles } = makeRegistry(1);
|
|
const wrapper = ({ children }: { children: React.ReactNode }) => (
|
|
<MeshRegistryProvider registry={registry}>
|
|
{children}
|
|
</MeshRegistryProvider>
|
|
);
|
|
const { result } = renderHook(() => useMeshDevice(), { wrapper });
|
|
expect(result.current.myNodeNum).toBeUndefined();
|
|
|
|
await act(async () => {
|
|
handles[0]!.respond.withMyNodeInfo({ myNodeNum: 555 });
|
|
await new Promise((r) => setTimeout(r, 10));
|
|
});
|
|
await waitFor(() => expect(result.current.myNodeNum).toBe(555));
|
|
});
|
|
|
|
it("useNodes lists nodes from the active client and updates on packets", async () => {
|
|
const { registry, handles } = makeRegistry(1);
|
|
const wrapper = ({ children }: { children: React.ReactNode }) => (
|
|
<MeshRegistryProvider registry={registry}>
|
|
{children}
|
|
</MeshRegistryProvider>
|
|
);
|
|
const { result } = renderHook(() => useNodes(), { wrapper });
|
|
expect(result.current).toEqual([]);
|
|
|
|
await act(async () => {
|
|
handles[0]!.respond.withNodeInfo({ num: 7 });
|
|
await new Promise((r) => setTimeout(r, 10));
|
|
});
|
|
await waitFor(() => {
|
|
expect(result.current.map((n) => n.num)).toEqual([7]);
|
|
});
|
|
});
|
|
|
|
it("useNode selects by node number and re-renders on update", async () => {
|
|
const { registry, handles } = makeRegistry(1);
|
|
const wrapper = ({ children }: { children: React.ReactNode }) => (
|
|
<MeshRegistryProvider registry={registry}>
|
|
{children}
|
|
</MeshRegistryProvider>
|
|
);
|
|
const { result } = renderHook(() => useNode(11), { wrapper });
|
|
expect(result.current).toBeUndefined();
|
|
|
|
await act(async () => {
|
|
handles[0]!.respond.withNodeInfo({ num: 11, isFavorite: true });
|
|
await new Promise((r) => setTimeout(r, 10));
|
|
});
|
|
await waitFor(() => {
|
|
expect(result.current?.isFavorite).toBe(true);
|
|
});
|
|
});
|
|
|
|
it("useChannels reflects channel packets dispatched on the active client", async () => {
|
|
const { registry } = makeRegistry(1);
|
|
const client = registry.active.value;
|
|
if (!client) throw new Error("expected an active client");
|
|
|
|
const wrapper = ({ children }: { children: React.ReactNode }) => (
|
|
<MeshRegistryProvider registry={registry}>
|
|
{children}
|
|
</MeshRegistryProvider>
|
|
);
|
|
const { result } = renderHook(() => useChannels(), { wrapper });
|
|
expect(result.current).toEqual([]);
|
|
|
|
await act(async () => {
|
|
client.events.onChannelPacket.dispatch(
|
|
create(Protobuf.Channel.ChannelSchema, {
|
|
index: 0,
|
|
role: Protobuf.Channel.Channel_Role.PRIMARY,
|
|
}),
|
|
);
|
|
});
|
|
await waitFor(() => {
|
|
expect(result.current.length).toBe(1);
|
|
});
|
|
});
|
|
|
|
it("switches active client and re-renders against the new device", async () => {
|
|
const { registry, handles } = makeRegistry(2);
|
|
|
|
const wrapper = ({ children }: { children: React.ReactNode }) => (
|
|
<MeshRegistryProvider registry={registry}>
|
|
{children}
|
|
</MeshRegistryProvider>
|
|
);
|
|
const { result } = renderHook(() => useMeshDevice(), { wrapper });
|
|
|
|
await act(async () => {
|
|
handles[0]!.respond.withMyNodeInfo({ myNodeNum: 1 });
|
|
handles[1]!.respond.withMyNodeInfo({ myNodeNum: 2 });
|
|
await new Promise((r) => setTimeout(r, 10));
|
|
});
|
|
await waitFor(() => expect(result.current.myNodeNum).toBe(1));
|
|
|
|
await act(async () => {
|
|
registry.setActive(2);
|
|
});
|
|
await waitFor(() => expect(result.current.myNodeNum).toBe(2));
|
|
});
|
|
|
|
it("ChannelNumber enum exported as a value", () => {
|
|
expect(ChannelNumber.Primary).toBe(0);
|
|
});
|
|
});
|