ui(sidebar): drop Title field, add bulk notes editor

The Title (user_title) field hadn't earned its place in the sidebar
form — the underlying column stays on the model but the editable
row + its draft state + commit handler are gone.

Bulk Notes: a textarea in the multi-photo bulk panel that replaces
user_notes across the whole selection with one string. Apply commits;
Clear empties the draft without committing. New backend bulk action
'set_notes' validates the value is a string (or null/empty to clear)
and writes to every photo in the selection in one go. Wired through
the standard useBulkPhotoMutations optimistic-patch path, so the
photo cache flips immediately and rolls back on error.

user_notes added to the shared Photo type so patchPhotos accepts the
field; previously it was only on PhotoInfoPanel's local PhotoDetails.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
Claudio
2026-05-11 00:07:02 +02:00
parent c69322a89d
commit f743733edd
6 changed files with 91 additions and 31 deletions

View File

@@ -172,5 +172,22 @@ export function useBulkPhotoMutations() {
onSuccess: invalidatePhotoQueries,
})
return { bulkRating, bulkColor, invalidatePhotoQueries }
const bulkNotes = useMutation({
mutationFn: ({ ids, notes }: { ids: string[]; notes: string }) =>
photosApi.bulkSetNotes(ids, notes),
onMutate: ({ ids, notes }) => {
const snapshot = snapshotPhotos(ids)
// Mirror the server's empty-string -> null collapse so the
// optimistic cache matches what the API returns.
patchPhotos(ids, { user_notes: notes || null })
return { snapshot }
},
onError: (e, _vars, ctx) => {
if (ctx?.snapshot) restoreFromSnapshot(ctx.snapshot)
toast.error('Notes update failed', formatApiError(e))
},
onSuccess: invalidatePhotoQueries,
})
return { bulkRating, bulkColor, bulkNotes, invalidatePhotoQueries }
}