|
| 1 | +package botapi |
| 2 | + |
| 3 | +import ( |
| 4 | + "context" |
| 5 | + |
| 6 | + "github.com/gotd/td/fileid" |
| 7 | + "github.com/gotd/td/tg" |
| 8 | +) |
| 9 | + |
| 10 | +// UserProfileAudios is the result of GetUserProfileAudios: the audios a user has |
| 11 | +// added to their profile. |
| 12 | +type UserProfileAudios struct { |
| 13 | + // TotalCount is the total number of profile audios the user has. |
| 14 | + TotalCount int `json:"total_count"` |
| 15 | + // Audios are the requested profile audios. |
| 16 | + Audios []Audio `json:"audios"` |
| 17 | +} |
| 18 | + |
| 19 | +// GetUserProfileAudiosOption configures GetUserProfileAudios. |
| 20 | +type GetUserProfileAudiosOption func(*profileAudiosConfig) |
| 21 | + |
| 22 | +type profileAudiosConfig struct { |
| 23 | + offset int |
| 24 | + limit int |
| 25 | +} |
| 26 | + |
| 27 | +// WithProfileAudiosOffset sets the number of audios to skip. |
| 28 | +func WithProfileAudiosOffset(offset int) GetUserProfileAudiosOption { |
| 29 | + return func(c *profileAudiosConfig) { c.offset = offset } |
| 30 | +} |
| 31 | + |
| 32 | +// WithProfileAudiosLimit caps the number of audios returned (1-100). |
| 33 | +func WithProfileAudiosLimit(limit int) GetUserProfileAudiosOption { |
| 34 | + return func(c *profileAudiosConfig) { c.limit = limit } |
| 35 | +} |
| 36 | + |
| 37 | +// audioFromDocument builds a Bot API Audio from an MTProto audio document, |
| 38 | +// reusing the shared document classifier. |
| 39 | +func audioFromDocument(d *tg.Document) Audio { |
| 40 | + var m Message |
| 41 | + |
| 42 | + setDocumentMedia(d, &m) |
| 43 | + |
| 44 | + if m.Audio != nil { |
| 45 | + return *m.Audio |
| 46 | + } |
| 47 | + |
| 48 | + fileID, uniqueID := encodeFileID(fileid.FromDocument(d)) |
| 49 | + |
| 50 | + return Audio{FileID: fileID, FileUniqueID: uniqueID, MIMEType: d.MimeType, FileSize: d.Size} |
| 51 | +} |
| 52 | + |
| 53 | +// GetUserProfileAudios returns the audios a user has added to their profile. |
| 54 | +func (b *Bot) GetUserProfileAudios(ctx context.Context, userID int64, opts ...GetUserProfileAudiosOption) (*UserProfileAudios, error) { |
| 55 | + cfg := profileAudiosConfig{limit: 100} |
| 56 | + for _, o := range opts { |
| 57 | + o(&cfg) |
| 58 | + } |
| 59 | + |
| 60 | + user, err := b.resolveInputUser(ctx, userID) |
| 61 | + if err != nil { |
| 62 | + return nil, err |
| 63 | + } |
| 64 | + |
| 65 | + res, err := b.raw.UsersGetSavedMusic(ctx, &tg.UsersGetSavedMusicRequest{ |
| 66 | + ID: user, |
| 67 | + Offset: cfg.offset, |
| 68 | + Limit: cfg.limit, |
| 69 | + }) |
| 70 | + if err != nil { |
| 71 | + return nil, asAPIError(err) |
| 72 | + } |
| 73 | + |
| 74 | + music, ok := res.(*tg.UsersSavedMusic) |
| 75 | + if !ok { |
| 76 | + return &UserProfileAudios{}, nil |
| 77 | + } |
| 78 | + |
| 79 | + out := &UserProfileAudios{TotalCount: music.Count, Audios: make([]Audio, 0, len(music.Documents))} |
| 80 | + |
| 81 | + for _, doc := range music.Documents { |
| 82 | + if d, ok := doc.(*tg.Document); ok { |
| 83 | + out.Audios = append(out.Audios, audioFromDocument(d)) |
| 84 | + } |
| 85 | + } |
| 86 | + |
| 87 | + return out, nil |
| 88 | +} |
0 commit comments