different-ai/openwork · error
uploadErrorMessage(metadata.filename, error)
Error message
uploadErrorMessage(metadata.filename, error)
What it means
When uploading an attachment into the worker inbox via endpoint.client.uploadInbox, any thrown error is re-thrown as 'uploadErrorMessage(metadata.filename, error)' so the failure names the file and cause. This wraps network failures, permission errors, and client-side I/O errors from reading the file.
Source
Thrown at apps/app/src/react-app/domains/session/sync/attachment-file-part.ts:377
// chip already shows its uploading state. When the transport uploads the
// original file from its local path, re-encoding would detach that path,
// so the original bytes are sent instead.
const file = input.endpoint.client.uploadInboxPrefersOriginalFile?.(attachment.file)
? attachment.file
: await compressImageFile(attachment.file);
const metadata = resolveAttachmentFileMetadata(file);
const id = input.createId ? input.createId() : randomAttachmentId();
const inboxPath = buildChatAttachmentInboxPath({
sessionId: input.sessionId,
filename: metadata.filename,
id,
});
let result: InboxUploadResult;
try {
result = await input.endpoint.client.uploadInbox(workspaceId, file, { path: inboxPath });
} catch (error) {
throw new Error(uploadErrorMessage(metadata.filename, error));
}
if (result.ok === false) {
throw new Error(`Failed to copy attachment "${metadata.filename}" into this worker workspace: upload was rejected`);
}
if (!result.path.trim()) {
throw new Error(`Failed to copy attachment "${metadata.filename}" into this worker workspace: upload did not return a path`);
}
if (result.bytes !== file.size) {
throw new Error(`Failed to copy attachment "${metadata.filename}" into this worker workspace: expected ${file.size} bytes, wrote ${result.bytes}`);
}
const workspacePath = workspaceInboxPath(result.path);
const absolutePath = joinWorkspaceRelativePath(workspaceRoot, workspacePath);
uploaded.push({
filename: metadata.filename,
mime: metadata.mime,
bytes: result.bytes,View on GitHub (pinned to 2b7df46e8a)
Solutions
- Inspect the wrapped cause from uploadErrorMessage and retry the send if the failure was transient (network).
- Re-attach the file if it was moved or deleted; verify it is readable.
- Check server logs/inbox permissions if uploads persistently fail.
Example fix
// before: await parts(store, draft) // throws with wrapped upload error | // after: try { await parts(store, draft) } catch (e) { showUploadError(e); } // names filename + cause Defensive patterns
Strategy: try-catch
Validate before calling
try { await attachment.file.slice(0, 1).arrayBuffer(); } catch { showToast(`Cannot read "${attachment.filename}" — re-attach the file`); return; } Try / catch
try { const parts = await composerAttachmentsToWorkspaceFileParts({ attachments, endpoint, sessionId, workspaceRoot }); } catch (e) { showToast(String(e.message)); if (isTransient(e)) { await retrySend(); } } Prevention
- Verify attached files still exist and are readable at send time.
- Retry transient network failures with backoff before giving up.
- Surface the wrapped filename+cause message instead of a generic failure.
When it happens
Trigger: uploadInbox throws — server unreachable, HTTP error on the upload request, file read failure (file moved/deleted/permission revoked after attach), or the inbox path could not be created.
Common situations: Temporary server outage while sending a message with attachments; the user moved/renamed/deleted the attached file on disk after adding it to the composer; sandbox permission prevents reading the file.
Related errors
- Failed to copy attachment "${metadata.filename}" into this w
- Failed to copy attachment "${metadata.filename}" into this w
- Failed to copy attachment "${metadata.filename}" into this w
- attachment_fetch_failed
- Attachment hostname ${hostname} did not resolve.
AI-assisted analysis of different-ai/openwork@2b7df46e8a (2026-09-01).
Data as JSON: /api/errors/66d6e44b08dff066.
Report an issue: GitHub.