fix record not found error handling

This commit is contained in:
Evan Jarrett
2025-10-13 11:24:59 -05:00
parent 8c048d6279
commit 4dc66c09a9
5 changed files with 28 additions and 30 deletions

View File

@@ -4,6 +4,7 @@ import (
"context"
"database/sql"
"encoding/json"
"errors"
"fmt"
"log"
"net/http"
@@ -123,7 +124,7 @@ func (h *UnstarRepositoryHandler) ServeHTTP(w http.ResponseWriter, r *http.Reque
err = pdsClient.DeleteRecord(r.Context(), atproto.StarCollection, rkey)
if err != nil {
// If record doesn't exist, still return success (idempotent)
if err.Error() != "record not found" {
if !errors.Is(err, atproto.ErrRecordNotFound) {
log.Printf("UnstarRepository: Failed to delete star record: %v", err)
http.Error(w, fmt.Sprintf("Failed to delete star: %v", err), http.StatusInternalServerError)
return

View File

@@ -5,6 +5,7 @@ import (
"context"
"encoding/base64"
"encoding/json"
"errors"
"fmt"
"io"
"net/http"
@@ -13,6 +14,11 @@ import (
"github.com/bluesky-social/indigo/atproto/client"
)
// Sentinel errors
var (
ErrRecordNotFound = errors.New("record not found")
)
// Client wraps ATProto operations for the registry
type Client struct {
pdsEndpoint string
@@ -118,8 +124,12 @@ func (c *Client) GetRecord(ctx context.Context, collection, rkey string) (*Recor
var result Record
err := c.indigoClient.Get(ctx, "com.atproto.repo.getRecord", params, &result)
if err != nil {
if strings.Contains(err.Error(), "404") || strings.Contains(err.Error(), "not found") {
return nil, fmt.Errorf("record not found")
// Check for RecordNotFound error from indigo's APIError type
var apiErr *client.APIError
if errors.As(err, &apiErr) {
if apiErr.StatusCode == 404 || apiErr.Name == "RecordNotFound" {
return nil, ErrRecordNotFound
}
}
return nil, fmt.Errorf("getRecord failed: %w", err)
}
@@ -148,12 +158,17 @@ func (c *Client) GetRecord(ctx context.Context, collection, rkey string) (*Recor
defer resp.Body.Close()
if resp.StatusCode == http.StatusNotFound {
return nil, fmt.Errorf("record not found")
return nil, ErrRecordNotFound
}
if resp.StatusCode != http.StatusOK {
bodyBytes, _ := io.ReadAll(resp.Body)
return nil, fmt.Errorf("get record failed with status %d: %s", resp.StatusCode, string(bodyBytes))
bodyStr := string(bodyBytes)
// Check for RecordNotFound error (PDS returns 400 with this error)
if strings.Contains(bodyStr, "RecordNotFound") {
return nil, ErrRecordNotFound
}
return nil, fmt.Errorf("get record failed with status %d: %s", resp.StatusCode, bodyStr)
}
var result Record

View File

@@ -3,6 +3,7 @@ package atproto
import (
"context"
"encoding/json"
"errors"
"fmt"
"maps"
"strings"
@@ -47,7 +48,7 @@ func (s *ManifestStore) Exists(ctx context.Context, dgst digest.Digest) (bool, e
_, err := s.client.GetRecord(ctx, ManifestCollection, rkey)
if err != nil {
// If not found, return false without error
if err.Error() == "record not found" {
if errors.Is(err, ErrRecordNotFound) {
return false, nil
}
return false, err

View File

@@ -3,6 +3,7 @@ package atproto
import (
"context"
"encoding/json"
"errors"
"fmt"
)
@@ -63,28 +64,7 @@ func UpdateProfile(ctx context.Context, client *Client, profile *SailorProfileRe
return nil
}
// isNotFoundError checks if an error is a 404 not found error
// isNotFoundError checks if an error is a record not found error
func isNotFoundError(err error) bool {
// This is a simple check - in practice, you might need to parse the error more carefully
if err == nil {
return false
}
errStr := err.Error()
return contains(errStr, "404") || contains(errStr, "not found") || contains(errStr, "RecordNotFound")
}
// contains checks if a string contains a substring (case-insensitive helper)
func contains(s, substr string) bool {
return len(s) >= len(substr) && (s == substr || len(s) > len(substr) &&
(s[:len(substr)] == substr || s[len(s)-len(substr):] == substr ||
findSubstring(s, substr)))
}
func findSubstring(s, substr string) bool {
for i := 0; i <= len(s)-len(substr); i++ {
if s[i:i+len(substr)] == substr {
return true
}
}
return false
return errors.Is(err, ErrRecordNotFound)
}

View File

@@ -3,6 +3,7 @@ package hold
import (
"context"
"encoding/json"
"errors"
"fmt"
"log"
"net/http"
@@ -288,7 +289,7 @@ func (s *HoldService) hasAllowAllCrewRecord() (bool, error) {
record, err := client.GetRecord(ctx, atproto.HoldCrewCollection, "allow-all")
if err != nil {
// Record doesn't exist
if strings.Contains(err.Error(), "not found") {
if errors.Is(err, atproto.ErrRecordNotFound) {
return false, nil
}
return false, fmt.Errorf("failed to get crew record: %w", err)