server/lastfm: make a scrobbler interface and migrate lastfm to use it

This commit is contained in:
Alex McGrath
2021-01-08 13:09:42 +00:00
committed by Senan Kelly
parent cc93d61908
commit f4ff7e70f2
5 changed files with 38 additions and 12 deletions

View File

@@ -13,6 +13,7 @@ import (
"go.senan.xyz/gonic/server/ctrlsubsonic/params"
"go.senan.xyz/gonic/server/ctrlsubsonic/spec"
"go.senan.xyz/gonic/server/jukebox"
"go.senan.xyz/gonic/server/lastfm"
)
type CtxKey int
@@ -28,6 +29,7 @@ type Controller struct {
CachePath string
CoverCachePath string
Jukebox *jukebox.Jukebox
Scrobblers []lastfm.Scrobbler
}
type metaResponse struct {

View File

@@ -61,14 +61,16 @@ func (c *Controller) ServeScrobble(r *http.Request) *spec.Response {
StampMili: params.GetOrInt("time", int(time.Now().UnixNano()/1e6)),
Submission: params.GetOrBool("submission", true),
}
err = lastfm.Scrobble(
c.DB.GetSetting("lastfm_api_key"),
c.DB.GetSetting("lastfm_secret"),
user.LastFMSession,
opts,
)
if err != nil {
return spec.NewError(0, "error when submitting: %v", err)
scrobbleErrs := []error{}
for _, scrobbler := range c.Scrobblers {
if !scrobbler.Enabled(user) {
continue
}
err = scrobbler.Scrobble(user, opts)
scrobbleErrs = append(scrobbleErrs, err)
}
if len(scrobbleErrs) != 0 {
return spec.NewError(0, "error when submitting: %v", scrobbleErrs)
}
return spec.NewResponse()
}

View File

@@ -15,7 +15,8 @@ import (
)
const (
baseURL = "https://ws.audioscrobbler.com/2.0/"
lastfmBaseURL = "https://ws.audioscrobbler.com/2.0/"
lbBaseURL = "https://api.listenbrainz.org"
)
var (
@@ -42,7 +43,7 @@ func getParamSignature(params url.Values, secret string) string {
}
func makeRequest(method string, params url.Values) (LastFM, error) {
req, _ := http.NewRequest(method, baseURL, nil)
req, _ := http.NewRequest(method, lastfmBaseURL, nil)
req.URL.RawQuery = params.Encode()
resp, err := http.DefaultClient.Do(req)
if err != nil {
@@ -79,7 +80,18 @@ type ScrobbleOptions struct {
Submission bool
}
func Scrobble(apiKey, secret, session string, opts ScrobbleOptions) error {
type LastfmScrobbler struct { //nolint
DB *db.DB
}
func (lfm *LastfmScrobbler) Scrobble(reqUser interface{}, opts ScrobbleOptions) error {
apiKey := lfm.DB.GetSetting("lastfm_api_key")
secret := lfm.DB.GetSetting("lastfm_secret")
// fetch user to get lastfm session
user := reqUser.(*db.User)
if user.LastFMSession == "" {
return fmt.Errorf("you don't have a last.fm session: %w", ErrLastFM)
}
params := url.Values{}
if opts.Submission {
params.Add("method", "track.Scrobble")
@@ -89,7 +101,7 @@ func Scrobble(apiKey, secret, session string, opts ScrobbleOptions) error {
params.Add("method", "track.updateNowPlaying")
}
params.Add("api_key", apiKey)
params.Add("sk", session)
params.Add("sk", user.LastFMSession)
params.Add("artist", opts.Track.TagTrackArtist)
params.Add("track", opts.Track.TagTitle)
params.Add("trackNumber", strconv.Itoa(opts.Track.TagTrackNumber))

View File

@@ -4,6 +4,10 @@ import (
"encoding/xml"
)
type Scrobbler interface {
Scrobble(interface{}, ScrobbleOptions) error
}
type LastFM struct {
XMLName xml.Name `xml:"lfm"`
Status string `xml:"status,attr"`

View File

@@ -17,6 +17,7 @@ import (
"go.senan.xyz/gonic/server/ctrlsubsonic"
"go.senan.xyz/gonic/server/db"
"go.senan.xyz/gonic/server/jukebox"
"go.senan.xyz/gonic/server/lastfm"
"go.senan.xyz/gonic/server/scanner"
)
@@ -62,11 +63,16 @@ func New(opts Options) *Server {
sessDB.SessionOpts.SameSite = http.SameSiteLaxMode
//
ctrlAdmin := ctrladmin.New(base, sessDB)
lastfmScrobbler := &lastfm.LastfmScrobbler{DB: opts.DB}
scrobblers := []lastfm.Scrobbler{
lastfmScrobbler,
}
ctrlSubsonic := &ctrlsubsonic.Controller{
Controller: base,
CachePath: opts.CachePath,
CoverCachePath: opts.CoverCachePath,
Jukebox: jukebox,
Scrobblers: scrobblers,
}
setupMisc(r, base)
setupAdmin(r.PathPrefix("/admin").Subrouter(), ctrlAdmin)