quarkusio/quarkus · error · GradleException

Failed to get source file mtime for

Error message

Failed to get source file mtime for 

What it means

CustomFileSystemOperations.execute (used by Quarkus' timestamp-preserving copy action) resolves each source file and reads its last-modified time via Files.getLastModifiedTime. On IOException it throws GradleException 'Failed to get source file mtime for <sourcePath>'. This metadata is needed to preserve modification timestamps on copied files.

Source

Thrown at devtools/gradle/gradle-application-plugin/src/main/java/io/quarkus/gradle/util/CustomFileSystemOperations.java:97

        public TimestampPreservingCopyAction(Path srcDir, Path destDir, List<CopiedFileMetadata> processedFiles) {
            this.srcDir = srcDir;
            this.destDir = destDir;
            this.processedFiles = processedFiles;
        }

        @Override
        public void execute(FileCopyDetails details) {
            // Capture source file timestamp for later restoration.
            // Also delete any pre-existing non-writeable destination file to prevent copy failures.
            // This occurs with read-only files like 'app-cds.jsa' which should remain read-only.

            FileTime sourceMtime;
            Path sourceFile = srcDir.resolve(details.getSourcePath());
            try {
                sourceMtime = Files.getLastModifiedTime(sourceFile);
            } catch (IOException e) {
                throw new GradleException("Failed to get source file mtime for " + details.getSourcePath(), e);
            }
            Path destFile = destDir.resolve(details.getPath());
            if (Files.exists(destFile) && !Files.isWritable(destFile)) {
                deleteFileIfExists(destFile);
            }
            processedFiles.add(new CopiedFileMetadata(sourceFile, destFile, sourceMtime));
        }
    }

    private record CopiedFileMetadata(Path source, Path destination, FileTime sourceMtime) {
    }

    /**
     * Copies files while preserving their original timestamps.
     *
     * @param customizer configuration customizer
     * @return the result of the copy operation
     */

View on GitHub (pinned to e1c734241f)

Solutions

  1. Re-run the build — a transient race (file deleted mid-copy) usually resolves on a clean retry.
  2. Ensure no concurrent task/process deletes the source directory while copying (avoid running clean in parallel).
  3. Check read permissions on the source directory and files.
  4. Replace broken symlinks or remove special files from the source directory.
Defensive patterns

Strategy: retry

Validate before calling

File srcDir = ...;
if (!srcDir.canRead()) throw new IllegalStateException("source dir unreadable: " + srcDir);
// avoid concurrent clean while copy tasks run: use --no-parallel and don't run clean concurrently

Try / catch

try {
    ./gradlew build
} catch (GradleException e) {
    if (e.getMessage().startsWith("Failed to get source file mtime for")) {
        // transient race — stop other build processes and retry
    }
}

Prevention

When it happens

Trigger: Running a Quarkus Gradle task that copies files with the custom copy/sync configuration when the source file cannot be stat'd: the source file was deleted or renamed between listing and copying (race with concurrent task or clean), or an I/O permission error occurs reading the attribute.

Common situations: Parallel Gradle tasks or external processes (clean, IDE sync) deleting files mid-copy; symlinked or special files in srcDir; permission-restricted source directories; network filesystems flaking on attribute reads.

Understand the failure class

Background: "failed to read file", EACCES, ENOENT and "could not read <path>" errors: when a program can't read a file from disk — this error's family across 49 libraries.

Related errors


AI-assisted analysis of quarkusio/quarkus@e1c734241f (2026-09-05). Data as JSON: /api/errors/9b90a02f50a2bb63. Report an issue: GitHub.