Skip to content

audit: read-only droplet-drift checker (issue #38)#40

Merged
mfwolffe merged 1 commit into
trunkfrom
chore/droplet-drift-audit-script
May 10, 2026
Merged

audit: read-only droplet-drift checker (issue #38)#40
mfwolffe merged 1 commit into
trunkfrom
chore/droplet-drift-audit-script

Conversation

@espadonne
Copy link
Copy Markdown
Contributor

Summary

Stopgap tool for issue #38: a read-only script that compares every file the ansible roles claim to manage against what's actually on shithub-prod, in a single ssh round-trip. Reports OK / DRIFT / MISSING / TEMPLATE per path.

`copy:` files (no templating) are diffed by md5. `template:` files are listed with stat info — comparing rendered output requires inventory vars we don't have locally.

What it caught (and we already fixed in this pass)

Three drifted files. PR #21's path fix and PR #15's aide exclusions had landed in the repo but never reached the droplet:

File Source Reason
`/usr/local/bin/shithub-backup-daily` PR #21 rclone config path moved, script never redeployed
`/usr/local/bin/shithub-spaces-sync` PR #21 same
`/usr/local/bin/shithub-ssh-authkeys` initial deploy of PR #26 comments tightened in repo, droplet kept old
`/var/lib/git/git-shell-commands/shithubd` initial deploy of PR #26 same
`/etc/aide/aide.conf.d/99_shithub_exclude` PR #15 excludes for postgres + sysstat log churn — droplet was firing nightly false alarms

All five files now match between repo and droplet.

How to use

```sh
deploy/audit/check-droplet-drift.sh

Exit 0: no drift on copy: files

Exit 1: drift detected (eyeball template rows manually)

Exit 2: ssh failure

```

Followup

This script is a stopgap; it does not solve issue #38. The decision between "make ansible authoritative" vs "drop ansible" is still pending.

After every PR that touches `deploy/ansible/`, run this and fix any drift before closing the loop. Eventually a `make audit` target or CI check should run it, but that requires CI to have an ssh key to prod which is its own decision.

Compares md5 of every file the ansible roles install against the
live droplet over a single ssh round-trip. TEMPLATE rows (those
rendered from .j2 with inventory vars) are reported with stat
info but not auto-diffed.

Run after any PR that touches deploy/ansible/ to surface what
needs to be pushed manually until we resolve the broader ansible
ownership question (issue #38).
@mfwolffe mfwolffe merged commit 450adaa into trunk May 10, 2026
1 check passed
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.

2 participants