feat(migrations): cleanup funnel-duplicate roster leftovers (chat#1859)#45
Conversation
Complete the deferred cleanup after the repoint migrations. Step 1 removes redundant duplicate roster rows where the account already holds the canonical twin (Category B — the repoint skips these; 5 rows on prod 2026-07-08). Step 2 deletes fully-orphaned funnel-duplicate artist accounts (song-less, catalog-less, Spotify-social, one song-owning same-name twin, zero roster refs; 16 already orphaned from the original repoint plus those newly orphaned). Runs after the pass-2 repoint; both are needed for the #1859 health-check query to return 0. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
|
Bugbot is not enabled for your account, so this pull request was not reviewed. Enable Bugbot in the Cursor dashboard to get automatic reviews on future PRs. |
|
Warning Review limit reached
Next review available in: 49 minutes Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available. How can I continue?After more reviews become available, a review can be triggered using the To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews. How do review limits work?CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability. For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window. Please refer docs for additional details. Review details⚙️ Run configurationConfiguration used: defaults Review profile: CHILL Plan: Pro Run ID: 📒 Files selected for processing (1)
✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
|
Updates to Preview Branch (feat/cleanup-funnel-dupe-leftovers) ↗︎
Tasks are run on every commit but only new migration files are pushed.
View logs for this Workflow Run ↗︎. |
There was a problem hiding this comment.
2 issues found across 1 file
Prompt for AI agents (unresolved issues)
Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.
<file name="supabase/migrations/20260708170500_cleanup_funnel_duplicate_roster_leftovers.sql">
<violation number="1" location="supabase/migrations/20260708170500_cleanup_funnel_duplicate_roster_leftovers.sql:88">
P1: Step 2 only checks whether the duplicate account is referenced as `artist_id`, so it can still delete an account that owns `account_artist_ids` rows and cascade those rows away. The guard needs to exclude both sides of the join before deleting the account.</violation>
<violation number="2" location="supabase/migrations/20260708170500_cleanup_funnel_duplicate_roster_leftovers.sql:101">
P1: Deleting these orphan duplicate accounts can cascade more than the intended scraped account_socials when a qualifying account still has artist-scoped records such as funnel_analytics, campaigns, segment_reports, memories, or scheduled_actions. Consider either guarding orphan_dupe_accounts against every cascading dependent table or deleting only after explicitly verifying those dependents are absent.</violation>
</file>
Reply with feedback, questions, or to request a fix.
Re-trigger cubic
| WHERE c.name = a.name AND c.id <> a.id | ||
| AND EXISTS (SELECT 1 FROM public.song_artists sa WHERE sa.artist = c.id)) = 1; | ||
|
|
||
| DELETE FROM public.accounts a |
There was a problem hiding this comment.
P1: Deleting these orphan duplicate accounts can cascade more than the intended scraped account_socials when a qualifying account still has artist-scoped records such as funnel_analytics, campaigns, segment_reports, memories, or scheduled_actions. Consider either guarding orphan_dupe_accounts against every cascading dependent table or deleting only after explicitly verifying those dependents are absent.
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At supabase/migrations/20260708170500_cleanup_funnel_duplicate_roster_leftovers.sql, line 101:
<comment>Deleting these orphan duplicate accounts can cascade more than the intended scraped account_socials when a qualifying account still has artist-scoped records such as funnel_analytics, campaigns, segment_reports, memories, or scheduled_actions. Consider either guarding orphan_dupe_accounts against every cascading dependent table or deleting only after explicitly verifying those dependents are absent.</comment>
<file context>
@@ -0,0 +1,119 @@
+ WHERE c.name = a.name AND c.id <> a.id
+ AND EXISTS (SELECT 1 FROM public.song_artists sa WHERE sa.artist = c.id)) = 1;
+
+DELETE FROM public.accounts a
+USING orphan_dupe_accounts o
+WHERE a.id = o.id;
</file context>
| CREATE TEMP TABLE orphan_dupe_accounts ON COMMIT DROP AS | ||
| SELECT a.id | ||
| FROM public.accounts a | ||
| WHERE NOT EXISTS (SELECT 1 FROM public.account_artist_ids aai WHERE aai.artist_id = a.id) |
There was a problem hiding this comment.
P1: Step 2 only checks whether the duplicate account is referenced as artist_id, so it can still delete an account that owns account_artist_ids rows and cascade those rows away. The guard needs to exclude both sides of the join before deleting the account.
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At supabase/migrations/20260708170500_cleanup_funnel_duplicate_roster_leftovers.sql, line 88:
<comment>Step 2 only checks whether the duplicate account is referenced as `artist_id`, so it can still delete an account that owns `account_artist_ids` rows and cascade those rows away. The guard needs to exclude both sides of the join before deleting the account.</comment>
<file context>
@@ -0,0 +1,119 @@
+CREATE TEMP TABLE orphan_dupe_accounts ON COMMIT DROP AS
+SELECT a.id
+FROM public.accounts a
+WHERE NOT EXISTS (SELECT 1 FROM public.account_artist_ids aai WHERE aai.artist_id = a.id)
+ AND NOT EXISTS (SELECT 1 FROM public.song_artists sa WHERE sa.artist = a.id)
+ AND NOT EXISTS (SELECT 1 FROM public.account_catalogs ac WHERE ac.account = a.id)
</file context>
What
The cleanup-delete — second of the two backfill follow-ups on chat#1859. Completes the deletion that database#43 deliberately deferred ("Duplicate accounts are NOT deleted — orphaning them is enough; deletion is a follow-up").
Adds
20260708170500_cleanup_funnel_duplicate_roster_leftovers.sql, which removes the two leftovers the repoint migrations cannot:(account, canonical)link — leaving a redundant row pointing at the song-less duplicate that no re-run touches. Deletes those.Scope (measured 2026-07-08 on prod, read-only)
Safety (destructive — tightly guarded, idempotent)
song_artists(never a canonical or any real artist), zeroaccount_catalogs, not inartist_organization_ids, carries a Spotify social, has exactly one song-owning same-name twin, and is fully orphaned (zeroaccount_artist_idsrefs). Deletion cascades only its own scrapedaccount_socials.RAISE EXCEPTIONif any redundant (dupe + canonical on the same account) row remains. Re-running finds nothing.Verification
song_artists,account_catalogs, or an org link is in scope.Merge order
Merge pass-2 repoint (#44) first, then this. This file's timestamp is later so they apply repoint → cleanup; merging in that order keeps the migration history in sequence. Running this before the repoint is safe but leaves Category A unfixed (that's the repoint's job).
Links
20260707190000, the deferred-deletion note) · feat(migrations): repoint funnel-duplicate roster artists — pass 2 (chat#1859) #44 (pass-2 repoint)🤖 Generated with Claude Code
Summary by cubic
Adds
20260708170500_cleanup_funnel_duplicate_roster_leftovers.sqlto remove redundant roster rows and delete fully orphaned funnel-duplicate artist accounts left by the repoint, completing cleanup for chat#1859.account_artist_idswhere the account already links to the canonical twin.song_artists, noaccount_catalogs, no org link, has a Spotify social, exactly one same‑name song‑owning twin, and no roster refs; cascades only its ownaccount_socials.Written for commit 66c4f9c. Summary will update on new commits.