HMCL-dev/HMCL · error · IOException
/assets/
Error message
/assets/
What it means
Validation failure: an Mcbbs modpack manifest must declare a non-null files array listing every file in the pack. A manifest without files cannot be installed or completed, so validate() rejects it with JsonParseException.
Solutions
- Add a "files" array (possibly empty []) to the manifest JSON
- Re-export/re-download the modpack with a spec-compliant tool
- Validate the manifest against the Mcbbs modpack spec before importing
Example fix
// before
{"manifestType": "minecraftModpack"}
// after
{"manifestType": "minecraftModpack", "files": [], "addons": []} Defensive patterns
Strategy: validation
Validate before calling
if (!manifest.has("files") || manifest.get("files").isJsonNull())
throw new IllegalArgumentException("Manifest missing files array"); Try / catch
try { manifest.validate(); } catch (JsonParseException e) { /* report missing field to user */ } Prevention
- Always emit "files": [] even for empty packs
- Validate exported manifests against the spec
- Test-export a minimal pack with your tool
When it happens
Trigger: Importing an Mcbbs pack whose manifest JSON lacks the "files" field or has it explicitly null.
Common situations: Hand-crafted or minimal manifests missing the files section; packs exported by broken tools; manifests for server-side-only packs with files omitted instead of an empty array.
Understand the failure class
Background: "is required", "must be set", "missing required field": configuration validation errors across open-source libraries — this error's family across 36 libraries.
Related errors
- Invalid library path:
- Interrupted while waiting for pending instance writes
- Instance
- Theme-pack author must be an object or a string
- Theme packs cannot reference built-in wallpaper
AI-assisted analysis of HMCL-dev/HMCL@24702dc5a0 (2026-09-10).
Data as JSON: /api/errors/67f7ad26e741a125.
Report an issue: GitHub.
Appendix: source
Thrown at HMCL/src/main/java/org/jackhuang/hmcl/game/HMCLGameLauncher.java:202
private Path extractLwjglUnsafeAgent() throws IOException {
String agentVersion = JarUtils.getAttribute("hmcl.lwjgl-unsafe-agent.version", null);
if (agentVersion == null) {
throw new IOException("Missing hmcl.lwjgl-unsafe-agent.version attribute");
}
Library library = new Library(new Artifact("org.glavo", "lwjgl-unsafe-agent", agentVersion));
String fileName = library.artifact().getFileName();
Path agentPath = instance.getLayout().getLibraryFile(instance.getId(), library).toAbsolutePath().normalize();
if (agentPath.toString().contains("=")) {
throw new IOException("Invalid library path: " + agentPath);
}
byte[] bytes;
try (InputStream input = DefaultLauncher.class.getResourceAsStream("/assets/" + fileName)) {
if (input == null) {
throw new IOException("/assets/" + fileName + " not found");
}
bytes = input.readAllBytes();
}
if (Files.isRegularFile(agentPath)) {
try {
if (Files.size(agentPath) == bytes.length) {
return agentPath;
}
} catch (IOException e) {
LOG.warning("Failed to check size of " + agentPath, e);
}
}
Files.createDirectories(agentPath.getParent());
FileUtils.saveSafely(agentPath, output -> output.write(bytes));
return agentPath;View on GitHub (pinned to 24702dc5a0)