Files
fusion/packages/dashboard/app/components/ShellConnectionStatus.tsx
Fusion 9c484cf19c docs(FN-3408): document shell connection chrome contracts
- Add architecture notes describing shell connection chrome contracts
- Expand dashboard README with shell chrome expectations and integration details
- Add desktop README note aligning desktop shell behavior with documented contracts

Fusion-Task-Id: FN-3408
2026-05-08 00:40:15 -07:00

56 lines
2.3 KiB
TypeScript

import { useCallback } from "react";
import type { ShellConnectionNativeResult } from "../shell-native";
import "./ShellConnectionStatus.css";
export interface ShellConnectionStatusProps {
status: ShellConnectionNativeResult;
onError?: (message: string) => void;
}
function buildSummary(status: ShellConnectionNativeResult): { title: string; actionLabel: string; dotClassName: string } {
if (status.hostKind === "desktop-shell" && status.mode === "local") {
return { title: "Desktop local mode", actionLabel: "Switch server", dotClassName: "status-dot status-dot--online" };
}
const profileText = status.profileLabel ?? status.profileId;
const originText = status.serverOrigin;
const summary = profileText && originText ? `${profileText} · ${originText}` : profileText ?? originText;
if (status.mode === "remote") {
return {
title: summary ?? "Connection info unavailable",
actionLabel: status.hostKind === "desktop-shell" ? "Switch server" : "Manage connections",
dotClassName: summary ? "status-dot status-dot--online" : "status-dot status-dot--pending",
};
}
return {
title: summary ?? "Connection info unavailable",
actionLabel: "Manage connections",
dotClassName: summary ? "status-dot status-dot--online" : "status-dot status-dot--pending",
};
}
export function ShellConnectionStatus({ status, onError }: ShellConnectionStatusProps) {
if (status.hostKind === "browser" || !status.available) {
return null;
}
const view = buildSummary(status);
const handleClick = useCallback(async () => {
const result = await status.openConnectionManager();
if (!result.ok && result.reason === "failed") {
onError?.(result.error ?? "Failed to open connection manager");
}
}, [onError, status]);
return (
<button type="button" className="btn shell-connection-status" onClick={() => void handleClick()} data-testid="shell-connection-status-button">
<span className={view.dotClassName} aria-hidden="true" />
<span className="shell-connection-status__kind">{status.hostKind === "desktop-shell" ? "Desktop" : "Mobile"}</span>
<span className="shell-connection-status__summary" title={view.title}>{view.title}</span>
<span className="shell-connection-status__action">{view.actionLabel}</span>
</button>
);
}