Files
cdnutterandClaude Opus 5.5 7320e3f707 Save source descriptions, add "Why it's #N", fix IGDB studio names
Descriptions
- Items keep the source's description (TMDB/TheTVDB overview, IGDB
  summary, Wikipedia intro) in a new items.description column
  (migration 3); editable in the item form
- Deezer/MusicBrainz track counts and album names are now display-only
  hints, not saved as descriptions

Why it's #N
- The owner's note is presented as "Why it's #N" in the editor and the
  public detail view, above an "About" section with the description

IGDB developers
- IGDB credits internal divisions ("Nintendo EAD", "Nintendo EPD
  Production Group No. 8"). A developer whose name shares its first word
  with its parent company is credited to the parent ("Nintendo");
  independently named studios keep their name (Retro Studios, Naughty
  Dog, Landfall Games)
- Fall back to the publisher when IGDB lists no developer

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-24 18:05:20 -07:00

56 lines
2.3 KiB
Go

package providers
import (
"encoding/json"
"testing"
)
func TestStudioName(t *testing.T) {
cases := []struct{ json, want string }{
// Internal divisions roll up to the company.
{`{"name":"Nintendo EAD","parent":{"name":"Nintendo"}}`, "Nintendo"},
{`{"name":"Nintendo EPD Production Group No. 8","parent":{"name":"Nintendo EPD","parent":{"name":"Nintendo"}}}`, "Nintendo"},
{`{"name":"Ubisoft Montreal","parent":{"name":"Ubisoft Entertainment"}}`, "Ubisoft Entertainment"},
// Studios with their own name stay themselves.
{`{"name":"Retro Studios","parent":{"name":"Nintendo"}}`, "Retro Studios"},
{`{"name":"Naughty Dog","parent":{"name":"Sony Interactive Entertainment"}}`, "Naughty Dog"},
{`{"name":"Landfall Games"}`, "Landfall Games"},
// Stop climbing once the name changes.
{`{"name":"Rockstar North","parent":{"name":"Rockstar Games","parent":{"name":"Take-Two Interactive"}}}`, "Rockstar Games"},
// An unexpanded parent arrives as a bare ID.
{`{"name":"Nintendo EAD Tokyo","parent":1234}`, "Nintendo EAD Tokyo"},
}
for _, c := range cases {
var co igdbCompany
if err := json.Unmarshal([]byte(c.json), &co); err != nil {
t.Fatalf("%s: %v", c.json, err)
}
if got := studioName(&co); got != c.want {
t.Errorf("%s → %q, want %q", c.json, got, c.want)
}
}
}
// A whole search response decodes, and co-developers from the same company
// collapse to one name.
func TestIGDBDevelopers(t *testing.T) {
body := `[{"id":1,"name":"Super Mario Sunshine","involved_companies":[
{"developer":true,"publisher":false,"company":{"name":"Nintendo EAD","parent":{"name":"Nintendo"}}},
{"developer":true,"publisher":false,"company":{"name":"Nintendo EAD Tokyo","parent":{"name":"Nintendo EAD","parent":{"name":"Nintendo"}}}},
{"developer":false,"publisher":true,"company":{"name":"Nintendo"}}]},
{"id":2,"name":"Publisher only","involved_companies":[{"developer":false,"publisher":true,"company":{"name":"Devolver Digital"}}]}]`
var games []struct {
InvolvedCompanies []igdbInvolved `json:"involved_companies"`
}
if err := json.Unmarshal([]byte(body), &games); err != nil {
t.Fatal(err)
}
want := []string{"Nintendo", "Devolver Digital"}
for i, g := range games {
devs := igdbStudios(g.InvolvedCompanies)
if len(devs) != 1 || devs[0] != want[i] {
t.Errorf("game %d developers = %v, want [%s]", i, devs, want[i])
}
}
}