Skip to content

Harden sync failure handling - #7

Open
paintface wants to merge 5 commits into
jonbp:masterfrom
paintface:fix/sync-failure-handling
Open

paintface wants to merge 5 commits into
jonbp:masterfrom
paintface:fix/sync-failure-handling

Conversation

@paintface

@paintface paintface commented Sep 19, 2026

Copy link
Copy Markdown
Contributor

A few ways a failed sync could pass silently, one commit each:

  • The database export/import pipe ignored its exit status — a remote wp db export dying mid-stream (dropped SSH, disk full, bad credentials) piped a truncated dump into wp db import, ran the post-sync queries against a partial database, and still finished green. The pipe now runs under set -o pipefail, a non-zero exit counts as a failed task, and the post-sync queries are skipped when the import didn't complete.
  • The remote WP-CLI check only failed on the literal string false, so an ssh failure producing no output slipped through. Anything but true now fails the check.
  • The rsync tasks didn't check their exit status, so a failed transfer still finished green. Non-zero exits now count as failed tasks, except code 24 (files vanished mid-transfer), which is routine when the live site is writing uploads during a sync.
  • The rsync paths and exclude patterns are now shell-escaped, so a project location or exclude containing a space can't split the command.
  • The backtick which checks are swapped for shell_exec() — PHP 8.5 deprecates the backtick operator, so syncs on 8.5 throw deprecation notices otherwise. Same behaviour on every PHP version.

The export/import pipeline ignored its exit status, so a failed remote
export could pipe a truncated dump into wp db import and the sync would
still report success. Run the pipe under pipefail, count a non-zero
exit as a failed task, and skip the post-sync queries when the import
didn't complete.
Only the literal string 'false' counted as a failure, so an ssh
connection that dropped after the first check and produced no output
slipped through and the sync carried on against a broken connection.
A failed rsync left no trace: the task printed its progress and the run
finished green. Non-zero exits now count as failed tasks, except code
24 (files vanished mid-transfer), which is routine when the live site
is writing uploads during the sync.
A project location, uploads folder or exclude pattern containing a
space or shell metacharacter split the rsync command apart. The remote
and local paths and each exclude are now passed through escapeshellarg.
PHP 8.5 deprecates the backtick operator, so the which pv / which
rsync checks throw deprecation notices during a sync. Backticks are an
alias for shell_exec(), so this is the same behaviour on every PHP
version, just without the notice.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant