e4cebf70d1
The Series browse tab had no way to find a series in a long grid and no per-series actions. Add a search field (instant client-side name/artist filter over the already-loaded list) and a kebab on each card with Rename (reuses TagRenameDialog → PATCH /api/tags/<id>, with its collision-merge flow) and Delete (confirm dialog → DELETE /api/admin/tags/<id>; series_page/chapter/ suggestion cascade, images kept). Gap badge moved to the cover's top-left so the kebab can sit top-right. Operator-asked 2026-06-09. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
49 lines
1.6 KiB
JavaScript
49 lines
1.6 KiB
JavaScript
import { defineStore } from 'pinia'
|
|
import { ref } from 'vue'
|
|
import { useApi } from '../composables/useApi.js'
|
|
import { useAsyncAction } from '../composables/useAsyncAction.js'
|
|
|
|
// Backs the Series browse view (FC-6.2). list_series returns every series as a
|
|
// card; homelab scale is small enough to load the whole list and sort/filter
|
|
// server-side.
|
|
export const useSeriesBrowseStore = defineStore('seriesBrowse', () => {
|
|
const api = useApi()
|
|
const series = ref([])
|
|
const sort = ref('recent')
|
|
const artistId = ref(null)
|
|
const { loading, error, run } = useAsyncAction({ errorAs: 'message' })
|
|
|
|
async function load() {
|
|
await run(async () => {
|
|
const params = { sort: sort.value }
|
|
if (artistId.value != null) params.artist_id = artistId.value
|
|
const body = await api.get('/api/series', { params })
|
|
series.value = body.series || []
|
|
})
|
|
}
|
|
|
|
function setSort(s) {
|
|
sort.value = s
|
|
return load()
|
|
}
|
|
|
|
// A series IS a Tag(kind=series); deleting it removes the series structure
|
|
// (pages/chapters cascade) via the shared admin tag-delete. Splice the card
|
|
// out for instant feedback rather than reloading the whole grid.
|
|
async function remove(id) {
|
|
await api.delete(`/api/admin/tags/${id}`)
|
|
series.value = series.value.filter(s => s.id !== id)
|
|
}
|
|
|
|
// Reflect an in-place rename (PATCH /api/tags/<id>) without a full reload.
|
|
function applyRename(id, name) {
|
|
const row = series.value.find(s => s.id === id)
|
|
if (row) row.name = name
|
|
}
|
|
|
|
return {
|
|
series, sort, artistId, loading, error,
|
|
load, setSort, remove, applyRename,
|
|
}
|
|
})
|