package console import ( "context" "strings" "testing" "time" "github.com/carlosframework/platform/internal/provision" "github.com/carlosframework/platform/internal/release" ) // codex R2-6: shapes that never inherit the app default are not listed; // a no-region socket-backed instance created after the app is. func TestPlacementDiscrepancyLog(t *testing.T) { fx := newConsoleFixture(t) fx.srv.cfg.HomeRegion = "ie" created := time.Now().Add(-time.Hour) fx.st.CreateAppInRegion(OpsAccountID, "blog", "p@k.dev", "uk", "chosen", created) ctx := context.Background() put := func(r provision.Record) { r.Schema, r.App, r.Account, r.Channel, r.CreatedAt = 1, "blog", release.OpsAccount, "stable", time.Now() if err := provision.CreateRecord(ctx, fx.rel, r); err != nil { t.Fatal(err) } } put(provision.Record{Host: "blog.go.tito.io", Kind: "static"}) put(provision.Record{Host: "svc.go.tito.io", Kind: "service", Addrs: []string{"10.0.0.4:8080"}}) put(provision.Record{Host: "r.go.tito.io", Region: "au", Role: "replica"}) put(provision.Record{Host: "pooled.go.tito.io", Pool: "tito"}) put(provision.Record{Host: "uk.go.tito.io", Region: "uk"}) put(provision.Record{Host: "drift.go.tito.io"}) var logs strings.Builder restore := captureLogTo(&logs) fx.srv.LogPlacementDiscrepancies(ctx) restore() out := logs.String() if !strings.Contains(out, msgPlacementDiscrepancy("drift.go.tito.io", "blog", "uk")) { t.Fatalf("drift not listed: %s", out) } for _, quiet := range []string{"blog.go.tito.io", "svc.go.tito.io", "r.go.tito.io", "pooled.go.tito.io", "uk.go.tito.io"} { if strings.Contains(out, quiet+" of") { t.Errorf("%s listed", quiet) } } } // A record older than its app cannot be the roll-forward's work, so it is // not listed. func TestPlacementDiscrepancyLogSkipsRecordsOlderThanTheApp(t *testing.T) { fx := newConsoleFixture(t) fx.st.CreateAppInRegion(OpsAccountID, "blog", "p@k.dev", "uk", "chosen", time.Now().Add(-time.Hour)) ctx := context.Background() err := provision.CreateRecord(ctx, fx.rel, provision.Record{ Schema: 1, Host: "old.go.tito.io", App: "blog", Account: release.OpsAccount, Channel: "stable", CreatedAt: time.Now().Add(-2 * time.Hour), }) if err != nil { t.Fatal(err) } var logs strings.Builder restore := captureLogTo(&logs) fx.srv.LogPlacementDiscrepancies(ctx) restore() if strings.Contains(logs.String(), "old.go.tito.io") { t.Fatalf("older record listed: %s", logs.String()) } } // A bucket that cannot be listed is logged (O18) and never fails or panics: // the check is advisory. func TestPlacementDiscrepancyLogListError(t *testing.T) { fx := newConsoleFixture(t) fx.st.CreateAppInRegion(OpsAccountID, "blog", "p@k.dev", "uk", "chosen", time.Now()) fx.srv.cfg.Releases = failingList{fx.rel} var logs strings.Builder restore := captureLogTo(&logs) fx.srv.LogPlacementDiscrepancies(context.Background()) restore() want := "console: placement discrepancy check " + release.OpsAccount + "/blog: bucket unreachable" if !strings.Contains(logs.String(), want) { t.Fatalf("want %q in %s", want, logs.String()) } } // Past the cap the check says so (O9) instead of silently stopping. func TestPlacementDiscrepancyLogTruncated(t *testing.T) { fx := newConsoleFixture(t) fx.st.CreateAppInRegion(OpsAccountID, "blog", "p@k.dev", "uk", "chosen", time.Now().Add(-time.Hour)) ctx := context.Background() for _, h := range []string{"a.go.tito.io", "b.go.tito.io"} { err := provision.CreateRecord(ctx, fx.rel, provision.Record{ Schema: 1, Host: h, App: "blog", Account: release.OpsAccount, Channel: "stable", CreatedAt: time.Now(), }) if err != nil { t.Fatal(err) } } var logs strings.Builder restore := captureLogTo(&logs) fx.srv.logPlacementDiscrepancies(ctx, 1) restore() want := "console: placement discrepancy check " + release.OpsAccount + "/blog: only the first 1 records were checked" if !strings.Contains(logs.String(), want) { t.Fatalf("want %q in %s", want, logs.String()) } } // No deployment bucket: nothing to check, nothing logged. func TestPlacementDiscrepancyLogNoBucket(t *testing.T) { fx := newConsoleFixture(t) fx.srv.cfg.Releases = nil var logs strings.Builder restore := captureLogTo(&logs) fx.srv.LogPlacementDiscrepancies(context.Background()) restore() if logs.Len() != 0 { t.Fatalf("logged: %s", logs.String()) } }