{"record":{"id":"f4db327e9e7d9d6f","repo":"multica-ai/multica","slug":"upload-attachment-s-w","errorCode":null,"errorMessage":"upload attachment %s: %w","messagePattern":"upload attachment (.+?): %w","errorType":"console","errorClass":null,"httpStatus":null,"severity":"error","filePath":"server/cmd/multica/cmd_issue.go","lineNumber":2000,"sourceCode":"\t\treturn fmt.Errorf(\"resolve issue: %w\", err)\n\t}\n\tissueID := issueRef.ID\n\n\t// Validate and read ALL attachments before uploading any. URLs are skipped\n\t// with a warning — `--attachment` only accepts local file paths. Reading\n\t// everything up front means a later invalid path (external / symlink escape\n\t// caught by the workdir guard) aborts the call with ZERO uploads, instead\n\t// of leaving an earlier file uploaded as an orphaned issue attachment while\n\t// the comment is never posted (which would duplicate on retry — MUL-4252).\n\tpending, err := collectLocalAttachments(cmd, attachments)\n\tif err != nil {\n\t\treturn err\n\t}\n\tvar attachmentIDs []string\n\tfor _, att := range pending {\n\t\tid, uploadErr := client.UploadFile(ctx, att.data, att.path, issueID)\n\t\tif uploadErr != nil {\n\t\t\treturn fmt.Errorf(\"upload attachment %s: %w\", att.path, uploadErr)\n\t\t}\n\t\tattachmentIDs = append(attachmentIDs, id)\n\t\tfmt.Fprintf(os.Stderr, \"Uploaded %s\\n\", att.path)\n\t}\n\n\tbody := map[string]any{\"content\": content}\n\tif parentID, _ := cmd.Flags().GetString(\"parent\"); parentID != \"\" {\n\t\tbody[\"parent_id\"] = parentID\n\t}\n\tif len(attachmentIDs) > 0 {\n\t\tbody[\"attachment_ids\"] = attachmentIDs\n\t}\n\tvar result map[string]any\n\tif err := client.PostJSON(ctx, \"/api/issues/\"+issueID+\"/comments\", body, &result); err != nil {\n\t\treturn fmt.Errorf(\"add comment: %w\", err)\n\t}\n\n\tfmt.Fprintf(os.Stderr, \"Comment added to issue %s.\\n\", issueRef.Display)","sourceCodeStart":1982,"sourceCodeEnd":2018,"githubUrl":"https://github.com/multica-ai/multica/blob/2c0912b6ec764b373d44eeea1e80f0d9f11ab417/server/cmd/multica/cmd_issue.go#L1982-L2018","documentation":"While adding a comment with attachments, each pre-validated local file is uploaded via client.UploadFile to the issue. This error wraps the failure of one upload (I/O read error, size limit, auth, 5xx) and names the offending file path. Note uploads happen after all files were validated, but a mid-loop failure can still leave earlier attachments orphaned — retrying will re-upload.","triggerScenarios":"`multica issue comment add <issue> --attachment big.bin` where the file exceeds a server size limit, the connection drops mid-upload, or the 60s-extended timeout is still too short for a very large/slow upload.","commonSituations":"Attaching large binaries over slow links; server-side upload restrictions; flaky networks causing truncated multipart requests.","solutions":["Retry the command once transient network issues clear.","Reduce the attachment size or split it (compress, split archives).","Confirm the file is a regular local file inside the workdir (no symlinks escaping it — the collect step would have caught that earlier).","Check server logs / upload limits if the failure is deterministic."],"exampleFix":null,"handlingStrategy":"retry","validationCode":"# bash: pre-check every attachment is a readable regular file\nfor f in \"${ATTACHMENTS[@]}\"; do\n  [[ -f \"$f\" && -r \"$f\" ]] || { echo \"bad attachment: $f\" >&2; exit 2; }\n  sz=$(stat -c%s \"$f\"); [[ $sz -le $MAX_UPLOAD ]] || { echo \"$f exceeds $MAX_UPLOAD bytes\" >&2; exit 2; }\ndone","typeGuard":null,"tryCatchPattern":"# bash: retry uploads once; report orphans on repeated failure\nmultica issue comment add \"$ISSUE\" --content \"$BODY\" \"${ATT[@]/#/--attachment }\" || {\n  echo \"upload failed — earlier files may be orphaned on the issue; check before re-running\" >&2; exit 1;\n}","preventionTips":["Size-check and readability-check attachments before the CLI call.","Keep attachments small or upload during stable network windows; remember a failed retry can orphan already-uploaded files."],"tags":["cli","upload","attachments","http"],"backgroundTag":null,"analyzedSha":"2c0912b6ec764b373d44eeea1e80f0d9f11ab417","analyzedAt":"2026-08-15T13:25:18.241Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}