{"record":{"id":"b5457e926292a59f","repo":"github/copilot-sdk","slug":"classpath-resource-is-empty","errorCode":null,"errorMessage":"Classpath resource is empty: ","messagePattern":"Classpath resource is empty: ","errorType":"exception","errorClass":"IllegalStateException","httpStatus":null,"severity":"error","filePath":"java/sdk/src/main/java/com/github/copilot/ffi/NativeRuntimeLoader.java","lineNumber":585,"sourceCode":"        if (isWindows()) {\n            return;\n        }\n        final boolean executableSet;\n        try {\n            executableSet = path.toFile().setExecutable(true, false);\n        } catch (SecurityException ex) {\n            throw new IOException(\"Failed to make Copilot CLI executable: \" + path, ex);\n        }\n        if (!executableSet || !Files.isExecutable(path)) {\n            throw new IOException(\"Failed to make Copilot CLI executable: \" + path);\n        }\n    }\n\n    private static void copyResourceToTemp(URL resource, String resourcePath, Path temp) throws IOException {\n        try (InputStream in = resource.openStream()) {\n            long bytesWritten = Files.copy(in, temp, StandardCopyOption.REPLACE_EXISTING);\n            if (bytesWritten == 0) {\n                throw new IllegalStateException(\"Classpath resource is empty: \" + resourcePath);\n            }\n        }\n        // Flush OS buffers to durable storage before the atomic rename.\n        try (FileChannel channel = FileChannel.open(temp, StandardOpenOption.WRITE)) {\n            channel.force(true);\n        }\n    }\n\n    /**\n     * Finds the Copilot CLI executable on the {@code PATH}.\n     *\n     * @return the absolute CLI path, or {@code null} if none was found\n     */\n    public static String findRuntimeOnPath() {\n        String pathValue = System.getenv(\"PATH\");\n        if (pathValue == null || pathValue.isBlank()) {\n            return null;\n        }","sourceCodeStart":567,"sourceCodeEnd":603,"githubUrl":"https://github.com/github/copilot-sdk/blob/cd8cf15dc3f9e762615790aaed0a771a0f392755/java/sdk/src/main/java/com/github/copilot/ffi/NativeRuntimeLoader.java#L567-L603","documentation":"copyResourceToTemp copies a classpath resource to a temp file and counts bytes written; a zero-byte result means the resource opened successfully but contained no data. The loader throws IllegalStateException because an empty native binary/asset is never valid — publishing it would cache a broken executable. This indicates the bundled artifact resource is empty or the stream was truncated.","triggerScenarios":"resource.openStream() yields 0 bytes for 'native/<classifier>/<file>' or the CLI resource during any extraction path (resolveRuntimeWrapper, extractRuntimeToCache, extractRuntimeAssetsToCache, extractCliToCache).","commonSituations":"A 0-byte file committed into the artifact jar; a broken release build that packaged empty natives; download corruption when the jar was fetched; a stub/placeholder resource left by misconfigured resource filtering (maven filtering corrupting binaries).","solutions":["Verify the resource inside the jar is non-empty (unzip -l / jar tf and extract to compare sizes); replace the artifact if empty.","Disable Maven resource filtering for binary/native resources (<filtering>false</filtering> on the native directory).","Re-download/rebuild the artifact and confirm checksums match the official release.","Clear the local cache dir so partial/truncated prior extractions aren't reused."],"exampleFix":"// before (pom.xml)\n<resource><directory>src/main/resources</directory><filtering>true</filtering></resource>\n// after\n<resource><directory>src/main/resources</directory><filtering>false</filtering><excludes><exclude>native/**</exclude></excludes></resource>","handlingStrategy":"validation","validationCode":"// Java: verify classpath resources are non-empty before extraction\nString resourcePath = \"native/linux-x64/runtime.node\";\ntry (InputStream in = loader.getResourceAsStream(resourcePath)) {\n    if (in == null || in.read() == -1) throw new IllegalStateException(\"Empty/missing classpath resource: \" + resourcePath);\n}","typeGuard":null,"tryCatchPattern":"try { loader.loadRuntime(); } catch (IllegalStateException e) { if (e.getMessage().startsWith(\"Classpath resource is empty\")) { // artifact jar is corrupt: rebuild/re-download and verify checksum } else throw e; }","preventionTips":["Never enable Maven resource filtering on binary/native resources","Verify artifact checksums after download or CI publish","Reject 0-byte files when committing native binaries","Clear the local cache after replacing artifact versions"],"tags":["classpath","empty-resource","java","corrupt-artifact"],"backgroundTag":"empty-required-field","analyzedSha":"cd8cf15dc3f9e762615790aaed0a771a0f392755","analyzedAt":"2026-09-09T18:32:31.973Z","contentChangedAt":"2026-09-09T18:32:31.973Z","schemaVersion":2},"datasetVersion":"2026-09-15T23:17:13.987Z"}