{"record":{"id":"6f5e9a2a8943bba2","repo":"microsoft/aspire","slug":"unable-to-create-a-unique-browser-log-command-artifact-file","errorCode":null,"errorMessage":"Unable to create a unique browser-log command artifact file under '{directory}'.","messagePattern":"Unable to create a unique browser-log command artifact file under '(.+?)'\\.","errorType":"exception","errorClass":"IOException","httpStatus":null,"severity":"error","filePath":"src/Aspire.Hosting.Browsers/BrowserLogsArtifacts.cs","lineNumber":93,"sourceCode":"            FileStream stream;\n            try\n            {\n                stream = new FileStream(filePath, FileMode.CreateNew, FileAccess.Write, FileShare.Read, bufferSize: 64 * 1024, useAsync: true);\n            }\n            catch (IOException) when (attempt < 99 && File.Exists(filePath))\n            {\n                continue;\n            }\n\n            await using (stream.ConfigureAwait(false))\n            {\n                await stream.WriteAsync(content, cancellationToken).ConfigureAwait(false);\n            }\n\n            return new BrowserLogsArtifact(resourceName, artifactType, filePath, mimeType, content.Length, createdAt);\n        }\n\n        throw new IOException($\"Unable to create a unique browser-log command artifact file under '{directory}'.\");\n    }\n\n    private static string GetAppHostSegment(string? appHostKey)\n    {\n        if (string.IsNullOrWhiteSpace(appHostKey))\n        {\n            return \"unknown-apphost\";\n        }\n\n        var segment = appHostKey.Length > AppHostKeySegmentLength\n            ? appHostKey[..AppHostKeySegmentLength]\n            : appHostKey;\n\n        return SanitizePathSegment(segment, fallback: \"unknown-apphost\");\n    }\n\n    private static string GetAspireCommandArtifactRoot()\n    {","sourceCodeStart":75,"sourceCodeEnd":111,"githubUrl":"https://github.com/microsoft/aspire/blob/25830f84bd145686607ad00c057b3f84e2e51d43/src/Aspire.Hosting.Browsers/BrowserLogsArtifacts.cs#L75-L111","documentation":"BrowserLogsArtifacts.WriteArtifactAsync generates candidate file names and creates the artifact file in a command artifacts directory. If it cannot create a unique file there (every candidate name collides or creation fails), it throws this IOException to signal the browser-log artifact could not be persisted.","triggerScenarios":"Writing a browser-log artifact when candidate filenames under the target directory are exhausted by collisions, or file creation fails (read-only directory, full disk, path-length limits).","commonSituations":"Artifacts directory holding thousands of same-named files; running under an account without write permission to the artifacts folder; long AppHost/resource names pushing paths past MAX_PATH on Windows; disk quota exceeded.","solutions":["Verify the artifacts directory is writable by the process user.","Free disk space / check quota.","Clean stale artifacts from the directory.","Shorten the artifacts directory path or resource names to avoid path-length limits."],"exampleFix":"// before\nvar artifact = await artifacts.WriteArtifactAsync(resource, BrowserLogsArtifactType.Console, directory: readOnlyDir, content, ct);\n\n// after\nDirectory.CreateDirectory(directory);\nif (!IsWritable(directory)) throw new InvalidOperationException(\"Configure a writable browser-logs artifacts directory.\");\nvar artifact = await artifacts.WriteArtifactAsync(resource, BrowserLogsArtifactType.Console, directory, content, ct);","handlingStrategy":"try-catch","validationCode":"// Pre-check the artifacts directory before writing\nif (!Directory.Exists(directory)) Directory.CreateDirectory(directory);\nvar probe = Path.Combine(directory, \".write-test\");\nusing (var fs = File.Create(probe)) { }\nFile.Delete(probe);","typeGuard":null,"tryCatchPattern":"try { artifact = await artifacts.WriteArtifactAsync(resource, type, directory, content, ct); }\ncatch (IOException ex) { logger.LogError(ex, \"Cannot persist browser-log artifact under {Dir}; cleaning stale files.\", directory); CleanStaleArtifacts(directory, olderThan: TimeSpan.FromHours(1)); }","preventionTips":["Ensure the artifacts directory is writable by the process account.","Prune old artifacts periodically to avoid filename exhaustion and disk pressure.","Keep AppHost/resource names short to stay under path-length limits."],"tags":["io","filesystem","artifact-write","filename-collision"],"backgroundTag":"file-write-failed","analyzedSha":"25830f84bd145686607ad00c057b3f84e2e51d43","analyzedAt":"2026-09-16T11:10:06.193Z","contentChangedAt":"2026-09-16T11:10:06.193Z","schemaVersion":2},"datasetVersion":"2026-09-21T09:17:21.228Z"}