Skip to content
This repository has been archived by the owner on Jun 28, 2024. It is now read-only.

Commit

Permalink
Reconnect on network change (#105)
Browse files Browse the repository at this point in the history
  • Loading branch information
kamil-stasiak authored Jun 26, 2024
1 parent 02d89a8 commit a69cdc1
Show file tree
Hide file tree
Showing 14 changed files with 630 additions and 439 deletions.
8 changes: 4 additions & 4 deletions examples/use-camera-and-microphone-example/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

26 changes: 6 additions & 20 deletions examples/use-camera-and-microphone-example/src/Badge.tsx
Original file line number Diff line number Diff line change
@@ -1,26 +1,12 @@
import type { PeerStatus } from "@fishjam-dev/react-client";

type Props = {
status: PeerStatus;
};

const getBadgeColor = (status: PeerStatus) => {
switch (status) {
case "joined":
return "badge-success";
case "error":
return "badge-error";
case "authenticated":
case "connected":
return "badge-info";
case "connecting":
return "badge-warning";
}
name: string;
status: string | null;
className: string;
};

export const Badge = ({ status }: Props) => (
export const Badge = ({ name, status, className }: Props) => (
<div className="flex items-center gap-1">
<span>Status:</span>
<span className={`badge ${getBadgeColor(status)}`}>{status}</span>
<span>{name}</span>
<span className={`badge ${className}`}>{status}</span>
</div>
);
15 changes: 14 additions & 1 deletion examples/use-camera-and-microphone-example/src/MainControls.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import {
useConnect,
useDisconnect,
useMicrophone,
useReconnection,
useScreenShare,
useSelector,
useSetupMedia,
Expand All @@ -26,6 +27,8 @@ import { AUDIO_TRACK_CONSTRAINTS, VIDEO_TRACK_CONSTRAINTS } from "@fishjam-dev/r
import { Badge } from "./Badge";
import { DeviceControls } from "./DeviceControls";
import { Radio } from "./Radio";
import { useReconnectLogs } from "./utils/useReconnectLogs";
import { getPeerStatusBadgeColor, getReconnectionStatusBadgeColor } from "./utils/BadgeUtils";

type OnDeviceChange = "remove" | "replace" | undefined;
type OnDeviceStop = "remove" | "mute" | undefined;
Expand Down Expand Up @@ -62,8 +65,12 @@ const autostartAtom = atomWithStorage<boolean>("autostart", false, undefined, {
export const MainControls = () => {
const [token, setToken] = useAtom(tokenAtom);

// for debugging
useReconnectLogs();

const connect = useConnect();
const disconnect = useDisconnect();
const reconnection = useReconnection();

const local = useSelector((s) => Object.values(s.local?.tracks || {}));
const client = useClient();
Expand Down Expand Up @@ -203,7 +210,13 @@ export const MainControls = () => {
</div>

<div className="flex w-full flex-row flex-wrap items-center gap-2">
<Badge status={status} />
<Badge name="Connection status:" status={status} className={getPeerStatusBadgeColor(status)} />

<Badge
name="Reconnection status:"
status={reconnection.status}
className={getReconnectionStatusBadgeColor(reconnection.status)}
/>

{authError && (
<div className="flex items-center gap-1">
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -61,9 +61,15 @@ export const {
useScreenShare,
useSelector,
useClient,
useReconnection,
} = create<PeerMetadata, TrackMetadata>({
peerMetadataParser: (obj) => peerMetadataSchema.parse(obj),
trackMetadataParser: (obj) => trackMetadataSchema.passthrough().parse(obj),
reconnect: {
delay: 1000,
initialDelay: 500,
maxAttempts: 1000,
},
});

export const useAuthErrorReason = () => {
Expand Down
28 changes: 28 additions & 0 deletions examples/use-camera-and-microphone-example/src/utils/BadgeUtils.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import type { PeerStatus } from "@fishjam-dev/react-client";
import type { ReconnectionStatus } from "@fishjam-dev/ts-client";

export const getPeerStatusBadgeColor = (status: PeerStatus): string => {
switch (status) {
case "joined":
return "badge-success";
case "error":
return "badge-error";
case "authenticated":
case "connected":
return "badge-info";
case "connecting":
return "badge-warning";
}
return "";
};

export const getReconnectionStatusBadgeColor = (status: ReconnectionStatus) => {
switch (status) {
case "idle":
return "badge-info";
case "error":
return "badge-error";
case "reconnecting":
return "badge-warning";
}
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
import type { ClientEvents } from "@fishjam-dev/react-client";
import type { PeerMetadata, TrackMetadata } from "../fishjamSetup";
import { useClient } from "../fishjamSetup";
import { useEffect } from "react";

/* eslint-disable no-console */
export const useReconnectLogs = () => {
const client = useClient();

useEffect(() => {
if (!client) return;

const onReconnectionStarted: ClientEvents<PeerMetadata, TrackMetadata>["reconnectionStarted"] = () => {
console.log("%c" + "reconnectionStarted", "color:green");
};

const onReconnected: ClientEvents<PeerMetadata, TrackMetadata>["reconnected"] = () => {
console.log("%cReconnected", "color:green");
};

const onReconnectionRetriesLimitReached: ClientEvents<
PeerMetadata,
TrackMetadata
>["reconnectionRetriesLimitReached"] = () => {
console.log("%cReconnectionRetriesLimitReached", "color:red");
};

const onSocketError: ClientEvents<PeerMetadata, TrackMetadata>["socketError"] = (error: Event) => {
console.warn(error);
};

const onConnectionError: ClientEvents<PeerMetadata, TrackMetadata>["connectionError"] = (error, client) => {
if (client.isReconnecting()) {
console.log("%c" + "During reconnection: connectionError %o", "color:gray", {
error,
// @ts-expect-error
iceConnectionState: error?.event?.target?.["iceConnectionState"],
});
} else {
// @ts-expect-error
console.warn({ error, state: error?.event?.target?.["iceConnectionState"] });
}
};

const onJoinError: ClientEvents<PeerMetadata, TrackMetadata>["joinError"] = (event) => {
console.log(event);
};

const onAuthError: ClientEvents<PeerMetadata, TrackMetadata>["authError"] = (reason) => {
if (client.isReconnecting()) {
console.log("%c" + "During reconnection: authError: " + reason, "color:gray");
}
};

const onSocketClose: ClientEvents<PeerMetadata, TrackMetadata>["socketClose"] = (event) => {
if (client.isReconnecting()) {
console.log("%c" + "During reconnection: Signaling socket closed", "color:gray");
} else {
console.warn(event);
}
};

client.on("reconnectionStarted", onReconnectionStarted);
client.on("reconnected", onReconnected);
client.on("reconnectionRetriesLimitReached", onReconnectionRetriesLimitReached);

client.on("socketError", onSocketError);
client.on("connectionError", onConnectionError);
client.on("joinError", onJoinError);
client.on("authError", onAuthError);
client.on("socketClose", onSocketClose);

return () => {
client.off("reconnectionStarted", onReconnectionStarted);
client.off("reconnected", onReconnected);
client.off("reconnectionRetriesLimitReached", onReconnectionRetriesLimitReached);

client.off("socketError", onSocketError);
client.off("connectionError", onConnectionError);
client.off("joinError", onJoinError);
client.off("authError", onAuthError);
client.off("socketClose", onSocketClose);
};
}, [client]);
};
43 changes: 2 additions & 41 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@
"typescript": "5.4.5"
},
"dependencies": {
"@fishjam-dev/ts-client": "github:fishjam-dev/ts-client-sdk",
"@fishjam-dev/ts-client": "github:fishjam-dev/ts-client-sdk#main",
"events": "3.3.0",
"lodash.isequal": "4.5.0"
},
Expand Down
Loading

0 comments on commit a69cdc1

Please sign in to comment.