Skip to content

Edit views: explicit slug field instead of silent re-slugging on rename #467

Description

@chiptus

Part 3 of the split of #41 (see that issue for background). Depends on #465 (slugify fallback); can land in parallel with #466.

Problem

Renaming a set or artist silently rewrites its slug client-side (src/api/sets/useUpdateSet.ts:36, src/api/artists/useUpdateArtist.ts:37 call generateSlug(updates.name)). This breaks bookmarked URLs and, for non-Latin names, writes an empty slug (no trigger runs on UPDATE).

Design (decided in triage)

  • Edit views for sets and artists show an explicit slug field, pre-filled with the current slug.
  • The user may edit it. Client validates format with isValidSlug / sanitizeSlug from src/lib/slug.ts and runs a lightweight uniqueness query (within the entity's uniqueness scope — global for artists, per-edition for sets) to warn before submit.
  • Empty is forbidden client-side (form validation error; react-hook-form per repo conventions).
  • Rename alone no longer changes the slug — the slug only changes when the user edits the slug field.
  • The DB stays the authority: unique constraints remain the backstop; map a constraint-violation error to a friendly form message.
  • Backstop: add BEFORE UPDATE triggers on sets and artists that re-derive via public.slugify(NEW.name) (with dedupe) if NEW.slug arrives empty/NULL, mirroring the existing insert triggers in 20260804101202_add_slug_dedupe_triggers.sql.

Work

  • Migration: extend sets_dedupe_slug / artists_dedupe_slug triggers to BEFORE INSERT OR UPDATE (guard so an unchanged slug on update is a no-op and doesn't self-collide — the existing id IS DISTINCT FROM NEW.id check covers this).
  • Remove auto generateSlug from useUpdateSet / useUpdateArtist; accept an optional explicit slug in the mutation input instead.
  • Add the slug field to the set and artist edit forms (find them under src/components/Admin/ / ArtistDetail/), with validation as above. Follow repo form conventions (react-hook-form, DialogTitle + DialogDescription).

Acceptance

  • Renaming a set/artist leaves its slug (and URLs) unchanged.
  • Editing the slug to a taken value shows a friendly error (both from the pre-check and from a raced constraint violation).
  • Submitting an empty slug is blocked by form validation.
  • An UPDATE that somehow arrives with an empty slug gets a trigger-derived non-empty slug.

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions