{"record":{"id":"82a40f66f58dbfb0","repo":"flipped-aurora/gin-vue-admin","slug":"w-82a40f","errorCode":null,"errorMessage":"写入临时文件失败: %w","messagePattern":"写入临时文件失败: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"server/service/system/auto_code_task.go","lineNumber":280,"sourceCode":"\t}\n\tdir := filepath.Dir(target)\n\tif err := os.MkdirAll(dir, 0o755); err != nil {\n\t\treturn fmt.Errorf(\"创建目标目录 %s 失败: %w\", dir, err)\n\t}\n\ttmp, err := os.CreateTemp(dir, \".autocode-*\")\n\tif err != nil {\n\t\treturn fmt.Errorf(\"创建临时文件失败: %w\", err)\n\t}\n\ttmpName := tmp.Name()\n\tdefer os.Remove(tmpName)\n\tif _, err = tmp.Write(content); err == nil {\n\t\terr = tmp.Sync()\n\t}\n\tif closeErr := tmp.Close(); err == nil {\n\t\terr = closeErr\n\t}\n\tif err != nil {\n\t\treturn fmt.Errorf(\"写入临时文件失败: %w\", err)\n\t}\n\tif err = os.Chmod(tmpName, mode.Perm()); err != nil {\n\t\treturn fmt.Errorf(\"设置临时文件权限失败: %w\", err)\n\t}\n\tif err = os.Rename(tmpName, target); err != nil {\n\t\treturn fmt.Errorf(\"原子替换 %s 失败: %w\", target, err)\n\t}\n\treturn nil\n}\n\nfunc (l autoCodeTaskLayout) classify(target string) (string, error) {\n\tif isPathWithin(l.serverRoot, target) {\n\t\treturn autoCodeTaskBackend, nil\n\t}\n\tif isPathWithin(l.webRoot, target) {\n\t\treturn autoCodeTaskFrontend, nil\n\t}\n\treturn \"\", fmt.Errorf(\"自动代码目标不在服务端或前端目录内: %s\", target)","sourceCodeStart":262,"sourceCodeEnd":298,"githubUrl":"https://github.com/flipped-aurora/gin-vue-admin/blob/3136500ef380842b0eb6c4daa87c3f8a47fcf9e0/server/service/system/auto_code_task.go#L262-L298","documentation":"After writing content to the temp file, replaceAutoCodeFileAtomically finalizes write+Sync+Close; any error in that sequence is reported as 写入临时文件失败 wrapping the underlying cause. This catches short writes, I/O errors during fsync, and close-time errors that only surface flushed data failures.","triggerScenarios":"tmp.Write(content) returns n < len(content) or an error, tmp.Sync() fails (I/O error, ENOSPC), or tmp.Close() returns an error — all normalized into this single wrapped error.","commonSituations":"Disk full mid-write, network/cloud-sync filesystems failing fsync, container storage driver errors, or hardware I/O failures on the underlying volume.","solutions":["Check the wrapped cause: ENOSPC → free disk space; EIO → check dmesg/storage health","Sync/flush or temporarily exclude project dirs from cloud-sync/network filesystems (NFS, Dropbox) that break fsync","Retry generation once space/storage is healthy; staging copies make retries safe"],"exampleFix":"// before\n$ df -h /var/www/project  →  100% used\n// after\n$ df -h /var/www/project  →  42% used  # after cleanup, retry generation","handlingStrategy":"retry","validationCode":"if free, err := diskFree(dir); err == nil && free < 64*1024*1024 {\n    return fmt.Errorf(\"insufficient space for generation: %d bytes free\", free)\n}","typeGuard":null,"tryCatchPattern":"err := commitAutoCodeFileTask(task, publish, persist)\nif err != nil && strings.Contains(err.Error(), \"写入临时文件失败\") {\n    var perr *fs.PathError\n    if errors.As(err, &perr) && errors.Is(perr.Err, syscall.ENOSPC) {\n        log.Print(\"disk full — free space and retry\")\n    }\n    if errors.Is(err, syscall.EIO) {\n        log.Print(\"I/O error — check storage health (dmesg)\")\n    }\n}","preventionTips":["Alert on disk usage before running generation jobs","Avoid writing generated code to network-synced filesystems","Monitor dmesg/journalctl for storage I/O errors","Retry generation after transient I/O failures — staging is idempotent"],"tags":["go","filesystem","io","atomic-write"],"backgroundTag":"temp-file-write-failed","analyzedSha":"3136500ef380842b0eb6c4daa87c3f8a47fcf9e0","analyzedAt":"2026-08-31T13:50:02.721Z","schemaVersion":2},"datasetVersion":"2026-08-31T19:17:28.585Z"}