Skip to content

v1.3.15 — Sanitize operator data from public sources

Note: this file is excluded from scripts/check-no-personal-data.sh by design — it documents the sanitization patch and must name the patterns it scrubbed. The exclusion is narrow (only this file + the script itself).

Security / hygiene patch. Scrubs operator-specific data that the v1.3.2-v1.3.14 dogfood pass leaked into committed release notes, CHANGELOG, ARCHITECTURE.md, a few code fixtures, and one frontend hint string. Adds a guardrail to keep it out going forward.

Why

argos-edge is a public repo (github.com/cmos486/argos-edge). Across roughly a dozen release-note files committed during the v1.3.2-v1.3.14 cycle, smoke-test sessions captured the maintainer's actual homelab deployment verbatim:

  • per-service subdomains (archive.cmos486.es, casa.cmos486.es, unifi.cmos486.es, ...) -- a fingerprint of what's running inside the maintainer's network
  • internal LAN IPs (192.168.3.156, 192.168.3.161, ...) -- topology hints
  • one Go comment + one frontend hint string referencing the apex domain as an example

None of this is critical attack-surface data on its own, but publishing the catalogue of services + addresses on a public repo is a courtesy lapse and a small attack-surface boost. The v1.3.15 patch removes it from the committed sources and wires in a CI check so the next dogfood pass can't regress it.

What was changed

Domain mappings (RFC 2606 placeholders)

Original (private) Replacement
archive.cmos486.es app.example.com
bookmarks.cmos486.es bookmarks.example.com
casa.cmos486.es home.example.com
emby.cmos486.es media.example.com
fotos.cmos486.es photos.example.com
huntlo.cmos486.es marketplace.example.com
instaplanner.cmos486.es planner.example.com
iot.cmos486.es iot.example.com
koi.cmos486.es fish-tracker.example.com
links.cmos486.es links.example.com
m3u.cmos486.es iptv.example.com
pad.cmos486.es notes.example.com
photo-quiz.cmos486.es quiz.example.com
plex.cmos486.es streaming.example.com
smokeping.cmos486.es ping-monitor.example.com
storage.cmos486.es storage.example.com
sync.cmos486.es sync.example.com
unifi.cmos486.es network-controller.example.com
uptime.cmos486.es uptime.example.com
urbex.cmos486.es mapping.example.com
any other *.cmos486.es app.example.com (catch-all)
*.cmos486.es (wildcard cert) *.example.com
bare cmos486.es (apex; not cmos486.github.io) example.com

IP mappings (RFC 5737 documentation ranges)

Original Replacement
192.168.3.X (services LAN) 192.0.2.X (last octet preserved)
192.168.5.X (client side) 198.51.100.X (last octet preserved)

Last octet is preserved so distinct hosts in worked examples stay visually distinct.

Files touched

File Why it was hit
CHANGELOG.md smoke output blocks
docs/release-notes/v1.3.2.md subdomain in repro
docs/release-notes/v1.3.7.md LAN IP in JSON example
docs/release-notes/v1.3.8.md RFC range string is fine; nothing actually changed here -- swept anyway
docs/release-notes/v1.3.12.md several smoke-test code blocks
docs/release-notes/v1.3.14.md WS smoke-test block
docs/release-notes/v1.0.0.md v1.1.0.md v1.0.1.md v1.3.0.md v1.3.1.md v1.2.0.md prereleases/v1.3.0-alpha.md prereleases/v1.3.0-beta.md repo-link footers (no operator data; not modified)
docs/phase1-dns.md testbed subdomain + IP
ARCHITECTURE.md foo.cmos486.es example
frontend/src/components/SSOSection.tsx UI hint string used the apex
backend/internal/oidc/config.go comment referenced apex as example
backend/internal/notifications/events.go sample event payload had operator IP
backend/internal/api/oidc_test.go test fixtures used the apex
backend/internal/api/target_health_test.go log-fixture lines used operator IPs

What was NOT touched (intentional)

  • Go module path github.com/cmos486/argos-edge -- the actual public repo URL; required by every Go import and by the README shield badges.
  • mkdocs.yml site_url: https://cmos486.github.io/argos-edge/, repo_url, repo_name, site_author: cmos486 -- the literal published-docs-portal config.
  • README.md badge URLs and the "edit this page" links -- intentional canonical references to the public repo.
  • All commit messages and authors. Rewriting history would break already-published GitHub release tags and any third-party bookmarks pointing at them.

The reasoning: cmos486 as a GitHub handle bound to this repo is the URL anyone reaches the project through. Scrubbing the handle would defeat its own purpose -- the next visitor would just look at the URL bar.

Operator action required

The committed release notes are now sanitized. The corresponding release bodies on GitHub are independent artifacts that the maintainer typed once when publishing each tag. They still contain the original operator data.

Re-edit each release body manually at:

(The other v1.3.X tags either contained no operator-specific data in their published body, or the body was already a copy-paste of the now-sanitized release-notes file. Spot-check each before saving.)

The simplest workflow: copy the body of the new docs/release-notes/v1.3.X.md (now sanitized) into the GitHub release-edit form and save.

Guardrail

scripts/check-no-personal-data.sh is a small grep-based check that fails non-zero on:

  1. cmos486.es subdomains or apex (excluding the cmos486.github.io docs URL).
  2. 192.168.3.X / 192.168.5.X LAN IPs.
  3. discodurovirtualk email handle.

.github/workflows/personal-data-guardrail.yml runs it on every push to main and every PR. CI fails if a future change re-introduces any of the three patterns.

To run locally:

./scripts/check-no-personal-data.sh

CONTRIBUTING.md

New file documenting the placeholder convention for future contributors / future-self:

  • Domains: example.com, *.example.com (RFC 2606)
  • LAN IPs: 192.0.2.X, 198.51.100.X, 203.0.113.X (RFC 5737)
  • Emails: ops@example.com, admin@example.com, user@example.com
  • And the explicit list of public references (Go module path, docs portal URL, mkdocs config) that stay un-scrubbed by design.

The doc is excluded from the rendered mkdocs site (it's contributor-facing, not operator-facing) but lives in docs/ for GitHub-side discoverability.

Files (5 commits)

Commit Files
security: sanitize operator hostnames and IPs from release notes (v1.3.2-v1.3.14) docs/release-notes/*.md, ARCHITECTURE.md, docs/phase1-dns.md, frontend SSOSection, oidc/config.go, notifications/events.go, oidc_test.go, target_health_test.go
security: sanitize CHANGELOG.md operator references CHANGELOG.md only
ci: add check-no-personal-data guardrail scripts/check-no-personal-data.sh, .github/workflows/personal-data-guardrail.yml
docs(contributing): operator data sanitization rules docs/CONTRIBUTING.md, mkdocs.yml exclude_docs
chore: bump version to 1.3.15 + CHANGELOG + release notes backend/cmd/argos/main.go, frontend/package.json, CHANGELOG.md (this entry), docs/release-notes/v1.3.15.md, mkdocs.yml nav

Verification

scripts/check-no-personal-data.sh -> [OK] no operator-specific data found in committed sources. go build ./..., go test ./..., go vet ./..., npm run build, npm run lint, mkdocs build --strict all pass post-sanitization.

Not changed

  • All v1.3.14 functional fixes (WebSocket transport, expect status messaging, AppSec block-mode CRS, panel CLI) unchanged.
  • No DB schema, no env vars, no compose surface modified.
  • Public repo URLs and the docs portal stay where they are.