package main import ( "strings" "testing" ) // A console older than per-environment stores does not read ?environment= at // all: it answers about the app's OWN store, with a 200 and an ordinary body. // Every console that knows about them echoes the environment on every reply, // so a reply that does not name what we asked about is the tell. // // This matters because the verbs behind it are not all reversible: create // fixes the env prefix once granted, grant mints a bucket and an IAM user, // and rotate cycles a live credential. Acting on the wrong store and // reporting success is the failure mode being closed here. func TestStoreEnvMismatch(t *testing.T) { cases := []struct { name string reply apiStoreReply asked string wantErr bool }{ {"app store, nothing asked", apiStoreReply{Environment: ""}, "", false}, {"environment echoed back", apiStoreReply{Environment: "beta"}, "beta", false}, {"old console omits it", apiStoreReply{Environment: ""}, "beta", true}, {"answered about another environment", apiStoreReply{Environment: "alpha"}, "beta", true}, // An old console answering an app-store request is the ordinary case // and must stay silent: this guard exists for the environment ask. {"old console, app store asked", apiStoreReply{}, "", false}, } for _, tc := range cases { t.Run(tc.name, func(t *testing.T) { err := storeEnvMismatch(tc.reply, tc.asked) if tc.wantErr != (err != nil) { t.Fatalf("storeEnvMismatch(%+v, %q) = %v, wantErr %v", tc.reply, tc.asked, err, tc.wantErr) } if err == nil { return } // The sentence has to name the environment asked for and the fix, // because the caller cannot inspect what happened without the // very verb that just answered about the wrong store. for _, want := range []string{tc.asked, "older than per-environment", "Upgrade the console"} { if !strings.Contains(err.Error(), want) { t.Errorf("refusal %q does not contain %q", err, want) } } }) } }