fix(web): confirm sidebar gateway restart and use DS checkboxes

Prompt before restarting from the sidebar system menu, and replace native
checkboxes on the System page with the design-system Checkbox component.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
Austin Pickett 2026-06-29 09:15:28 -04:00 committed by Teknium
parent 1abf0c6cbf
commit dbe92b9ed1
4 changed files with 62 additions and 14 deletions

View file

@ -58,6 +58,7 @@ import { Button } from "@nous-research/ui/ui/components/button";
import { SelectionSwitcher } from "@nous-research/ui/ui/components/selection-switcher";
import { Spinner } from "@nous-research/ui/ui/components/spinner";
import { Typography } from "@nous-research/ui/ui/components/typography/index";
import { ConfirmDialog } from "@nous-research/ui/ui/components/confirm-dialog";
import { cn } from "@/lib/utils";
import { SidebarFooter } from "@/components/SidebarFooter";
import { SidebarStatusStrip, gatewayLine } from "@/components/SidebarStatusStrip";
@ -901,6 +902,7 @@ function SidebarSystemActions({
const { activeAction, isBusy, isRunning, pendingAction, runAction } =
useSystemActions();
const canUpdateHermes = status?.can_update_hermes === true;
const [restartConfirmOpen, setRestartConfirmOpen] = useState(false);
const items: SystemActionItem[] = [
{
@ -923,12 +925,24 @@ function SidebarSystemActions({
const handleClick = (action: SystemAction) => {
if (isBusy) return;
if (action === "restart") {
setRestartConfirmOpen(true);
return;
}
void runAction(action);
navigate("/sessions");
onNavigate();
};
const confirmRestart = () => {
setRestartConfirmOpen(false);
void runAction("restart");
navigate("/sessions");
onNavigate();
};
return (
<>
<div
className={cn(
"shrink-0 flex flex-col",
@ -967,6 +981,23 @@ function SidebarSystemActions({
))}
</ul>
</div>
<ConfirmDialog
cancelLabel={t.common.cancel}
confirmLabel={t.status.restartGateway}
description={
t.status.restartGatewayConfirmMessage ??
"This restarts the Hermes gateway process. Connected channels and active sessions will reconnect afterward."
}
loading={pendingAction === "restart"}
onCancel={() => setRestartConfirmOpen(false)}
onConfirm={confirmRestart}
open={restartConfirmOpen}
title={
t.status.restartGatewayConfirmTitle ?? `${t.status.restartGateway}?`
}
/>
</>
);
}

View file

@ -121,6 +121,9 @@ export const en: Translations = {
platformError: "error",
recentSessions: "Recent Sessions",
restartGateway: "Restart Gateway",
restartGatewayConfirmMessage:
"This restarts the Hermes gateway process. Connected channels and active sessions will reconnect afterward.",
restartGatewayConfirmTitle: "Restart gateway?",
restartingGateway: "Restarting gateway…",
running: "Running",
runningRemote: "Running (remote)",

View file

@ -139,6 +139,8 @@ export interface Translations {
activeSessions: string;
recentSessions: string;
restartGateway: string;
restartGatewayConfirmMessage?: string;
restartGatewayConfirmTitle?: string;
restartingGateway: string;
running: string;
runningRemote: string;

View file

@ -32,6 +32,7 @@ import { Button } from "@nous-research/ui/ui/components/button";
import { Spinner } from "@nous-research/ui/ui/components/spinner";
import { H2 } from "@nous-research/ui/ui/components/typography/h2";
import { Card, CardContent } from "@nous-research/ui/ui/components/card";
import { Checkbox } from "@nous-research/ui/ui/components/checkbox";
import { Input } from "@nous-research/ui/ui/components/input";
import { Label } from "@nous-research/ui/ui/components/label";
import { Select, SelectOption } from "@nous-research/ui/ui/components/select";
@ -749,15 +750,21 @@ export default function SystemPage() {
/>
</div>
</div>
<label className="flex items-center gap-2 text-sm text-muted-foreground">
<input
type="checkbox"
<div className="flex items-center gap-2.5">
<Checkbox
checked={hookApprove}
onChange={(e) => setHookApprove(e.target.checked)}
id="hook-approve"
onCheckedChange={(checked) => setHookApprove(checked === true)}
/>
Approve now (grant consent so it fires; otherwise it stays
configured but inactive)
</label>
<Label
className="cursor-pointer text-sm font-normal normal-case tracking-normal text-muted-foreground"
htmlFor="hook-approve"
>
Approve now (grant consent so it fires; otherwise it stays
configured but inactive)
</Label>
</div>
<p className="text-xs text-warning">
Shell hooks run arbitrary commands on this host. Only add scripts
you trust. Takes effect on the next gateway/session restart.
@ -1325,16 +1332,21 @@ export default function SystemPage() {
</Button>
</div>
<label className="flex items-center gap-2 text-xs text-muted-foreground select-none">
<input
type="checkbox"
className="accent-current"
<div className="flex items-center gap-2.5">
<Checkbox
checked={shareRedact}
disabled={sharing}
onChange={(e) => setShareRedact(e.target.checked)}
id="share-redact"
onCheckedChange={(checked) => setShareRedact(checked === true)}
/>
Redact credential-shaped tokens before upload (recommended)
</label>
<Label
className="cursor-pointer select-none text-xs font-normal normal-case tracking-normal text-muted-foreground"
htmlFor="share-redact"
>
Redact credential-shaped tokens before upload (recommended)
</Label>
</div>
{shareResult && (
<div className="flex flex-col gap-2 border-t border-border pt-3">