package transcode_test import ( "context" "net/http" "testing" "scrabble/gateway/internal/transcode" fb "scrabble/pkg/fbs/scrabblefb" ) // TestProfileGetEncodesBanner verifies the gateway forwards the backend's banner // block verbatim into the Profile payload: the campaigns (weight + resolved // messages, in order) and the global display timings. func TestProfileGetEncodesBanner(t *testing.T) { backend, cleanup := fakeBackend(t, func(w http.ResponseWriter, r *http.Request) { if r.Method != http.MethodGet || r.URL.Path != "/api/v1/user/profile" { t.Errorf("unexpected %s %q", r.Method, r.URL.Path) } _, _ = w.Write([]byte(`{"user_id":"u-1","display_name":"Kaya","preferred_language":"en",` + `"banner":{"campaigns":[` + `{"weight":3,"messages":["promo-en"]},` + `{"weight":7,"messages":["house-a","house-b"]}],` + `"timings":{"hold_ms":60000,"edge_pause_ms":5000,"scroll_px_per_sec":40,` + `"fade_out_ms":1000,"gap_ms":250,"fade_in_ms":1000}}}`)) }) defer cleanup() reg := transcode.NewRegistry(backend, nil) op, ok := reg.Lookup(transcode.MsgProfileGet) if !ok { t.Fatal("profile.get not registered") } payload, err := op.Handler(context.Background(), transcode.Request{UserID: "u-1"}) if err != nil { t.Fatalf("handler: %v", err) } p := fb.GetRootAsProfile(payload, 0) banner := p.Banner(nil) if banner == nil { t.Fatal("profile carries no banner block") } if got := banner.CampaignsLength(); got != 2 { t.Fatalf("campaigns = %d, want 2", got) } var c fb.BannerCampaign banner.Campaigns(&c, 0) if c.Weight() != 3 || c.MessagesLength() != 1 || string(c.Messages(0)) != "promo-en" { t.Errorf("campaign 0 = weight %d, %d msgs, msg0=%q", c.Weight(), c.MessagesLength(), c.Messages(0)) } banner.Campaigns(&c, 1) if c.Weight() != 7 || c.MessagesLength() != 2 || string(c.Messages(1)) != "house-b" { t.Errorf("campaign 1 = weight %d, %d msgs, msg1=%q", c.Weight(), c.MessagesLength(), c.Messages(1)) } if banner.HoldMs() != 60000 || banner.EdgePauseMs() != 5000 || banner.ScrollPxPerSec() != 40 { t.Errorf("timings = hold %d edge %d scroll %d", banner.HoldMs(), banner.EdgePauseMs(), banner.ScrollPxPerSec()) } if banner.FadeOutMs() != 1000 || banner.GapMs() != 250 || banner.FadeInMs() != 1000 { t.Errorf("fade timings = out %d gap %d in %d", banner.FadeOutMs(), banner.GapMs(), banner.FadeInMs()) } } // TestProfileGetNoBanner verifies an ineligible viewer's profile carries no // banner block (the backend omits it). func TestProfileGetNoBanner(t *testing.T) { backend, cleanup := fakeBackend(t, func(w http.ResponseWriter, r *http.Request) { _, _ = w.Write([]byte(`{"user_id":"u-1","display_name":"Kaya","preferred_language":"en"}`)) }) defer cleanup() reg := transcode.NewRegistry(backend, nil) op, _ := reg.Lookup(transcode.MsgProfileGet) payload, err := op.Handler(context.Background(), transcode.Request{UserID: "u-1"}) if err != nil { t.Fatalf("handler: %v", err) } if p := fb.GetRootAsProfile(payload, 0); p.Banner(nil) != nil { t.Error("ineligible profile unexpectedly carries a banner block") } }