{"record":{"id":"a953389db1883d8d","repo":"larksuite/cli","slug":"create-temp-file-w","errorCode":null,"errorMessage":"create temp file: %w","messagePattern":"create temp file: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/vfs/localfileio/atomicwrite.go","lineNumber":60,"sourceCode":"// Link, which combines both guarantees this call has to make:\n//\n//   - No-clobber. Link fails with EEXIST instead of replacing an existing\n//     target, so the refusal is decided by the commit itself. A preceding\n//     existence check cannot do this: another writer may create the file while\n//     this one is still copying.\n//   - Whole-file visibility. The target name appears only once the content is\n//     complete and synced. Writing directly to the final name with O_EXCL would\n//     satisfy no-clobber but publish a partial file for the duration of the\n//     copy, and a killed process would leave that partial file behind as a\n//     phantom target for the next attempt.\n//\n// Rename cannot serve as the commit step because it replaces an existing target\n// unconditionally.\nfunc ExclusiveWriteFromReader(path string, reader io.Reader, perm os.FileMode) (int64, error) {\n\tdir := filepath.Dir(path)\n\ttmp, err := vfs.CreateTemp(dir, \".\"+filepath.Base(path)+\".*.tmp\")\n\tif err != nil {\n\t\treturn 0, fmt.Errorf(\"create temp file: %w\", err)\n\t}\n\ttmpName := tmp.Name()\n\n\tclosed := false\n\tdefer func() {\n\t\tif !closed {\n\t\t\ttmp.Close()\n\t\t}\n\t\t// The temp name is removed either way: on failure it is the partial\n\t\t// artifact, on success the link has already published the content.\n\t\tvfs.Remove(tmpName)\n\t}()\n\n\tif err := tmp.Chmod(perm); err != nil {\n\t\treturn 0, err\n\t}\n\tcopied, err := io.Copy(tmp, reader)\n\tif err != nil {","sourceCodeStart":42,"sourceCodeEnd":78,"githubUrl":"https://github.com/larksuite/cli/blob/7fd6ef3c07182257ce776cdc5a614e122d5bd4b3/internal/vfs/localfileio/atomicwrite.go#L42-L78","documentation":"ExclusiveWriteFromReader writes content to a temp file in the target's directory and then links it into place without ever replacing an existing target. This error wraps the failure of vfs.CreateTemp when creating that staging temp file ('.'+base+'.*.tmp' in the target directory). The write never starts; the original target is untouched.","triggerScenarios":"The target's parent directory does not exist, is not writable, or the path is invalid, causing CreateTemp to fail — raised via ExclusiveWriteFromReader (called by SaveExclusive and tests).","commonSituations":"Saving to a directory that was deleted or never created; read-only workspace/config directory; permission-changed directory; path pointing at a nonexistent mount; disk-full edge at creation.","solutions":["Create the parent directory first (e.g. os.MkdirAll(filepath.Dir(path), 0o755) or the vfs equivalent)","Check that the process has write permission on the target directory","Verify the target path is correct and on a mounted, writable filesystem","Inspect the wrapped cause (%w) — e.g. ENOENT vs EACCES — to distinguish missing dir from permissions"],"exampleFix":"// before\nn, err := ExclusiveWriteFromReader(\"/cfg/app/missing/file.json\", r, 0o600)\n// after\nif err := os.MkdirAll(\"/cfg/app/missing\", 0o755); err != nil {\n    return err\n}\nn, err := ExclusiveWriteFromReader(\"/cfg/app/missing/file.json\", r, 0o600)","handlingStrategy":"validation","validationCode":"func ensureWritableDir(path string) error {\n    dir := filepath.Dir(path)\n    fi, err := os.Stat(dir)\n    if err != nil { return fmt.Errorf(\"target dir missing: %w\", err) }\n    if !fi.IsDir() { return fmt.Errorf(\"%s is not a directory\", dir) }\n    if err := syscall.Access(dir, syscall.O_RDWR); err != nil { return fmt.Errorf(\"dir not writable: %w\", err) }\n    return nil\n}\n// call before ExclusiveWriteFromReader / SaveExclusive","typeGuard":"func canStage(path string) bool {\n    dir := filepath.Dir(path)\n    fi, err := os.Stat(dir)\n    return err == nil && fi.IsDir()\n}","tryCatchPattern":"if _, err := ExclusiveWriteFromReader(path, r, 0o600); err != nil && strings.Contains(err.Error(), \"create temp file\") {\n    if mkErr := os.MkdirAll(filepath.Dir(path), 0o755); mkErr != nil { return mkErr }\n    // retry once after creating the directory\n}","preventionTips":["Create parent directories before exclusive writes","Verify write permissions on config/workspace directories at startup","Check the wrapped errno: ENOENT = missing dir, EACCES = permissions, ENOSPC = disk full","Keep target paths within managed directories the CLI owns"],"tags":["filesystem","io","atomic-write","permissions"],"backgroundTag":"temp-file-creation-failed","analyzedSha":"7fd6ef3c07182257ce776cdc5a614e122d5bd4b3","analyzedAt":"2026-09-04T21:17:44.649Z","contentChangedAt":"2026-09-04T21:17:44.649Z","schemaVersion":2},"datasetVersion":"2026-09-12T02:17:10.037Z"}