bazelbuild/bazel · error · RuntimeException
Could not write exit file at ${file}
Error message
Could not write exit file at ${file} What it means
Thrown by JUnit4Runner.exitFileActive when the runner cannot truncate the file named by the TEST_PREMATURE_EXIT_FILE environment variable. Bazel's test harness sets this variable and expects the runner to empty the file at startup as a liveness signal; an IOException while opening or writing it is wrapped in a RuntimeException and aborts the run before any test executes.
Source
Thrown at src/java_tools/junitrunner/java/com/google/testing/junit/runner/junit4/JUnit4Runner.java:127
Runtime.getRuntime().removeShutdownHook(shutdownHook);
}
}
// Support for "premature exit files": Tests may write this to communicate
// to the runner in case of premature exit.
private static File getExitFile() {
String exitFile = System.getenv("TEST_PREMATURE_EXIT_FILE");
return exitFile == null ? null : new File(exitFile);
}
private static void exitFileActive(@Nullable File file) {
if (file != null) {
try (FileOutputStream outputStream = new FileOutputStream(file, false)) {
// Overwrite file content.
outputStream.write(new byte[0]);
outputStream.close();
} catch (IOException e) {
throw new RuntimeException("Could not write exit file at " + file, e);
}
}
}
private void exitFileInactive(@Nullable File file) {
if (file != null) {
try {
file.delete();
} catch (Throwable t) {
// Just print the stack trace, to avoid masking a real test failure.
t.printStackTrace(testRunnerOut);
}
}
}
// VisibleForTesting
TestSuiteModel getModel() {
return modelSupplier.get();View on GitHub (pinned to e6e199d060)
Solutions
- If running the runner by hand, unset TEST_PREMATURE_EXIT_FILE (the code tolerates a null file).
- Otherwise make the parent directory of the path exist and be writable by the test process (mkdir -p, chmod, correct volume mounts).
- Free disk space / fix filesystem permissions on the sandbox tree and re-run bazel test.
- When wrapping the runner, catch and report the IOException with the file path before it masks the real test result.
Example fix
# before TEST_PREMATURE_EXIT_FILE=/nonexistent/dir/exit_file java ... JUnit4Runner ... # after (manual run) unset TEST_PREMATURE_EXIT_FILE java ... JUnit4Runner ...
Defensive patterns
Strategy: validation
Validate before calling
// before running the runner in-process
String exitFile = System.getenv("TEST_PREMATURE_EXIT_FILE");
if (exitFile != null) {
File f = new File(exitFile);
File dir = f.getParentFile();
if (dir != null && !(dir.isDirectory() && dir.canWrite())) {
throw new IllegalStateException("TEST_PREMATURE_EXIT_FILE dir not writable: " + dir);
}
} Prevention
- Unset TEST_PREMATURE_EXIT_FILE when invoking the runner outside bazel test.
- Mount /tmp (or the sandbox tree) writable in containers that run Bazel tests.
- Monitor disk space on CI agents; premature-exit writes fail early when full.
When it happens
Trigger: TEST_PREMATURE_EXIT_FILE points into a directory that does not exist, is read-only, or is not writable by the test user; the path is on a full disk or a filesystem that rejects the open (e.g. path names a directory).
Common situations: Running the JUnit4Runner manually with copied harness environment variables after the Bazel sandbox was cleaned up; docker containers where /tmp is mounted read-only; disk-full CI agents; SELinux denying writes to the sandbox path.
Related errors
- Error writing shard file ${shardFile}
- Unsupported JUnit Runner API version ${JUNIT_API_VERSION_PRO
- No filter expression specified after ${arg}
- Could not create custom sharding strategy class ${strategy}
- This converter doesn't support Starlark reversal.
AI-assisted analysis of bazelbuild/bazel@e6e199d060 (2026-08-14).
Data as JSON: /api/errors/3c563e48f4053a2d.
Report an issue: GitHub.