44 Commits
Author SHA1 Message Date
Evan JarrettandClaude Fable 5.1 0ae9ca1a96 tests: make the carstore lock tests deterministic, and silence slog in test binaries
TestCarstoreConcurrentWritesTwoOpeners failed in CI on 2026-09-13 with
"database is locked" while the code was correct. It hammered the file with
five concurrent writers and asserted that no lock error surfaced within the
5 s busy_timeout, which on a loaded runner with every package testing in
parallel is a statement about the disk, not the code. The property it guards
(busy_timeout applied to every connection of every pool on a hold database,
c44a874) is now tested directly: one connection holds the write lock via
BEGIN IMMEDIATE, a second writer is shown to block rather than fail, and to
succeed once the lock is released. Both topologies are covered (the shared
OpenHoldDB pool, and a second opener on the same file, in both directions),
and a control shows a pool without busy_timeout fails immediately under the
same lock, so the passing tests are known to observe the mechanism.

The failure was also buried under the INFO lines every hold and PDS test
emits while booting. internal/testlog.Quiet swaps the default slog handler
for a discard handler unless the run is verbose or ATCR_TEST_LOGS is set,
and every package that produced that output now calls it from TestMain.
`go test` only shows a package's output when it fails, so this changes
nothing for passing runs and leaves a failing one readable.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Hho5da4daoCoPBJ9tCrL7s
2026-09-12 22:11:54 -05:00
Evan JarrettandClaude Opus 5 b4fccce4d1 hold: actually send subject, so the attestation scan guard can fire
The hold declines to enqueue a scan when a pushed manifest has a subject, which
is how it means to skip attestations, signatures and other referrer artifacts.
The AppView never sent one: notifyHoldAboutManifest built mediaType, config,
layers and manifests, and #manifestInfo defined only those four. So the
condition was always true, the guard never fired, and every referrer artifact
was enqueued for scanning.

The AppView already parsed subject. NewManifestRecord unmarshals it into
ManifestRecord.Subject, and Put hands that same pointer to
notifyHoldAboutManifest. The value was in scope and simply never serialized, so
this is one missing marshal step rather than a missing parse.

Adds subject to the lexicon as a #blobInfo ref, and mediaType to #blobInfo,
which config has always sent and the hold has always parsed. That only makes the
schema honest about what is already on the wire.

Hoists the hold's anonymous request struct to a named type with IsMultiArch,
IsReferrer and HasScannableContent, so the predicate is written once and
testable without standing up a HoldPDS.

Both directions degrade safely. An older hold ignores the unknown key and
behaves exactly as today, so shipping the appview alone is harmless but achieves
nothing until the hold catches up. An older appview sends no subject, leaving
the manifest enqueued as before.

Complements dfd604b rather than duplicating it. That guard lives in the scanner
after a job is created and dispatched, and catches unscannable work from any
source including the hold's proactive discovery pass. This one stops the row
being created at all, which matters because the row that froze all scanning for
nine days was exactly such an attestation. One gap neither closes: an
attestation with tar-shaped layers pushed by an old appview.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01PDqoCE1j3njokkZ9b1C5n9
2026-09-02 22:31:04 -05:00
Evan Jarrett 2eea5ff885 small fix for null columns and background pds inserts on push 2026-06-13 19:50:29 -05:00
Evan Jarrett a0cc862798 lots of new work for authenticating between appview -> hold. fixed quota handling, improve integration tests for round-trip push/pull/auth/quota checking 2026-05-11 09:20:55 -05:00
Evan Jarrett fd5bfc3c50 ui fixes for repo page, fix scanner priority, cleanup goreleaser scripts 2026-04-03 16:48:21 -05:00
Evan Jarrett 385f8987fe overhaul repo pages, add tab for 'artifacts' (tags, manifests, helm charts). implement digest page with layer commands and vuln reports 2026-03-22 21:10:47 -05:00
Evan Jarrett dc31ca2f35 more work on webhook, implement getMetadata endpoint for appview and link holds to a preferred appview 2026-02-22 22:49:33 -06:00
Evan Jarrett 33548ecf32 add scan on push to quota 2026-02-20 15:17:18 -06:00
Evan Jarrett 5615dd4132 update GC options, minor fix to scanners 2026-02-18 20:26:49 -06:00
Evan Jarrett f340158a79 tweaks related to did:plc, fix bluesky profile creation, update deploys to build locally then scp 2026-02-14 21:00:07 -06:00
Evan Jarrett de02e1f046 remove distribution from hold, add vulnerability scanning in appview.
1. Removing distribution/distribution from the Hold Service (biggest change)
  The hold service previously used distribution's StorageDriver interface for all blob operations. This replaces it with direct AWS SDK v2 calls through ATCR's own pkg/s3.S3Service:
  - New S3Service methods: Stat(), PutBytes(), Move(), Delete(), WalkBlobs(), ListPrefix() added to pkg/s3/types.go
  - Pull zone fix: Presigned URLs are now generated against the real S3 endpoint, then the host is swapped to the CDN URL post-signing (previously the CDN URL was set as the endpoint, which
  broke SigV4 signatures)
  - All hold subsystems migrated: GC, OCI uploads, XRPC handlers, profile uploads, scan broadcaster, manifest posts — all now use *s3.S3Service instead of storagedriver.StorageDriver
  - Config simplified: Removed configuration.Storage type and buildStorageConfigFromFields(); replaced with a simple S3Params() method
  - Mock expanded: MockS3Client gains an in-memory object store + 5 new methods, replacing duplicate mockStorageDriver implementations in tests (~160 lines deleted from each test file)
2. Vulnerability Scan UI in AppView (new feature)
  Displays scan results from the hold's PDS on the repository page:
  - New lexicon: io/atcr/hold/scan.json with vulnReportBlob field for storing full Grype reports
  - Two new HTMX endpoints: /api/scan-result (badge) and /api/vuln-details (modal with CVE table)
  - New templates: vuln-badge.html (severity count chips) and vuln-details.html (full CVE table with NVD/GHSA links)
  - Repository page: Lazy-loads scan badges per manifest via HTMX
  - Tests: ~590 lines of test coverage for both handlers
3. S3 Diagnostic Tool
  New cmd/s3-test/main.go (418 lines) — tests S3 connectivity with both SDK v1 and v2, including presigned URL generation, pull zone host swapping, and verbose signing debug output.
4. Deployment Tooling
  - New syncServiceUnit() for comparing/updating systemd units on servers
  - Update command now syncs config keys (adds missing keys from template) and service units with daemon-reload
5. DB Migration
  0011_fix_captain_successor_column.yaml — rebuilds hold_captain_records to add the successor column that was missed in a previous migration.
6. Documentation
  - APPVIEW-UI-FUTURE.md rewritten as a status-tracked feature inventory
  - DISTRIBUTION.md renamed to CREDENTIAL_HELPER.md
  - New REMOVING_DISTRIBUTION.md — 480-line analysis of fully removing distribution from the appview side
7. go.mod
  aws-sdk-go v1 moved from indirect to direct (needed by cmd/s3-test).
2026-02-13 15:26:24 -06:00
Evan Jarrett 2c39a78ac2 minor fixes 2026-02-04 20:14:25 -06:00
Evan Jarrett d6114cf549 implementation of syft/grype scanner as a separate binary 2026-02-04 09:53:04 -06:00
Evan Jarrett 57593a8683 remove the filesystem and buffered upload ability on the holds. going forward the only supported storage is s3. adds extra mocks and tests around uploading 2026-01-19 16:59:03 -06:00
Evan Jarrett eb3eed5f7a lint, fix repo-card styling 2026-01-14 23:18:35 -06:00
Evan Jarrett 055b34af71 varies fixes for indigo xrpc calls, avatars broken on bsku profile change, opengraph card fixes, other ui improvements 2026-01-14 23:14:43 -06:00
Evan Jarrett 3409af6c67 implement hold discovery dropdown in settings. implement a data privacy export feature 2026-01-07 22:41:14 -06:00
Evan Jarrett 9704fe091d use chi/render to simplify returned json 2026-01-06 22:47:21 -06:00
Evan Jarrett a448e8257b fix bug creating layer records on non-tagged pushes 2026-01-05 12:08:04 -06:00
Evan Jarrett 487fc8a47e wording 2026-01-04 23:37:31 -06:00
Evan Jarrett af815fbc7d use for range and wg.Go 2026-01-04 22:39:48 -06:00
Evan Jarrett aa4b32bbd6 basic implementation of quotas 2026-01-04 20:09:41 -06:00
Evan Jarrett 53e196a261 start researching quotas based on layer size per DID 2026-01-04 15:53:44 -06:00
Evan Jarrett 7dcef54d28 clean up temporary migration code 2026-01-02 17:26:50 -06:00
Evan Jarrett 1f0705a218 fix pull stats tracking 2026-01-02 13:38:46 -06:00
Evan Jarrett 88998904d6 remove auth middleware 2025-12-31 13:31:34 -06:00
Evan Jarrett 1df1bb57a4 clean up logs, delete cached data when atproto account is deleted 2025-12-31 12:21:17 -06:00
Evan Jarrett f19dfa2716 move download stats to the hold account so it can persist across different appviews 2025-12-31 11:04:15 -06:00
Evan Jarrett 23303c2187 have Holds post with new og card 2025-12-20 10:40:11 -06:00
Evan Jarrett 4063544cdf cleanup view around attestations. credential helper self upgrades. better oauth support 2025-12-18 09:33:31 -06:00
Evan Jarrett 6793ba6a50 use confidential oauth in production 2025-10-29 12:06:47 -05:00
Evan Jarrett e17600db28 slog and refactor config in appview 2025-10-25 11:00:48 -05:00
Evan Jarrett f75d9ceafb big scary refactor. sync enable_bluesky_posts with captain record. implement oauth logout handler. implement crew assignment to hold. this caused a lot of circular dependencies and needed to move functions around in order to fix 2025-10-24 23:51:32 -05:00
Evan Jarrett 0c4d1cae8f fix post schema 2025-10-24 20:27:16 -05:00
Evan Jarrett 9eb69e2ea7 more linting fixes 2025-10-24 01:05:19 -05:00
Evan Jarrett dd79b8a0ee actually wrap them in a envvar check 2025-10-23 16:43:58 -05:00
Evan Jarrett 751fa1a3f0 post to bluesky when manifests uploaded. linting fixes 2025-10-23 12:24:04 -05:00
Evan Jarrett 30ea5256f3 try and add cursor=0 to subscribe 2025-10-22 22:20:23 -05:00
Evan Jarrett 3e9a496a5d refactor how annotations are stored. add ability to create bsky profile for hold user 2025-10-22 11:08:13 -05:00
Evan Jarrett ce7160cdca add backlinks to tags 2025-10-21 09:29:40 -05:00
Evan Jarrett 5d52007104 general bug fixes 2025-10-21 09:21:51 -05:00
Evan Jarrett 965e73881b try and support multi-arch manifest types. add more unit tests. add scope for oras blobs for future proofing 2025-10-19 22:26:47 -05:00
Evan Jarrett 7228b532ba bug fixes, code cleanup, tests. trying to get multipart uploads working for the 12th time 2025-10-19 20:55:18 -05:00
Evan Jarrett 1b3a4eea47 refactor hold pkg to separate oci image endpoints 2025-10-19 17:23:46 -05:00