From 40b4ea32ca40ed2ce991f6415f136f6d9f25c1dc Mon Sep 17 00:00:00 2001 From: rob thijssen Date: Thu, 3 Sep 2026 13:38:09 +0300 Subject: [PATCH] deploy: restore the previous binary with install, not cp The first rollback failed with "cp: cannot create regular file '/usr/local/bin/quantus-miner': Text file busy": cp writes in place and the binary was executing. install unlinks the destination first, the same reason rsync's temp-file-and-rename push works. Sudoers grant updated and applied to benjy and quadbrat. Co-Authored-By: Claude Fable 5.1 Claude-Session: https://claude.ai/code/session_01CBgs2nSi4H2mdh8kD8vMX5 --- .gitea/workflows/deploy.yaml | 5 ++++- deploy/infra-setup.sh | 7 ++++--- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/.gitea/workflows/deploy.yaml b/.gitea/workflows/deploy.yaml index 5a92dd8..0651d53 100644 --- a/.gitea/workflows/deploy.yaml +++ b/.gitea/workflows/deploy.yaml @@ -340,7 +340,10 @@ jobs: run() { ssh $SSHOPTS gitea_ci@"${{ matrix.host }}" "$@"; } if run test -x /usr/local/bin/quantus-miner.prev; then echo "validate failed after a restart — restoring the previous binary" - run sudo cp -p /usr/local/bin/quantus-miner.prev /usr/local/bin/quantus-miner + # install, not cp: cp writes in place and fails with "Text file busy" + # on a running binary; install unlinks the destination first (the + # same reason rsync's temp-file-and-rename works for the push). + run sudo install -m 0755 /usr/local/bin/quantus-miner.prev /usr/local/bin/quantus-miner run sudo restorecon -R /usr/local/bin/quantus-miner /etc/quantus-miner /var/lib/quantus-miner run sudo systemctl restart quantus-miner.service echo "restored: $(run /usr/local/bin/quantus-miner --version)" diff --git a/deploy/infra-setup.sh b/deploy/infra-setup.sh index da55c0d..45e9281 100755 --- a/deploy/infra-setup.sh +++ b/deploy/infra-setup.sh @@ -110,11 +110,12 @@ gitea_ci ALL=(root) NOPASSWD: /usr/bin/systemctl restart quantus-miner.service # mining for a measurement window and resume it afterwards. gitea_ci ALL=(root) NOPASSWD: /usr/bin/systemctl stop quantus-miner.service gitea_ci ALL=(root) NOPASSWD: /usr/bin/systemctl start quantus-miner.service -# Rollback: the deploy keeps the previous binary as .prev and restores it when -# validate fails. Deploying from main means a bad commit reaches production; +# Rollback: the deploy keeps the previous binary as .prev (cp) and restores it +# with install when validate fails; cp back would hit "Text file busy" on the +# running binary, install unlinks the destination first. Deploying from main means a bad commit reaches production; # this is what makes that survivable. gitea_ci ALL=(root) NOPASSWD: /usr/bin/cp -p /usr/local/bin/quantus-miner /usr/local/bin/quantus-miner.prev -gitea_ci ALL=(root) NOPASSWD: /usr/bin/cp -p /usr/local/bin/quantus-miner.prev /usr/local/bin/quantus-miner +gitea_ci ALL=(root) NOPASSWD: /usr/bin/install -m 0755 /usr/local/bin/quantus-miner.prev /usr/local/bin/quantus-miner SUDO chmod 0440 "$tmp" visudo -cf "$tmp"