{"record":{"id":"ebe566a13f203eda","repo":"argoproj/argo-workflows","slug":"failed-to-close-s-w","errorCode":null,"errorMessage":"failed to close %s: %w","messagePattern":"failed to close (.+?): %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"cmd/argoexec/commands/emissary.go","lineNumber":720,"sourceCode":"\tdstPath := filepath.Join(varRunArgo, \"/outputs/artifacts/\", strings.TrimSuffix(srcPath, \"/\")+\".tgz\")\n\tlogger.WithFields(logging.Fields{\n\t\t\"src\": srcPath,\n\t\t\"dst\": dstPath,\n\t}).Info(ctx, \"saving artifact\")\n\tz := filepath.Dir(dstPath)\n\tif err := os.MkdirAll(z, 0o755); err != nil { // chmod rwxr-xr-x\n\t\treturn fmt.Errorf(\"failed to create directory %s: %w\", z, err)\n\t}\n\tdst, err := os.Create(dstPath)\n\tif err != nil {\n\t\treturn fmt.Errorf(\"failed to create destination %s: %w\", dstPath, err)\n\t}\n\tdefer func() { _ = dst.Close() }()\n\tif err = archive.TarGzToWriter(ctx, srcPath, gzip.DefaultCompression, dst); err != nil {\n\t\treturn fmt.Errorf(\"failed to tarball the output %s to %s: %w\", srcPath, dstPath, err)\n\t}\n\tif err = dst.Close(); err != nil {\n\t\treturn fmt.Errorf(\"failed to close %s: %w\", dstPath, err)\n\t}\n\treturn nil\n}\n\nfunc saveParameter(ctx context.Context, template *wfv1.Template, srcPath string) error {\n\tlogger := logging.RequireLoggerFromContext(ctx)\n\n\tif common.FindOverlappingVolume(template, srcPath) != nil {\n\t\tlogger.WithField(\"src\", srcPath).Info(ctx, \"no need to save parameter - on overlapping volume\")\n\t\treturn nil\n\t}\n\tsrc, err := os.Open(filepath.Clean(srcPath))\n\tif os.IsNotExist(err) { // might be optional, so we ignore\n\t\tlogger.WithField(\"src\", srcPath).WithError(err).Warn(ctx, \"cannot save parameter, does not exist\")\n\t\treturn nil\n\t}\n\tif err != nil {\n\t\treturn fmt.Errorf(\"failed to open %s: %w\", srcPath, err)","sourceCodeStart":702,"sourceCodeEnd":738,"githubUrl":"https://github.com/argoproj/argo-workflows/blob/35bff19146f5a6ada77468c431f2624bd577e373/cmd/argoexec/commands/emissary.go#L702-L738","documentation":"saveArtifact failed on the explicit dst.Close() after tarballing succeeded. The tar.gz data may not be fully flushed to disk, so the artifact file can be truncated or corrupt even though compression itself succeeded. This is uncommon and almost always a disk-level problem.","triggerScenarios":"dst.Close() returns an error after TarGzToWriter: buffered data flush fails due to ENOSPC, I/O error on the underlying storage, or NFS/volume detach mid-write.","commonSituations":"Disk fills exactly during final flush of a large artifact; flaky network-attached storage (EBS/Ceph) returning I/O errors; node-level storage faults.","solutions":["Retry the workflow step; if it recurs, investigate node storage health (dmesg, kubelet logs).","Free disk space — Close flushes remaining buffered gzip data and can hit ENOSPC.","Keep large artifacts on reliable volumes; avoid overfull local disks.","Check for truncated/corrupt artifact uploads from that node and cordon it if the I/O errors persist."],"exampleFix":null,"handlingStrategy":"retry","validationCode":"// pre-check storage health headroom\nstat, err := os.Statfs(\"/var/run/argo/outputs\")\nif err == nil && stat.Bavail*uint64(stat.Bsize) < 100<<20 {\n    return errors.New(\"less than 100MB free for artifact export\")\n}","typeGuard":null,"tryCatchPattern":"err := runStep(ctx)\nif err != nil && strings.Contains(err.Error(), \"failed to close\") {\n    // close() flush failures are usually transient storage issues: retry once\n    return retryOnce(ctx, err)\n}","preventionTips":["Keep 10-20% free disk on nodes running artifact-heavy workflows","Prefer reliable volumes over flaky network storage for output staging","Retry transient step failures (retryStrategy) to ride out storage blips","Cordon nodes emitting repeated I/O errors in dmesg"],"tags":["argo-workflows","argoexec","artifacts","filesystem"],"backgroundTag":"file-close-failed","analyzedSha":"35bff19146f5a6ada77468c431f2624bd577e373","analyzedAt":"2026-09-03T19:34:35.908Z","contentChangedAt":"2026-09-03T19:34:35.908Z","schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}