{"record":{"id":"50b994ac3ad84c35","repo":"immich-app/immich","slug":"errors-unable-to-upload-file","errorCode":null,"errorMessage":"errors.unable_to_upload_file","messagePattern":"errors\\.unable_to_upload_file","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"web/src/lib/utils/file-uploader.ts","lineNumber":210,"sourceCode":"          };\n        }\n      } catch (error) {\n        console.error(`Error calculating sha1 file=${assetFile.name})`, error);\n      }\n    }\n\n    if (!responseData) {\n      const queryParams = asQueryString(authManager.params);\n\n      uploadAssetsStore.updateItem(deviceAssetId, { message: $t('asset_uploading') });\n      const response = await uploadRequest<AssetMediaResponseDto>({\n        url: getBaseUrl() + '/assets' + (queryParams ? `?${queryParams}` : ''),\n        data: formData,\n        onUploadProgress: (event) => uploadAssetsStore.updateProgress(deviceAssetId, event.loaded, event.total),\n      });\n\n      if (![200, 201].includes(response.status)) {\n        throw new Error($t('errors.unable_to_upload_file'));\n      }\n\n      responseData = response.data;\n    }\n\n    if (responseData.status === AssetMediaStatus.Duplicate) {\n      uploadAssetsStore.track('duplicate');\n    } else {\n      uploadAssetsStore.track('success');\n    }\n\n    if (albumId && !authManager.isSharedLink) {\n      uploadAssetsStore.updateItem(deviceAssetId, { message: $t('asset_adding_to_album') });\n      await addAssetsToAlbums([albumId], [responseData.id], { notify: false });\n      uploadAssetsStore.updateItem(deviceAssetId, { message: $t('asset_added_to_album') });\n    }\n\n    uploadAssetsStore.updateItem(deviceAssetId, {","sourceCodeStart":192,"sourceCodeEnd":228,"githubUrl":"https://github.com/immich-app/immich/blob/e55ac299a4ec7cb372e35dbf2c6c05ee9ce77f6c/web/src/lib/utils/file-uploader.ts#L192-L228","documentation":"In the web app's file uploader, after POSTing the asset to /assets, any HTTP status other than 200/201 throws a localized error ('errors.unable_to_upload_file'). This signals the server rejected the upload (validation failure, auth issue, duplicate handling error, etc.) for that specific device asset.","triggerScenarios":"fileUploader receives an axios response from the /assets endpoint with a status outside {200, 201} — e.g. 401 (expired session), 413 (payload too large via reverse proxy), 4xx/5xx server errors.","commonSituations":"Nginx/proxy client_max_body_size smaller than the photo; session expiring mid-upload; server storage full or returning 500; uploading zero-byte or corrupted files the API rejects.","solutions":["Check the response status/body (network tab) to identify the underlying rejection (401 vs 413 vs 500).","For 413: raise the reverse proxy body-size limit (e.g. nginx client_max_body_size) above your largest photo/video.","For 401: re-authenticate (log in again) and retry the upload.","For 500: check immich-server logs (disk full? database error?) and free space or fix storage config.","Retry failed assets from the upload queue after fixing the cause."],"exampleFix":"// nginx before\nclient_max_body_size 1m;\n// after\nclient_max_body_size 50000M;","handlingStrategy":"try-catch","validationCode":"if (!navigator.onLine) throw new OfflineError('Defer upload until online');\nif (file.size === 0) throw new ValidationError('Refusing to upload empty file');","typeGuard":"const isUploadFailure = (e: unknown): boolean =>\n  e instanceof Error && e.message === $t('errors.unable_to_upload_file');","tryCatchPattern":"try { await fileUploader(file); } catch (e) { if (isUploadFailure(e)) { uploadAssetsStore.markFailed(deviceAssetId); showToast(t('errors.unable_to_upload_file')); } else throw e; }","preventionTips":["Set reverse-proxy client_max_body_size above your largest media file","Keep sessions alive during long uploads (re-auth before large batches)","Monitor server disk space; full disks surface as 500s during upload","Show per-asset upload status so failures can be retried individually"],"tags":["upload","http","network","web"],"backgroundTag":"http-error-response","analyzedSha":"e55ac299a4ec7cb372e35dbf2c6c05ee9ce77f6c","analyzedAt":"2026-09-15T07:20:19.675Z","contentChangedAt":"2026-09-15T07:20:19.675Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}