HMCL-dev/HMCL · error · FileNotFoundException
Entry not found
Error message
Entry not found: {entryPath} What it means
ArchiveFileTree.getInputStream(String entryPath) looks up the entry by path and throws FileNotFoundException 'Entry not found: <entryPath>' when no entry with that path exists in the archive. This is the string-based overload; entry objects bypass the check.
Solutions
- Check the entry exists first with getEntry(entryPath) != null before opening the stream.
- List entries (or use the tree traversal) to find the correct exact path, including case.
- Handle the FileNotFoundException and treat the missing file as a soft failure (e.g. mod without plugin.yml).
- Verify you opened the intended archive (right jar/version).
Example fix
// before
InputStream in = tree.getInputStream("fabric.mod.json"); // FileNotFoundException if absent
// after
if (tree.getEntry("fabric.mod.json") != null) {
InputStream in = tree.getInputStream("fabric.mod.json");
} else {
// fallback: not a fabric mod
} Defensive patterns
Strategy: validation
Validate before calling
if (tree.getEntry("fabric.mod.json") != null) {
try (InputStream in = tree.getInputStream("fabric.mod.json")) { /* ... */ }
} Try / catch
try {
InputStream in = tree.getInputStream(entryPath);
} catch (FileNotFoundException e) {
// entry absent; treat as missing file
} Prevention
- Resolve the exact entry path (case included) from the tree before reading.
- Guard with getEntry() != null when the file is optional.
- Confirm the correct archive version is opened.
When it happens
Trigger: Calling getInputStream("path/in/archive") with a path that does not match any entry — missing entry, wrong casing, missing leading/trailing slash conventions, or path present only in a different archive.
Common situations: Reading well-known files like 'fabric.mod.json' or 'plugin.yml' from jars that turn out to be of the other type; files removed/renamed in newer versions of a mod.
Understand the failure class
Background: "File not found" and ENOENT errors: why libraries can't find a file that should exist — this error's family across 50 libraries.
Related errors
- Asset index file malformed
- Bad exit code
- Cannot export a background directory as a theme-pack asset
- Cannot find suitable encoding for the zip.
- Cannot parse the version of
AI-assisted analysis of HMCL-dev/HMCL@24702dc5a0 (2026-09-10).
Data as JSON: /api/errors/fd801db0ccf0a2db.
Report an issue: GitHub.
Appendix: source
Thrown at HMCLCore/src/main/java/org/jackhuang/hmcl/util/tree/ArchiveFileTree.java:175
dir = dir.subDirs.computeIfAbsent(item, Dir::new);
if (isLastPart) {
if (dir.entry == null)
dir.entry = entry;
else if (!dir.entry.isDirectory())
LOG.warning("A file and a directory have the same name: " + entry.getName());
break;
}
}
}
public abstract InputStream getInputStream(E entry) throws IOException;
public @NotNull InputStream getInputStream(String entryPath) throws IOException {
E entry = getEntry(entryPath);
if (entry == null)
throw new FileNotFoundException("Entry not found: " + entryPath);
return getInputStream(entry);
}
public BufferedReader getBufferedReader(@NotNull E entry) throws IOException {
return new BufferedReader(new InputStreamReader(getInputStream(entry), StandardCharsets.UTF_8));
}
public @NotNull BufferedReader getBufferedReader(String entryPath) throws IOException {
E entry = getEntry(entryPath);
if (entry == null)
throw new FileNotFoundException("Entry not found: " + entryPath);
return getBufferedReader(entry);
}
public byte[] readBinaryEntry(@NotNull E entry) throws IOException {
try (InputStream input = getInputStream(entry)) {
return input.readAllBytes();
}View on GitHub (pinned to 24702dc5a0)