feat(playlists): act on the selected rows from the toolbar, and undo either
While rows are selected the toolbar's second row is the band: the count, the last target as one click, Move to, Remove, Clear selection. Both write in one request and undo back to the places; a video the target held before stays there. Delete takes the selection when there is one. A failure puts the rows back ticked. A row's own move goes through the same write, so it undoes too, and the single-row move route and service function are gone. A playlist row drops its grip below a 24rem table: the row menu keeps the moves.
This commit is contained in:
@@ -77,16 +77,58 @@ export const playlistsApi = {
|
||||
}),
|
||||
removeFromPlaylist: (id: number, videoId: string) =>
|
||||
req(`/api/playlists/${id}/items/${videoId}`, { method: "DELETE" }),
|
||||
// One request on purpose: add-then-remove from the client leaves the video in BOTH lists when
|
||||
// the second call fails. The server does it in one transaction.
|
||||
moveToPlaylist: (
|
||||
// One request on purpose: add-then-remove from the client leaves a video in BOTH lists when the
|
||||
// second call fails. The server does it in one transaction, and says which landed in the target
|
||||
// and which it already held: the Undo needs to tell them apart.
|
||||
moveManyToPlaylist: (
|
||||
id: number,
|
||||
videoId: string,
|
||||
videoIds: string[],
|
||||
targetPlaylistId: number,
|
||||
): Promise<{ ok: true; from_playlist_id: number; to_playlist_id: number; video_id: string }> =>
|
||||
req(`/api/playlists/${id}/items/${videoId}/move`, {
|
||||
): Promise<{
|
||||
ok: true;
|
||||
from_playlist_id: number;
|
||||
to_playlist_id: number;
|
||||
moved: string[];
|
||||
already_there: string[];
|
||||
}> =>
|
||||
req(`/api/playlists/${id}/items/move-bulk`, {
|
||||
method: "POST",
|
||||
body: JSON.stringify({ target_playlist_id: targetPlaylistId }),
|
||||
body: JSON.stringify({ video_ids: videoIds, target_playlist_id: targetPlaylistId }),
|
||||
}),
|
||||
// The Undo of a move, back into `id`. `positions` pairs with `moved` + `alreadyThere`.
|
||||
undoPlaylistMove: (
|
||||
id: number,
|
||||
fromPlaylistId: number,
|
||||
moved: string[],
|
||||
alreadyThere: string[],
|
||||
positions: number[],
|
||||
): Promise<{ ok: true; playlist_id: number; added: number }> =>
|
||||
req(`/api/playlists/${id}/items/undo-move`, {
|
||||
method: "POST",
|
||||
body: JSON.stringify({
|
||||
from_playlist_id: fromPlaylistId,
|
||||
moved,
|
||||
already_there: alreadyThere,
|
||||
positions,
|
||||
}),
|
||||
}),
|
||||
removeManyFromPlaylist: (
|
||||
id: number,
|
||||
videoIds: string[],
|
||||
): Promise<{ ok: true; playlist_id: number; removed: number }> =>
|
||||
req(`/api/playlists/${id}/items/remove-bulk`, {
|
||||
method: "POST",
|
||||
body: JSON.stringify({ video_ids: videoIds }),
|
||||
}),
|
||||
// The Undo of a removal, in one request; an index in the stored order per video.
|
||||
restoreToPlaylist: (
|
||||
id: number,
|
||||
videoIds: string[],
|
||||
positions: number[],
|
||||
): Promise<{ ok: true; playlist_id: number; added: number }> =>
|
||||
req(`/api/playlists/${id}/items/restore`, {
|
||||
method: "POST",
|
||||
body: JSON.stringify({ video_ids: videoIds, positions }),
|
||||
}),
|
||||
reorderPlaylist: (id: number, videoIds: string[]) =>
|
||||
req(`/api/playlists/${id}/order`, {
|
||||
|
||||
Reference in New Issue
Block a user