0b70da2955
Surface the Run-now button on every schedule when the host is online,
not just enabled ones. Disabled rows render the button as a non-primary
style + a HX-confirm dialog ("This schedule is paused — running it now
won't change that. Fire it once anyway?"); enabled rows keep the
zero-friction primary button.
Server-side, Run-now no longer short-circuits on !Enabled — it
dispatches the source groups inline rather than via dispatchScheduledJob
(which always bails on disabled schedules, since cron-tick semantics
are different from explicit operator intent). The audit-log entry
inside dispatchBackupForGroup still records every fire.
85 lines
3.9 KiB
HTML
85 lines
3.9 KiB
HTML
{{define "title"}}{{.Title}}{{end}}
|
|
|
|
{{define "content"}}
|
|
{{template "host_chrome" .}}
|
|
{{$page := .Page}}
|
|
{{$host := $page.Host}}
|
|
{{$groupNames := $page.GroupNames}}
|
|
<div class="max-w-[1280px] mx-auto px-8 pb-14 pt-6">
|
|
|
|
<div class="flex items-center justify-between mb-4">
|
|
<p class="text-pretty text-[12.5px] text-ink-mute leading-[1.6] max-w-[760px]">
|
|
A schedule is a cron expression pointing at one or more source groups. When it fires, the agent runs a separate
|
|
<span class="mono text-ink-mid">restic backup</span> per chosen group — independent jobs, independent snapshots,
|
|
independent retention. Failure of one group doesn't fail the others.
|
|
</p>
|
|
<a href="/hosts/{{$host.ID}}/schedules/new" class="btn btn-primary whitespace-nowrap">+ New schedule</a>
|
|
</div>
|
|
|
|
{{if eq (len $page.Schedules) 0}}
|
|
<div class="panel rounded-[7px] empty-state" style="border-radius: 7px;">
|
|
<h3 class="text-base font-medium tracking-[-0.005em]">No schedules yet.</h3>
|
|
<p class="text-pretty text-ink-mute text-[13px] mt-2 mx-auto max-w-[480px] leading-[1.65]">
|
|
Add one and the agent will start running backups on whatever cron expression you give it.
|
|
Until then, Run-now from the Sources tab is the only way to trigger a backup.
|
|
</p>
|
|
<div class="mt-5">
|
|
<a href="/hosts/{{$host.ID}}/schedules/new" class="btn btn-primary">+ New schedule</a>
|
|
</div>
|
|
</div>
|
|
{{else}}
|
|
<div class="panel rounded-[7px] overflow-hidden">
|
|
<div class="schd-row head hairline">
|
|
<div>Status</div>
|
|
<div>Cron</div>
|
|
<div>Sources</div>
|
|
<div></div>
|
|
</div>
|
|
{{range $i, $sc := $page.Schedules}}
|
|
<div class="schd-row clickable {{if not (eq $i 0)}}hairline{{end}}">
|
|
<a href="/hosts/{{$host.ID}}/schedules/{{$sc.ID}}/edit" class="row-link" aria-label="Edit schedule">edit</a>
|
|
<div>
|
|
{{if $sc.Enabled}}
|
|
<span class="mono text-[11px] text-ok">enabled</span>
|
|
{{else}}
|
|
<span class="mono text-[11px] text-ink-fade">paused</span>
|
|
{{end}}
|
|
</div>
|
|
<div class="mono {{if $sc.Enabled}}text-ink{{else}}text-ink-mute{{end}}">{{$sc.CronExpr}}</div>
|
|
<div class="flex gap-1.5 flex-wrap">
|
|
{{range $sc.SourceGroupIDs}}
|
|
{{$name := index $groupNames .}}
|
|
<span class="tag" style="border-color: color-mix(in oklch, var(--accent), transparent 60%); color: var(--accent); {{if not $sc.Enabled}}opacity: 0.6;{{end}}">{{if $name}}{{$name}}{{else}}<span class="text-ink-fade">unknown</span>{{end}}</span>
|
|
{{end}}
|
|
</div>
|
|
<div class="flex gap-1.5 justify-end row-action">
|
|
{{if eq $host.Status "online"}}
|
|
{{if $sc.Enabled}}
|
|
<button class="btn btn-primary"
|
|
hx-post="/hosts/{{$host.ID}}/schedules/{{$sc.ID}}/run"
|
|
hx-swap="none"
|
|
hx-disabled-elt="this">Run now</button>
|
|
{{else}}
|
|
<button class="btn"
|
|
hx-post="/hosts/{{$host.ID}}/schedules/{{$sc.ID}}/run"
|
|
hx-swap="none"
|
|
hx-disabled-elt="this"
|
|
hx-confirm="This schedule is paused — running it now won't change that. Fire it once anyway?"
|
|
title="schedule is paused; click to fire one ad-hoc run anyway">Run now</button>
|
|
{{end}}
|
|
{{else}}
|
|
<button class="btn" disabled title="host is offline">Run now</button>
|
|
{{end}}
|
|
<form method="post" action="/hosts/{{$host.ID}}/schedules/{{$sc.ID}}/delete" style="display: inline;"
|
|
onsubmit="return confirm('Delete this schedule? Existing snapshots are not affected.');">
|
|
<button type="submit" class="btn btn-danger">Delete</button>
|
|
</form>
|
|
</div>
|
|
</div>
|
|
{{end}}
|
|
</div>
|
|
{{end}}
|
|
|
|
</div>
|
|
{{end}}
|