web/queue: in-place queue task retrying

no more duplicate tasks
This commit is contained in:
wukko 2025-05-19 22:49:54 +06:00
parent 479a64890e
commit 98cd4dfc0d
No known key found for this signature in database
GPG Key ID: 3E30B3F26C7B4AA2
4 changed files with 24 additions and 5 deletions

View File

@ -45,6 +45,7 @@
retrying = true; retrying = true;
await savingHandler({ await savingHandler({
request: info.originalRequest, request: info.originalRequest,
oldTaskId: id,
}); });
retrying = false; retrying = false;
} }

View File

@ -11,7 +11,13 @@ import { createSavePipeline } from "$lib/task-manager/queue";
import type { CobaltSaveRequestBody } from "$lib/types/api"; import type { CobaltSaveRequestBody } from "$lib/types/api";
export const savingHandler = async ({ url, request }: { url?: string, request?: CobaltSaveRequestBody }) => { type SavingHandlerArgs = {
url?: string,
request?: CobaltSaveRequestBody,
oldTaskId?: string
}
export const savingHandler = async ({ url, request, oldTaskId }: SavingHandlerArgs) => {
downloadButtonState.set("think"); downloadButtonState.set("think");
const error = (errorText: string) => { const error = (errorText: string) => {
@ -103,7 +109,7 @@ export const savingHandler = async ({ url, request }: { url?: string, request?:
if (response.status === "local-processing") { if (response.status === "local-processing") {
downloadButtonState.set("done"); downloadButtonState.set("done");
return createSavePipeline(response, selectedRequest); return createSavePipeline(response, selectedRequest, oldTaskId);
} }
if (response.status === "picker") { if (response.status === "picker") {

View File

@ -127,7 +127,11 @@ const showError = (errorCode: string) => {
}); });
} }
export const createSavePipeline = (info: CobaltLocalProcessingResponse, request: CobaltSaveRequestBody) => { export const createSavePipeline = (
info: CobaltLocalProcessingResponse,
request: CobaltSaveRequestBody,
oldTaskId?: string
) => {
// this is a pre-queue part of processing, // this is a pre-queue part of processing,
// so errors have to be returned via a regular dialog // so errors have to be returned via a regular dialog
@ -135,7 +139,7 @@ export const createSavePipeline = (info: CobaltLocalProcessingResponse, request:
return showError("pipeline.missing_response_data"); return showError("pipeline.missing_response_data");
} }
const parentId = crypto.randomUUID(); const parentId = oldTaskId || crypto.randomUUID();
const pipeline: CobaltPipelineItem[] = []; const pipeline: CobaltPipelineItem[] = [];
// reverse is needed for audio (second item) to be downloaded first // reverse is needed for audio (second item) to be downloaded first

View File

@ -15,6 +15,8 @@ const startPipeline = (pipelineItem: CobaltPipelineItem) => {
startWorker(pipelineItem); startWorker(pipelineItem);
} }
// this is really messy, sorry to whoever
// reads this in the future (probably myself)
export const schedule = () => { export const schedule = () => {
const queueItems = get(queue); const queueItems = get(queue);
const ongoingTasks = get(currentTasks); const ongoingTasks = get(currentTasks);
@ -58,7 +60,13 @@ export const schedule = () => {
} }
// start the nearest waiting task and wait to be called again // start the nearest waiting task and wait to be called again
else if (task.state === "waiting" && task.pipeline.length > 0) { else if (task.state === "waiting" && task.pipeline.length > 0 && Object.keys(ongoingTasks).length === 0) {
// this is really bad but idk how to prevent tasks from running simultaneously
// on retry if a later task is running & user restarts an old task
for (const task of Object.values(queueItems)) {
if (task.state === "running") return;
}
startPipeline(task.pipeline[0]); startPipeline(task.pipeline[0]);
// break because we don't want to start next tasks before this one is done // break because we don't want to start next tasks before this one is done