← all releases

v1.3.0

on GitHub

Not the newest. v1.5.1 is out →

Release notes

Added

  • Service health checks: an optional [services.<name>.health_check] command decides when an instance is healthy and stops it as unhealthy when it keeps failing, so restart brings it back. It reuses task keys (cron, timeout, failures, retry_*).
  • Release tarballs, checksums and Docker images now ship with signed build provenance you can check with gh attestation verify.
  • failures accepts output:<regex> tokens: a run whose stdout or stderr matches the pattern is marked failed, even if it exits 0. For example, failures = ["+output:(?i)error"].
  • Pause a cron task’s schedule from the schedule chip on its Web UI page, p in the TUI, runwisp pause/resume, or POST /api/tasks/{task}/pause and .../resume. Skipped ticks are not caught up, manual runs still work, and the pause survives reloads and restarts. Needs manual_trigger = true; runwisp status lists paused tasks.
  • runwisp logs <target...> prints the output of tasks, services, and runs from the CLI (-n N for the last lines, -n +N for the first), or follows it live with -f. --json prints one record per line for scripts.

Changed

  • TUI status messages now appear as a toast in the bottom-right corner, red for failures, instead of in the help bar.

Fixed

  • runwisp run no longer gives up on a task that prints nothing for hours and exits 0 while it is still running.
  • After runwisp takeover, if systemd gives up restarting RunWisp, cron is unmasked and started again, so the box is never left without a scheduler.
  • Uninstalling or rolling back a take-over restores cron to the state it was in before: a cron you had masked stays masked, and a stopped one is not started.
  • The daemon now exits non-zero when it shuts down because of a fatal error (the server failing to start, a crash in a background worker), so systemd and launchd restart it. runwisp stop and SIGTERM still exit 0.
  • Config and crontab edits (import, takeover, promote) are now power-loss safe, write through a symlinked runwisp.toml instead of replacing the link, and keep the file’s owner when run as root.
  • The headless startup warning about a generated password no longer claims the Web UI can’t be logged into; it points to runwisp password.
  • runwisp takeover now warns when a crontab sets MAILTO that cron mail stops, and points to notifications.
  • The advice for held cron jobs now says to disable cron, not just stop it. A stopped cron that is still enabled kept the jobs held with nothing running them.
  • On WSL and in containers where systemd isn’t running, RunWisp no longer trusts systemctl to decide whether cron is live, so a running cron keeps its jobs held instead of both schedulers running them.
  • The live event stream no longer drops an event published at the moment a web UI tab or the TUI connects, so a run starting right then shows up without a refresh.
  • run_on_start = "boot" runs a task once per machine boot, or per container start, instead of on every daemon start. true keeps its current meaning.
  • Cron @reboot jobs and systemd Type=oneshot units imported by runwisp import/takeover now use run_on_start = "boot", so a daemon restart or update no longer runs them a second time in the same boot.
  • runwisp takeover no longer says “Nothing to do” while the RunWisp service is stopped and cron is masked; it starts the service instead. runwisp stop now warns when stopping leaves cron masked by a take-over, so no jobs run.
  • runwisp import --write no longer writes a config that fails to load. When a line can’t be converted, it exits non-zero, names the line, and writes nothing.
  • A cron expression with */N in the day-of-month or day-of-week field now matches both day fields, as cron does: 0 0 */2 * 1 fires on odd days that are Mondays, not on every odd day plus every Monday. This affects [tasks.*] cron as well as imported crontabs.
  • Crontabs read by runwisp import cron or include_cron no longer turn TZ= into the task’s timezone; it goes into env, since cron only passes it to the job. CRON_TZ= is kept in env too, and sets timezone except on Debian/Ubuntu, whose cron ignores it.
  • A cron job with the same command as a job in another crontab, or for another user, now runs as its own task (renamed, like backup-zeta) in include_cron, runwisp takeover and runwisp import cron.
  • runwisp takeover now lists a symlink in /etc/cron.d as a job that won’t run and stops on it, since RunWisp doesn’t read cron sources through symlinks.
  • The TUI now shows a Delete button on failed runs, next to Retry.
  • The TUI run header fits an 80-column terminal: its Stop, Retry, and Delete buttons were pushed off-screen.
  • In the TUI, opening a notification whose run was deleted now says the run no longer exists, instead of closing the panel and showing nothing.
  • In the TUI, stopping a service from a run opened on the Home page now works.
  • In the TUI, restarting a service now leaves the old run and opens the fresh instance (or returns to the task), instead of staying on the dead run with a Stop button.
  • The Web UI task list now picks up runwisp reload without a page refresh.
  • Long task names no longer wrap onto a second line in the Web UI top bar; they are cut short instead.
  • Notifications for a run killed by log_on_full = "kill" now say so instead of reporting the kill signal’s exit code.
  • Jittered tasks that share a cron tick no longer start two at once at the tick. They now take turns whatever order the scheduler hands them over in.
All releases