package httpserver import ( "context" "net/http" "net/http/httptest" "strings" "testing" "git.yuntuo.hk/k2safe/orbit/internal/retention" core "git.yuntuo.hk/k2safe/orbit/model" "git.yuntuo.hk/k2safe/orbit/platform/auth" ) type fakeRetentionStore struct { policy retention.Policy gotKey string updates int } func (f *fakeRetentionStore) GetRetentionPolicy(_ context.Context, namespace core.ID) (retention.Policy, error) { p := f.policy p.NamespaceID = namespace return p, nil } func (f *fakeRetentionStore) UpdateRetentionPolicy(_ context.Context, token auth.Token, key string, in retention.UpdateInput) (retention.Policy, error) { f.gotKey = key f.updates++ p, err := in.ToPolicy(token.NamespaceID) if err != nil { return retention.Policy{}, err } p.Revision = 1 p.Source = "database" f.policy = p return p, nil } func TestConsoleRetentionRequiresSessionAndIdempotencyKey(t *testing.T) { ns, _ := core.NewID() cred, _ := core.NewID() raw, _, err := auth.Issue(ns, cred) if err != nil { t.Fatal(err) } authStore := &fakeConsoleAuth{valid: true} retentionStore := &fakeRetentionStore{policy: retention.Defaults(ns)} server := NewWithConsoleAuth("127.0.0.1:0", nil, authStore) RegisterConsoleRetention(server, authStore, retentionStore, nil) unauthenticated := httptest.NewRequest(http.MethodGet, "/console/retention", nil) unauthenticatedRes := httptest.NewRecorder() server.Handler.ServeHTTP(unauthenticatedRes, unauthenticated) if unauthenticatedRes.Code != http.StatusUnauthorized { t.Fatalf("unauthenticated status=%d", unauthenticatedRes.Code) } body := `{"expected_revision":"0","enabled":true,"idempotency_days":90,"task_history_days":365,"workflow_history_days":365,"event_log_days":365,"delivery_history_days":90,"inbox_history_days":90,"audit_log_days":2555,"reason":"test"}` missingKey := httptest.NewRequest(http.MethodPut, "/console/retention", strings.NewReader(body)) missingKey.Header.Set("Content-Type", "application/json") missingKey.AddCookie(&http.Cookie{Name: consoleSessionCookie, Value: raw}) missingKeyRes := httptest.NewRecorder() server.Handler.ServeHTTP(missingKeyRes, missingKey) if missingKeyRes.Code != http.StatusBadRequest { t.Fatalf("missing key status=%d", missingKeyRes.Code) } req := httptest.NewRequest(http.MethodPut, "/console/retention", strings.NewReader(body)) req.Header.Set("Content-Type", "application/json") req.Header.Set("Idempotency-Key", "retention-http-1") req.AddCookie(&http.Cookie{Name: consoleSessionCookie, Value: raw}) res := httptest.NewRecorder() server.Handler.ServeHTTP(res, req) if res.Code != http.StatusOK || retentionStore.updates != 1 || retentionStore.gotKey != "retention-http-1" { t.Fatalf("update status=%d updates=%d key=%q body=%s", res.Code, retentionStore.updates, retentionStore.gotKey, res.Body.String()) } }