feat(tags): fandom-edit UI in tags directory + image modal
CI / lint (push) Successful in 3s
CI / backend-lint-and-test (push) Successful in 13s
CI / frontend-build (push) Successful in 26s
CI / intimp (push) Successful in 3m47s
CI / intapi (push) Successful in 7m52s
CI / intcore (push) Successful in 8m58s

Adds the missing UI to change a character tag's fandom, in both places:

- FandomSetDialog (shared): pick an existing fandom, create a new one, or
  clear it; on a name collision in the target fandom it surfaces a merge
  confirmation and resolves via setFandom(merge:true). Reuses the tags
  store's fandom cache.
- TagCard kebab gains "Set fandom…" for character tags (→ TagsView opens
  the dialog, reloads on success).
- TagPanel chip kebab gains "Set fandom…" for character tags (→ reloads the
  modal's tag list on success).
- tags store: setFandom(tagId, fandomId, {merge}) action + test.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-06-03 23:21:25 -04:00
parent d9ab6e15c6
commit e678d1dfdf
6 changed files with 258 additions and 2 deletions
+14 -1
View File
@@ -49,8 +49,21 @@ export const useTagStore = defineStore('tags', () => {
return fandom
}
// Set / change / clear a character tag's fandom. fandomId null clears it.
// Throws ApiError (status 409, body.target) on a name collision in the
// target fandom; pass { merge: true } to resolve it by merging this tag
// into the existing character. Returns the updated/surviving tag.
async function setFandom(tagId, fandomId, { merge = false } = {}) {
const body = { fandom_id: fandomId ?? null }
if (merge) body.merge = true
return await api.patch(`/api/tags/${tagId}`, { body })
}
function kindOptions() { return KIND_OPTIONS }
function colorFor(kind) { return KIND_COLOR[kind] || 'on-surface' }
return { fandomCache, autocomplete, loadFandoms, createFandom, kindOptions, colorFor }
return {
fandomCache, autocomplete, loadFandoms, createFandom, setFandom,
kindOptions, colorFor
}
})