package music import ( "encoding/json" "net/http" "github.com/jmoiron/sqlx" ) type Artist struct { ID string `json:"id"` Name string `json:"name"` Website string `json:"website"` } var Artists []Artist func GetArtist(id string) *Artist { for _, artist := range Artists { if artist.GetID() == id { return &artist } } return nil } // GETTERS func (artist Artist) GetID() string { return artist.ID } func (artist Artist) GetName() string { return artist.Name } func (artist Artist) GetWebsite() string { return artist.Website } // SETTERS func (artist Artist) SetID(id string) error { artist.ID = id return nil } func (artist Artist) SetName(name string) error { artist.Name = name return nil } func (artist Artist) SetWebsite(website string) error { artist.Website = website return nil } // DATABASE func (artist Artist) PushToDB(db *sqlx.DB) { // fmt.Printf("Pushing artist [%s] to database...", artist.Name) db.MustExec( "INSERT INTO artists (id, name, website) "+ "VALUES ($1, $2, $3) "+ "ON CONFLICT (id) "+ "DO UPDATE SET name=$2, website=$3", artist.ID, artist.Name, artist.Website, ) // fmt.Printf("done!\n") } func PullAllArtists(db *sqlx.DB) ([]Artist, error) { artists := []Artist{} rows, err := db.Query("SELECT id, name, website FROM artists") if err != nil { return nil, err } for rows.Next() { var artist = Artist{} err = rows.Scan( &artist.ID, &artist.Name, &artist.Website, ) if err != nil { return nil, err } artists = append(artists, artist) } return artists, nil } // HTTP HANDLERS func ServeArtist() http.Handler { return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { if r.URL.Path == "/" { http.NotFound(w, r) return } type ( creditJSON struct { Role string `json:"role"` Primary bool `json:"primary"` } artistJSON struct { Artist Credits map[string]creditJSON `json:"credits"` } ) var res = artistJSON{} res.ID = r.URL.Path[1:] var artist = GetArtist(res.ID) if artist == nil { http.NotFound(w, r) return } res.Name = artist.Name res.Website = artist.Website res.Credits = make(map[string]creditJSON) for _, release := range Releases { for _, credit := range release.Credits { if credit.Artist.ID != res.ID { continue } res.Credits[release.ID] = creditJSON{ Role: credit.Role, Primary: credit.Primary, } } } jsonBytes, err := json.Marshal(res) if err != nil { http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError) return } w.Header().Add("Content-Type", "application/json") w.WriteHeader(http.StatusOK) w.Write(jsonBytes) }) }