import { Database, Eraser, HardDrive, Pencil, Play, Square, Trash2 } from "lucide-react"; import { useMemo, useState } from "react"; import { OnOff } from "~/client/components/onoff"; import { Button } from "~/client/components/ui/button"; import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "~/client/components/ui/card"; import { AlertDialog, AlertDialogAction, AlertDialogCancel, AlertDialogContent, AlertDialogDescription, AlertDialogHeader, AlertDialogTitle, } from "~/client/components/ui/alert-dialog"; import type { BackupSchedule } from "~/client/lib/types"; import { BackupProgressCard } from "./backup-progress-card"; import { runForgetMutation } from "~/client/api-client/@tanstack/react-query.gen"; import { useMutation } from "@tanstack/react-query"; import { toast } from "sonner"; import { parseError } from "~/client/lib/errors"; import { Link } from "react-router"; type Props = { schedule: BackupSchedule; handleToggleEnabled: (enabled: boolean) => void; handleRunBackupNow: () => void; handleStopBackup: () => void; handleDeleteSchedule: () => void; setIsEditMode: (isEdit: boolean) => void; }; export const ScheduleSummary = (props: Props) => { const { schedule, handleToggleEnabled, handleRunBackupNow, handleStopBackup, handleDeleteSchedule, setIsEditMode } = props; const [showDeleteConfirm, setShowDeleteConfirm] = useState(false); const [showForgetConfirm, setShowForgetConfirm] = useState(false); const runForget = useMutation({ ...runForgetMutation(), onSuccess: () => { toast.success("Retention policy applied successfully"); }, onError: (error) => { toast.error("Failed to apply retention policy", { description: parseError(error)?.message }); }, }); const summary = useMemo(() => { const scheduleLabel = schedule ? schedule.cronExpression : "-"; const retentionParts: string[] = []; if (schedule?.retentionPolicy) { const rp = schedule.retentionPolicy; if (rp.keepLast) retentionParts.push(`${rp.keepLast} last`); if (rp.keepHourly) retentionParts.push(`${rp.keepHourly} hourly`); if (rp.keepDaily) retentionParts.push(`${rp.keepDaily} daily`); if (rp.keepWeekly) retentionParts.push(`${rp.keepWeekly} weekly`); if (rp.keepMonthly) retentionParts.push(`${rp.keepMonthly} monthly`); if (rp.keepYearly) retentionParts.push(`${rp.keepYearly} yearly`); } return { vol: schedule.volume.name, scheduleLabel, repositoryLabel: schedule.repositoryId || "No repository selected", retentionLabel: retentionParts.length > 0 ? retentionParts.join(" • ") : "No retention policy", }; }, [schedule, schedule.volume.name]); const handleConfirmDelete = () => { setShowDeleteConfirm(false); handleDeleteSchedule(); }; const handleConfirmForget = () => { setShowForgetConfirm(false); runForget.mutate({ path: { scheduleId: schedule.id.toString() } }); }; return (
{schedule.name} {schedule.volume.name} {schedule.repository.name}
{schedule.lastBackupStatus === "in_progress" ? ( ) : ( )} {schedule.retentionPolicy && ( )}

Schedule

{summary.scheduleLabel}

Repository

{schedule.repository.name}

Last backup

{schedule.lastBackupAt ? new Date(schedule.lastBackupAt).toLocaleString() : "Never"}

Next backup

{schedule.nextBackupAt ? new Date(schedule.nextBackupAt).toLocaleString() : "Never"}

Status

{schedule.lastBackupStatus === "success" && "✓ Success"} {schedule.lastBackupStatus === "error" && "✗ Error"} {schedule.lastBackupStatus === "in_progress" && "⟳ in progress..."} {schedule.lastBackupStatus === "warning" && "! Warning"} {!schedule.lastBackupStatus && "—"}

{schedule.lastBackupStatus === "warning" && (

Warning Details

Last backup completed with warnings. Check your container logs for more details.

)} {schedule.lastBackupError && (

Error Details

{schedule.lastBackupError}

)}
{schedule.lastBackupStatus === "in_progress" && } Delete backup schedule? Are you sure you want to delete this backup schedule for {schedule.volume.name}? This action cannot be undone. Existing snapshots will not be deleted.
Cancel Delete schedule
Run retention policy cleanup? This will apply the retention policy and permanently delete old snapshots according to the configured rules ({summary.retentionLabel}). This action cannot be undone.
Cancel Run cleanup
); };