mirror of
https://github.com/block/buzz.git
synced 2026-11-03 07:51:22 +00:00
Signed-off-by: Will Pfleger <pfleger.will@gmail.com> Co-authored-by: npub1mn7jgtj4w2pd0g0zeuhxsa6jy6p0rewxz4kujt98my82ahfmp72sxjexk7 <dcfd242e557282d7a1e2cf2e6877522682f1e5c6156dc92ca7d90eaedd3b0f95@sprout-oss.stage.blox.sqprod.co>
120 lines
3.6 KiB
TypeScript
120 lines
3.6 KiB
TypeScript
import * as React from "react";
|
|
import { openUrl } from "@tauri-apps/plugin-opener";
|
|
import { CircleArrowUp, ExternalLink } from "lucide-react";
|
|
|
|
import { useUpdaterContext } from "./hooks/UpdaterProvider";
|
|
import { shouldShowSidebarUpdateCard } from "./sidebarUpdateCardVisibility";
|
|
import { SidebarCompactActionCard } from "@/shared/ui/sidebar-action-card";
|
|
import { Spinner } from "@/shared/ui/spinner";
|
|
|
|
type SidebarUpdateCardProps = {
|
|
onDismiss: () => void;
|
|
};
|
|
|
|
type SidebarUpdateCompactCardProps = SidebarUpdateCardProps & {
|
|
actionTestId?: string;
|
|
testId?: string;
|
|
};
|
|
|
|
export function SidebarUpdateCompactCard({
|
|
actionTestId,
|
|
onDismiss,
|
|
testId = "sidebar-update-card-compact",
|
|
}: SidebarUpdateCompactCardProps) {
|
|
const { installAndRelaunch } = useUpdaterContext();
|
|
const [isUpdatePending, setIsUpdatePending] = React.useState(false);
|
|
const updatePendingRef = React.useRef(false);
|
|
const updateFrameRef = React.useRef<number | null>(null);
|
|
const updateTimeoutRef = React.useRef<number | null>(null);
|
|
|
|
React.useEffect(() => {
|
|
return () => {
|
|
if (updateFrameRef.current !== null) {
|
|
window.cancelAnimationFrame(updateFrameRef.current);
|
|
}
|
|
if (updateTimeoutRef.current !== null) {
|
|
window.clearTimeout(updateTimeoutRef.current);
|
|
}
|
|
updatePendingRef.current = false;
|
|
};
|
|
}, []);
|
|
|
|
const handleUpdate = React.useCallback(() => {
|
|
if (updatePendingRef.current) {
|
|
return;
|
|
}
|
|
|
|
updatePendingRef.current = true;
|
|
setIsUpdatePending(true);
|
|
updateFrameRef.current = window.requestAnimationFrame(() => {
|
|
updateFrameRef.current = null;
|
|
updateTimeoutRef.current = window.setTimeout(() => {
|
|
updateTimeoutRef.current = null;
|
|
void installAndRelaunch()
|
|
.catch((error) => {
|
|
console.error("[SidebarUpdateCard] update failed:", error);
|
|
})
|
|
.finally(() => {
|
|
updatePendingRef.current = false;
|
|
setIsUpdatePending(false);
|
|
});
|
|
}, 0);
|
|
});
|
|
}, [installAndRelaunch]);
|
|
|
|
return (
|
|
<SidebarCompactActionCard
|
|
actionAriaLabel="Update now"
|
|
actionDisabled={isUpdatePending}
|
|
actionTestId={actionTestId}
|
|
description={isUpdatePending ? "Updating" : "Click to update"}
|
|
dismissLabel="Dismiss update notification"
|
|
icon={
|
|
isUpdatePending ? (
|
|
<Spinner aria-hidden="true" className="h-5 w-5 border-2" />
|
|
) : (
|
|
<CircleArrowUp aria-hidden="true" className="h-5 w-5" />
|
|
)
|
|
}
|
|
iconKey={isUpdatePending ? "pending" : "idle"}
|
|
onAction={handleUpdate}
|
|
onDismiss={onDismiss}
|
|
testId={testId}
|
|
title="Ready to update!"
|
|
/>
|
|
);
|
|
}
|
|
|
|
export function SidebarUpdateCard({ onDismiss }: SidebarUpdateCardProps) {
|
|
const { status } = useUpdaterContext();
|
|
|
|
if (!shouldShowSidebarUpdateCard(status)) {
|
|
return null;
|
|
}
|
|
|
|
if (status.state === "manual-required") {
|
|
return (
|
|
<SidebarCompactActionCard
|
|
actionAriaLabel="Download update from GitHub"
|
|
actionTestId="sidebar-update-download-github"
|
|
description={`v${status.version} available — download from GitHub. Switch to AppImage for automatic updates.`}
|
|
dismissLabel="Dismiss update notification"
|
|
icon={<ExternalLink aria-hidden="true" className="h-5 w-5" />}
|
|
iconKey="manual"
|
|
onAction={() => void openUrl(status.releaseUrl)}
|
|
onDismiss={onDismiss}
|
|
testId="sidebar-update-card-manual"
|
|
title="Update available"
|
|
/>
|
|
);
|
|
}
|
|
|
|
return (
|
|
<SidebarUpdateCompactCard
|
|
actionTestId="sidebar-update-now"
|
|
onDismiss={onDismiss}
|
|
testId="sidebar-update-card"
|
|
/>
|
|
);
|
|
}
|