diff --git a/src/frontend/src/helpers/create-file-upload.ts b/src/frontend/src/helpers/create-file-upload.ts index b11363ce5..196716756 100644 --- a/src/frontend/src/helpers/create-file-upload.ts +++ b/src/frontend/src/helpers/create-file-upload.ts @@ -2,34 +2,59 @@ export async function createFileUpload(props?: { accept?: string; multiple?: boolean; }): Promise { - let lock = false; return new Promise((resolve) => { const input = document.createElement("input"); input.type = "file"; input.accept = props?.accept ?? ".json"; input.multiple = props?.multiple ?? true; input.style.display = "none"; - // add a change event listener to the file input - input.onchange = async (e: Event) => { - lock = true; - resolve(Array.from((e.target as HTMLInputElement).files!)); - document.body.removeChild(input); + + let isResolved = false; + + const cleanup = () => { + // Check if the input element still exists in the DOM before attempting to remove it + if (input && document.body.contains(input)) { + try { + document.body.removeChild(input); + } catch (error) { + console.warn("Error removing input element:", error); + } + } + window.removeEventListener("focus", handleFocus); }; - window.addEventListener( - "focus", - () => { - setTimeout(() => { - if (!lock) { - resolve([]); - document.body.removeChild(input); - } - }, 300); - }, - { once: true }, - ); - // add the input element to the body to ensure it is part of the DOM + + const handleChange = (e: Event) => { + if (!isResolved) { + isResolved = true; + const files = Array.from((e.target as HTMLInputElement).files!); + cleanup(); + resolve(files); + } + }; + + const handleFocus = () => { + setTimeout(() => { + if (!isResolved) { + isResolved = true; + cleanup(); + resolve([]); + } + }, 300); + }; + + input.addEventListener("change", handleChange); + window.addEventListener("focus", handleFocus); + document.body.appendChild(input); - // trigger the file input click event to open the file dialog input.click(); + + // Fallback timeout to ensure resolution + setTimeout(() => { + if (!isResolved) { + isResolved = true; + cleanup(); + resolve([]); + } + }, 60000); }); }