Skip to content

Commit c37d5dd

Browse files
committed
fix: resolve CI failures — formatting and conformance test
- Remove extra blank line in handlers.go (gofmt) - Revert storage-level ErrSubjectNotFound mapping for soft-deleted versions; move Confluent-compatible 40401 error code mapping to handler level via isSubjectFullyDeleted helper
1 parent 7115cf4 commit c37d5dd

File tree

2 files changed

+27
-13
lines changed

2 files changed

+27
-13
lines changed

internal/api/handlers/handlers.go

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,6 @@ func (h *Handler) checkModeForWrite(r *http.Request, subject string) string {
7777
return ""
7878
}
7979

80-
8180
// resolveAlias resolves a subject alias. If the subject has an alias configured,
8281
// the alias target is returned. Otherwise the original subject is returned.
8382
// Alias resolution is single-level (no recursive chaining).
@@ -284,6 +283,12 @@ func (h *Handler) GetVersion(w http.ResponseWriter, r *http.Request) {
284283
return
285284
}
286285
if errors.Is(err, storage.ErrVersionNotFound) {
286+
// Confluent returns 40401 (subject not found) when all versions
287+
// of a subject are soft-deleted, rather than 40402 (version not found).
288+
if h.isSubjectFullyDeleted(r.Context(), subject) {
289+
writeError(w, http.StatusNotFound, types.ErrorCodeSubjectNotFound, "Subject not found")
290+
return
291+
}
287292
writeError(w, http.StatusNotFound, types.ErrorCodeVersionNotFound, "Version not found")
288293
return
289294
}
@@ -330,6 +335,23 @@ func (h *Handler) findDeletedVersion(ctx context.Context, subject string, versio
330335
return nil, storage.ErrVersionNotFound
331336
}
332337

338+
// isSubjectFullyDeleted returns true if the subject exists but all its versions
339+
// are soft-deleted. Used to map ErrVersionNotFound → 40401 (Confluent behavior).
340+
func (h *Handler) isSubjectFullyDeleted(ctx context.Context, subject string) bool {
341+
// Check if subject has any versions including deleted ones
342+
allVersions, err := h.registry.GetVersions(ctx, subject, true)
343+
if err != nil || len(allVersions) == 0 {
344+
return false
345+
}
346+
// Check if subject has any active (non-deleted) versions
347+
activeVersions, err := h.registry.GetVersions(ctx, subject, false)
348+
if err != nil {
349+
// GetVersions returns ErrSubjectNotFound when all versions are deleted
350+
return errors.Is(err, storage.ErrSubjectNotFound)
351+
}
352+
return len(activeVersions) == 0
353+
}
354+
333355
// RegisterSchema handles POST /subjects/{subject}/versions
334356
func (h *Handler) RegisterSchema(w http.ResponseWriter, r *http.Request) {
335357
subject := h.resolveAlias(r.Context(), chi.URLParam(r, "subject"))
@@ -1150,6 +1172,10 @@ func (h *Handler) GetRawSchemaByVersion(w http.ResponseWriter, r *http.Request)
11501172
return
11511173
}
11521174
if errors.Is(err, storage.ErrVersionNotFound) {
1175+
if h.isSubjectFullyDeleted(r.Context(), subject) {
1176+
writeError(w, http.StatusNotFound, types.ErrorCodeSubjectNotFound, "Subject not found")
1177+
return
1178+
}
11531179
writeError(w, http.StatusNotFound, types.ErrorCodeVersionNotFound, "Version not found")
11541180
return
11551181
}

internal/storage/memory/store.go

Lines changed: 0 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -212,18 +212,6 @@ func (s *Store) GetSchemaBySubjectVersion(ctx context.Context, subject string, v
212212
}
213213

214214
if info.deleted {
215-
// If ALL versions of this subject are deleted, treat the subject as not found
216-
// (matches Confluent behavior: 40401 instead of 40402).
217-
hasActive := false
218-
for _, vi := range subjectVersionMap {
219-
if !vi.deleted {
220-
hasActive = true
221-
break
222-
}
223-
}
224-
if !hasActive {
225-
return nil, storage.ErrSubjectNotFound
226-
}
227215
return nil, storage.ErrVersionNotFound
228216
}
229217

0 commit comments

Comments
 (0)