A diet Tap option for handling atproto sync
17

Configure Feed

Select the types of activity you want to include in your feed.

`syntax.AtIdentifier` as simple string (#1218)

This was a clever struct wrapped, but that was weird and inconsistent
with all the other types.

This updates it to be a simple string alias type.

This is (slightly) breaking, and will require updates in downstream
packages. Particularly those doing OAuth.

authored by

bnewbold and committed by
GitHub
(Jan 20, 2026, 2:59 PM -0800) 1c2af7dd 03781188

+61 -62
+2 -2
atproto/atclient/cmd/atp-client-demo/main.go
··· 186 186 187 187 dir := identity.DefaultDirectory() 188 188 189 - c, err := atclient.LoginWithPassword(ctx, dir, *atid, cmd.String("password"), "", nil) 189 + c, err := atclient.LoginWithPassword(ctx, dir, atid, cmd.String("password"), "", nil) 190 190 if err != nil { 191 191 return err 192 192 } ··· 214 214 215 215 dir := identity.DefaultDirectory() 216 216 217 - c, err := atclient.LoginWithPassword(ctx, dir, *atid, cmd.String("password"), "", nil) 217 + c, err := atclient.LoginWithPassword(ctx, dir, atid, cmd.String("password"), "", nil) 218 218 if err != nil { 219 219 return err 220 220 }
+1 -1
atproto/auth/oauth/oauth.go
··· 538 538 if err != nil { 539 539 return "", fmt.Errorf("not a valid account identifier (%s): %w", identifier, err) 540 540 } 541 - ident, err := app.Dir.Lookup(ctx, *atid) 541 + ident, err := app.Dir.Lookup(ctx, atid) 542 542 if err != nil { 543 543 return "", fmt.Errorf("failed to resolve username (%s): %w", identifier, err) 544 544 }
+1 -1
atproto/identity/cmd/atp-id/main.go
··· 59 59 slog.Info("valid syntax", "at-identifier", id) 60 60 61 61 dir := identity.DefaultDirectory() 62 - acc, err := dir.Lookup(ctx, *id) 62 + acc, err := dir.Lookup(ctx, id) 63 63 if err != nil { 64 64 return err 65 65 }
+31 -32
atproto/syntax/atidentifier.go
··· 5 5 "strings" 6 6 ) 7 7 8 - type AtIdentifier struct { 9 - Inner interface{} 10 - } 8 + type AtIdentifier string 11 9 12 - func ParseAtIdentifier(raw string) (*AtIdentifier, error) { 10 + func ParseAtIdentifier(raw string) (AtIdentifier, error) { 13 11 if raw == "" { 14 - return nil, errors.New("expected AT account identifier, got empty string") 12 + return "", errors.New("expected AT account identifier, got empty string") 15 13 } 16 14 if strings.HasPrefix(raw, "did:") { 17 15 did, err := ParseDID(raw) 18 16 if err != nil { 19 - return nil, err 17 + return "", err 20 18 } 21 - return &AtIdentifier{Inner: did}, nil 19 + return AtIdentifier(did), nil 22 20 } 23 21 handle, err := ParseHandle(raw) 24 22 if err != nil { 25 - return nil, err 23 + return "", err 26 24 } 27 - return &AtIdentifier{Inner: handle}, nil 25 + return AtIdentifier(handle), nil 28 26 } 29 27 30 28 func (n AtIdentifier) IsHandle() bool { 31 - _, ok := n.Inner.(Handle) 32 - return ok 29 + return n != "" && !n.IsDID() 33 30 } 34 31 35 32 func (n AtIdentifier) AsHandle() (Handle, error) { 36 - handle, ok := n.Inner.(Handle) 37 - if ok { 38 - return handle, nil 33 + if n.IsHandle() { 34 + return Handle(n), nil 39 35 } 40 36 return "", errors.New("AT Identifier is not a Handle") 41 37 } 42 38 39 + func (n AtIdentifier) Handle() Handle { 40 + if n.IsHandle() { 41 + return Handle(n) 42 + } 43 + return "" 44 + } 45 + 43 46 func (n AtIdentifier) IsDID() bool { 44 - _, ok := n.Inner.(DID) 45 - return ok 47 + return strings.HasPrefix(n.String(), "did:") 46 48 } 47 49 48 50 func (n AtIdentifier) AsDID() (DID, error) { 49 - did, ok := n.Inner.(DID) 50 - if ok { 51 - return did, nil 51 + if n.IsDID() { 52 + return DID(n), nil 52 53 } 53 54 return "", errors.New("AT Identifier is not a DID") 54 55 } 55 56 57 + func (n AtIdentifier) DID() DID { 58 + if n.IsDID() { 59 + return DID(n) 60 + } 61 + return "" 62 + } 63 + 56 64 func (n AtIdentifier) Normalize() AtIdentifier { 57 - handle, ok := n.Inner.(Handle) 58 - if ok { 59 - return AtIdentifier{Inner: handle.Normalize()} 65 + if n.IsHandle() { 66 + return Handle(n).Normalize().AtIdentifier() 60 67 } 61 68 return n 62 69 } 63 70 64 71 func (n AtIdentifier) String() string { 65 - did, ok := n.Inner.(DID) 66 - if ok { 67 - return did.String() 68 - } 69 - handle, ok := n.Inner.(Handle) 70 - if ok { 71 - return handle.String() 72 - } 73 - return "" 72 + return string(n) 74 73 } 75 74 76 75 func (a AtIdentifier) MarshalText() ([]byte, error) { ··· 82 81 if err != nil { 83 82 return err 84 83 } 85 - *a = *atid 84 + *a = atid 86 85 return nil 87 86 }
+1 -1
atproto/syntax/atidentifier_test.go
··· 74 74 func TestEmpty(t *testing.T) { 75 75 assert := assert.New(t) 76 76 77 - atid := AtIdentifier{} 77 + atid := AtIdentifier("") 78 78 79 79 assert.False(atid.IsHandle()) 80 80 assert.False(atid.IsDID())
+4 -4
atproto/syntax/aturi.go
··· 51 51 parts := strings.SplitN(string(n), "/", 4) 52 52 if len(parts) < 3 { 53 53 // something has gone wrong (would not validate) 54 - return AtIdentifier{} 54 + return "" 55 55 } 56 56 atid, err := ParseAtIdentifier(parts[2]) 57 57 if err != nil { 58 - return AtIdentifier{} 58 + return "" 59 59 } 60 - return *atid 60 + return atid 61 61 } 62 62 63 63 // Returns path segment, without leading slash, as would be used in an atproto repository key. Or empty string if there is no path. ··· 102 102 103 103 func (n ATURI) Normalize() ATURI { 104 104 auth := n.Authority() 105 - if auth.Inner == nil { 105 + if auth == "" { 106 106 // invalid AT-URI; return the current value (!) 107 107 return n 108 108 }
+1 -1
atproto/syntax/did.go
··· 72 72 } 73 73 74 74 func (d DID) AtIdentifier() AtIdentifier { 75 - return AtIdentifier{Inner: d} 75 + return AtIdentifier(d) 76 76 } 77 77 78 78 func (d DID) String() string {
+1 -1
atproto/syntax/handle.go
··· 67 67 } 68 68 69 69 func (h Handle) AtIdentifier() AtIdentifier { 70 - return AtIdentifier{Inner: h} 70 + return AtIdentifier(h) 71 71 } 72 72 73 73 func (h Handle) String() string {
+6 -6
atproto/syntax/json_test.go
··· 11 11 assert := assert.New(t) 12 12 13 13 type AllTogether struct { 14 - Handle Handle `json:"handle"` 15 - Aturi ATURI `json:"aturi"` 16 - Did DID `json:"did"` 17 - Atid *AtIdentifier `json:"atid"` 18 - Rkey RecordKey `json:"rkey"` 19 - Col *NSID `json:"col"` // demonstrating a pointer 14 + Handle Handle `json:"handle"` 15 + Aturi ATURI `json:"aturi"` 16 + Did DID `json:"did"` 17 + Atid AtIdentifier `json:"atid"` 18 + Rkey RecordKey `json:"rkey"` 19 + Col *NSID `json:"col"` // demonstrating a pointer 20 20 } 21 21 fullJSON := `{ 22 22 "handle": "handle.example.com",
+3 -3
cmd/bluepages/main.go
··· 292 292 return err 293 293 } 294 294 295 - ident, err := dir.Lookup(ctx, *atid) 295 + ident, err := dir.Lookup(ctx, atid) 296 296 if err != nil { 297 297 return err 298 298 } ··· 317 317 return err 318 318 } 319 319 320 - err = dir.Purge(ctx, *atid) 320 + err = dir.Purge(ctx, atid) 321 321 if err != nil { 322 322 return err 323 323 } 324 324 325 - ident, err := dir.Lookup(ctx, *atid) 325 + ident, err := dir.Lookup(ctx, atid) 326 326 if err != nil { 327 327 return err 328 328 }
+1 -1
cmd/gosky/admin.go
··· 74 74 return err 75 75 } 76 76 77 - id, err := dir.Lookup(ctx, *ident) 77 + id, err := dir.Lookup(ctx, ident) 78 78 if err != nil { 79 79 return fmt.Errorf("resolve identifier %q: %w", cctx.Args().First(), err) 80 80 }
+1 -1
cmd/gosky/debug.go
··· 855 855 856 856 if !cctx.IsSet("host-1") { 857 857 dir := identity.DefaultDirectory() 858 - ident, err := dir.Lookup(ctx, *did) 858 + ident, err := dir.Lookup(ctx, did) 859 859 if err != nil { 860 860 return err 861 861 }
+2 -2
cmd/gosky/main.go
··· 445 445 return err 446 446 } 447 447 448 - resp, err := identity.DefaultDirectory().Lookup(ctx, *atid) 448 + resp, err := identity.DefaultDirectory().Lookup(ctx, atid) 449 449 if err != nil { 450 450 return err 451 451 } ··· 806 806 return err 807 807 } 808 808 809 - ident, err := identity.DefaultDirectory().Lookup(ctx, *idf) 809 + ident, err := identity.DefaultDirectory().Lookup(ctx, idf) 810 810 if err != nil { 811 811 return err 812 812 }
+2 -2
cmd/gosky/sync.go
··· 43 43 return err 44 44 } 45 45 dir := identity.DefaultDirectory() 46 - ident, err := dir.Lookup(ctx, *atid) 46 + ident, err := dir.Lookup(ctx, atid) 47 47 if err != nil { 48 48 return err 49 49 } ··· 98 98 } 99 99 100 100 dir := identity.DefaultDirectory() 101 - ident, err := dir.Lookup(ctx, *atid) 101 + ident, err := dir.Lookup(ctx, atid) 102 102 if err != nil { 103 103 return err 104 104 }
+2 -2
cmd/hepa/main.go
··· 449 449 return err 450 450 } 451 451 452 - return capture.FetchAndProcessRecent(ctx, srv.Engine, *atid, cmd.Int("limit")) 452 + return capture.FetchAndProcessRecent(ctx, srv.Engine, atid, cmd.Int("limit")) 453 453 }, 454 454 } 455 455 ··· 479 479 return err 480 480 } 481 481 482 - cap, err := capture.CaptureRecent(ctx, srv.Engine, *atid, cmd.Int("limit")) 482 + cap, err := capture.CaptureRecent(ctx, srv.Engine, atid, cmd.Int("limit")) 483 483 if err != nil { 484 484 return err 485 485 }
+2 -2
search/handlers.go
··· 107 107 } 108 108 } 109 109 if atid.IsHandle() { 110 - ident, err := s.dir.Lookup(e.Request().Context(), *atid) 110 + ident, err := s.dir.Lookup(e.Request().Context(), atid) 111 111 if err != nil { 112 112 return e.JSON(400, map[string]any{ 113 113 "error": "BadRequest", ··· 134 134 } 135 135 } 136 136 if atid.IsHandle() { 137 - ident, err := s.dir.Lookup(e.Request().Context(), *atid) 137 + ident, err := s.dir.Lookup(e.Request().Context(), atid) 138 138 if err != nil { 139 139 return e.JSON(400, map[string]any{ 140 140 "error": "BadRequest",