{"record":{"id":"f31f49bb012dafdb","repo":"GoogleContainerTools/skaffold","slug":"unable-to-create-directory-q-w-f31f49","errorCode":null,"errorMessage":"unable to create directory %q: %w","messagePattern":"unable to create directory %q: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"pkg/skaffold/event/v2/event.go","lineNumber":318,"sourceCode":"\t\t\t\tif x.Namespace != de.Namespace || x.PodName != de.PodName || x.ContainerName != de.ContainerName {\n\t\t\t\t\tev.state.DebuggingContainers[n] = x\n\t\t\t\t\tn++\n\t\t\t\t}\n\t\t\t}\n\t\t\tev.state.DebuggingContainers = ev.state.DebuggingContainers[:n]\n\t\t}\n\t\tev.stateLock.Unlock()\n\t}\n\tev.logEvent(event)\n}\n\n// SaveEventsToFile saves the current event log to the filepath provided\nfunc SaveEventsToFile(fp string) error {\n\thandler.logLock.Lock()\n\t// Ensure that the filepath provided has the directories available when attemping to save the file.\n\tdir := filepath.Dir(fp)\n\tif err := os.MkdirAll(dir, 0700); err != nil {\n\t\treturn fmt.Errorf(\"unable to create directory %q: %w\", dir, err)\n\t}\n\tf, err := os.OpenFile(fp, os.O_APPEND|os.O_WRONLY|os.O_CREATE, 0600)\n\tif err != nil {\n\t\treturn fmt.Errorf(\"opening %s: %w\", fp, err)\n\t}\n\tdefer f.Close()\n\tmarshaller := jsonpb.Marshaler{}\n\tfor _, ev := range handler.eventLog {\n\t\tcontents := bytes.NewBuffer([]byte{})\n\t\tif err := marshaller.Marshal(contents, ev); err != nil {\n\t\t\treturn fmt.Errorf(\"marshalling event: %w\", err)\n\t\t}\n\t\tif _, err := f.WriteString(contents.String() + \"\\n\"); err != nil {\n\t\t\treturn fmt.Errorf(\"writing string: %w\", err)\n\t\t}\n\t}\n\thandler.logLock.Unlock()\n\treturn nil","sourceCodeStart":300,"sourceCodeEnd":336,"githubUrl":"https://github.com/GoogleContainerTools/skaffold/blob/a1189de023efc32d4b8e11f395acc678aa555011/pkg/skaffold/event/v2/event.go#L300-L336","documentation":"The v2 event package's SaveEventsToFile mirrors the v1 behavior: it creates the target directory with os.MkdirAll(dir, 0700) before opening the file, wrapping failures as 'unable to create directory %q'. Identical causes and fixes as the v1 variant, but events come from the v2 event log.","triggerScenarios":"Calling pkg/skaffold/event/v2 SaveEventsToFile with a filepath whose parent directories cannot be created: no write permission, a file blocking a path component, read-only filesystem, or invalid path characters.","commonSituations":"Pointing the v2 event log at a read-only mount or another user's home directory; a stale regular file occupying the intended directory path; CI runners with sanitized /tmp permissions.","solutions":["Verify no regular file exists at any directory segment of the target path","Ensure the current user has write permission on the nearest existing parent (chmod/chown or choose another location)","Target a writable directory such as os.TempDir() or a mounted volume","Read the wrapped syscall error (EACCES/ENOTDIR/EROFS) to identify the failing component"],"exampleFix":"// before\nv2event.SaveEventsToFile(\"/sys/fs/cgroup/skaffold/events.json\")\n// after\nv2event.SaveEventsToFile(filepath.Join(os.TempDir(), \"skaffold-v2-events.json\"))","handlingStrategy":"validation","validationCode":"dir := filepath.Dir(fp)\nif info, err := os.Stat(dir); err == nil && !info.IsDir() {\n    return fmt.Errorf(\"%s blocks v2 event log directory\", dir)\n}\nif err := os.MkdirAll(dir, 0700); err != nil {\n    return fmt.Errorf(\"cannot prepare v2 event log dir %q: %w\", dir, err)\n}","typeGuard":null,"tryCatchPattern":"if err := v2event.SaveEventsToFile(fp); err != nil {\n    var pErr *fs.PathError\n    if errors.As(err, &pErr) && (errors.Is(pErr.Err, fs.ErrPermission) || errors.Is(pErr.Err, syscall.EROFS)) {\n        log.Warnf(\"v2 event log destination unusable: %v\", err)\n        return nil\n    }\n    return err\n}","preventionTips":["Default v2 event log paths to writable temp or volume directories","Verify path components with os.Stat before saving","Avoid read-only and pseudo filesystems as log destinations","Grant the running user ownership of the log directory in CI images"],"tags":["filesystem","events","v2","mkdir"],"backgroundTag":"permission-denied","analyzedSha":"a1189de023efc32d4b8e11f395acc678aa555011","analyzedAt":"2026-09-05T12:09:27.064Z","contentChangedAt":"2026-09-05T12:09:27.064Z","schemaVersion":2},"datasetVersion":"2026-09-12T17:17:11.597Z"}