Skip to content

Persist Spotify/SoundCloud follower counts from Link Wizard candidate selection #342

Description

@chiptus

Parent

#333 (Link Wizard search-assisted matching)

Problem

Candidate.followers (returned by search-artist-links for both providers) is shown on CandidateCard but is display-only — selecting a candidate in the Link Wizard only stages url/image/description (mergeCandidateSelection.ts). Follower counts aren't saved anywhere from this flow.

Today follower counts only exist for SoundCloud, via a separate mechanism: the soundcloud table (1:1 with artists, columns include followers_count) is populated by the unrelated sync-artist-data edge function/job, and surfaced in the admin artist list as soundcloud_followers (useArtists.ts, useArtistsPage.ts). There is no equivalent table/column for Spotify followers anywhere.

⚠️ Update: Spotify no longer provides followers/genres for this app

Since Spotify's Nov 27, 2024 Web API policy change, the followers and genres fields are stripped from artist objects (search, get-artist, get-artists) for any app that isn't in Extended Quota Mode. Extended Quota Mode requires ~250K MAU to apply, which this app doesn't have.

We confirmed this directly against the live API in search-artist-links's spotify-adapter.ts: /v1/search?type=artist and /v1/artists/{id} both come back with no followers/genres fields at all, even for globally massive artists (e.g. Pitbull). This isn't a bug in our code — SpotifyArtistSchema already types both fields as optional/nullable for this reason.

Practical impact on this ticket: Candidate.followers from Spotify will be null for effectively all searches going forward, so most of the "add a persistence target for Spotify followers" work here has no real data to persist. Scope should probably be narrowed to:

  • SoundCloud followers persistence (still works, has real data).
  • Spotify followers: either drop from scope, or persist opportunistically for the rare case Spotify does return a value, with the expectation it'll almost always be null.
  • genres has the same problem if it's ever sourced from Spotify elsewhere in the app — worth checking that too.

No known workaround exists via Spotify's official public Web API for a non-extended app.

What to build

  • Add a place to persist Spotify follower counts, analogous to the existing soundcloud table (new spotify table, or a spotify_followers column — follow the existing soundcloud/soundcloud_followers pattern for consistency).
  • When an admin selects a Link Wizard candidate, also stage/save that provider's follower count into the artist's record (extend mergeCandidateSelection.ts and CandidateUpdate/SelectableField, and the artist update call in LinkWizardStep).
  • Decide (and document) how this interacts with the existing SoundCloud sync-artist-data job, which already writes soundcloud_followers independently — e.g. does a later sync run overwrite what the Link Wizard staged, or does staging just seed an initial value until the next sync.

Acceptance criteria

  • Spotify follower counts have a persistence target (table/column) mirroring the SoundCloud pattern.
  • Selecting a candidate in the Link Wizard stages that provider's follower count for save, without requiring a separate manual step.
  • Existing soundcloud_followers sync via sync-artist-data is unaffected (no regression, and the overwrite behavior above is intentional, not accidental).
  • Admin artist list/table can surface Spotify followers the same way it already does for SoundCloud, if applicable.

Open questions

  • Should follower counts be selectable per-field like image/description (SelectableField), or always saved alongside the URL since they're not user-editable data?
  • Does this need its own sync/refresh mechanism over time, or is "whatever the Link Wizard captured at selection time" acceptable (counts go stale)?
  • Given Spotify's API restriction above: should this ticket be narrowed to SoundCloud-only, or closed/reworked?

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions