carlos / platform Public

provision: reconcile hands records with a run to RunSeen (run spec §5.2, codex 3)

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
claude agent, operated by paul@keymail.dev 623d89e4d5489e05b6f1fa39b2a9f6ba48baee55 parent 6638782
2 files changed, +39 −0
  • internal/provision/reconcile.go +10 −0
  • internal/provision/reconcile_test.go +29 −0

CI passed — run details

diff --git a/internal/provision/reconcile.go b/internal/provision/reconcile.go
index 70b3b0509..125691e5b 100644
--- a/internal/provision/reconcile.go
+++ b/internal/provision/reconcile.go
@@ -125,6 +125,13 @@ type ReconcileConfig struct {
// stage-requested marker: root re-judges what it staged under the new
// hold (registry.SetHold's contract, G10). Nil: nobody is told.
HoldWritten func(host string)
+ // RunSeen is called with every in-scope record of an untrashed app that
+ // carries a run, once per pass, before the pass acts on the record (run
+ // spec §5.2: pickup rides reconcile's own record reads, so an idle box
+ // pays nothing extra). It must not block: the box's runs worker only
+ // notes the record and acts after the pass, by which time a row this
+ // pass minted is in the registry. Nil: no one is told.
+ RunSeen func(rec Record)
// beforeHoldWrite is the tests' pause under the host's hold lock, just
// before holdExisting's conditional write (TestReconcileHoldWrite...).
@@ -1073,6 +1080,9 @@ func Reconcile(ctx context.Context, s release.Store, reg *registry.Registry, cfg
if trashedFor(rec.Account, rec.App) {
continue
}
+ if cfg.RunSeen != nil && rec.ActiveRun != nil {
+ cfg.RunSeen(rec)
+ }
// A mint-only fallback ("", the record-already-written-is-truth
// case) is fine here even when the manifest is unreadable this
// pass — there is no existing seed value a brand new route could
diff --git a/internal/provision/reconcile_test.go b/internal/provision/reconcile_test.go
index 51e53e7c6..6d6080a95 100644
--- a/internal/provision/reconcile_test.go
+++ b/internal/provision/reconcile_test.go
@@ -3551,3 +3551,32 @@ func TestWithHostHoldLockIsExclusivePerHost(t *testing.T) {
t.Fatal("the lock was not handed on")
}
}
+
+// Reconcile's own reads carry the runs to the box (run spec §5.2): every
+// in-scope record with a run, including one whose row this very pass
+// mints, and none out of scope.
+func TestReconcileHandsRunsToRunSeen(t *testing.T) {
+ s, sqid := setup(t)
+ withRun := acmeRecord(sqid)
+ withRun.ActiveRun = &RunState{ID: "run_abcdefghijklmnopqrstuvwxyz", State: RunQueued, Deadline: time.Now().Add(time.Minute)}
+ plain := acmeRecord(sqid)
+ plain.Host, plain.Slug = "plain.go.tito.io", "plain"
+ away := acmeRecord(sqid)
+ away.Host, away.Slug, away.Region = "away.go.tito.io", "away", "uk"
+ away.ActiveRun = withRun.ActiveRun
+ for _, rec := range []Record{withRun, plain, away} {
+ if err := CreateRecord(ctx, s, rec); err != nil {
+ t.Fatal(err)
+ }
+ }
+ var seen []string
+ cfg := ReconcileConfig{Region: "ie", Pools: []string{"tito"}, DataDir: "/data", RunSeen: func(rec Record) {
+ seen = append(seen, rec.Host+":"+rec.ActiveRun.ID)
+ }}
+ if err := Reconcile(ctx, s, regWith(t), cfg); err != nil {
+ t.Fatal(err)
+ }
+ if len(seen) != 1 || seen[0] != "acme.go.tito.io:run_abcdefghijklmnopqrstuvwxyz" {
+ t.Fatalf("RunSeen saw %q", seen)
+ }
+}