flowable/flowable-engine · error · FlowableException
Failed to read resource ${resource}
Error message
Failed to read resource ${resource} What it means
If reading the classpath resource stream raises an IOException while opening or closing it, addClasspathResource() wraps the IOException in FlowableException("Failed to read resource ..."). Note that the 'not found' FlowableException from the try block is not an IOException and propagates unchanged; this message specifically means an I/O problem, and its cause holds the details.
Source
Thrown at modules/flowable-app-engine/src/main/java/org/flowable/app/engine/impl/repository/AppDeploymentBuilderImpl.java:82
AppResourceEntity resource = resourceEntityManager.create();
resource.setName(resourceName);
resource.setBytes(bytes);
deployment.addResource(resource);
return this;
}
@Override
public AppDeploymentBuilder addClasspathResource(String resource) {
try (final InputStream inputStream = this.getClass().getClassLoader().getResourceAsStream(resource)) {
if (inputStream == null) {
throw new FlowableException("resource '" + resource + "' not found");
}
return addInputStream(resource, inputStream);
} catch (IOException ex) {
throw new FlowableException("Failed to read resource " + resource, ex);
}
}
@Override
public AppDeploymentBuilder addString(String resourceName, String text) {
if (text == null) {
throw new FlowableException("text is null");
}
AppResourceEntity resource = resourceEntityManager.create();
resource.setName(resourceName);
resource.setBytes(text.getBytes(StandardCharsets.UTF_8));
deployment.addResource(resource);
return this;
}
@Override
public AppDeploymentBuilder addBytes(String resourceName, byte[] bytes) {View on GitHub (pinned to d6d39ce1c6)
Solutions
- Inspect the cause chain of the FlowableException to find the underlying IOException source.
- Rebuild/re-download the artifact — a corrupted jar is the most common root cause.
- Extract the resource to the filesystem at startup and deploy from a FileInputStream instead of reading it through the classloader.
- Check for a security manager or custom classloader interfering with resource reads.
Example fix
// before
deploymentBuilder.addClasspathResource("apps/myApp.bar"); // IOException from corrupted jar
// after
byte[] data = Files.readAllBytes(Paths.get("conf/apps/myApp.bar")); // read from filesystem
deploymentBuilder.addInputStream("myApp.bar", new ByteArrayInputStream(data)); Defensive patterns
Strategy: try-catch
Validate before calling
try (InputStream test = getClass().getClassLoader().getResourceAsStream(resource)) { if (test == null || test.read() == -1) { throw new IllegalStateException("Resource unreadable or empty: " + resource); } } Try / catch
try { deploymentBuilder.addClasspathResource(resource); } catch (FlowableException e) { log.error("Reading resource {} failed: {}", resource, e.getCause(), e); } Prevention
- Inspect e.getCause() for the underlying IOException; corrupted jars are the usual culprit.
- Verify jar integrity (checksums) in CI to catch corrupted dependencies early.
- For problematic packaged resources, extract them to disk at startup and deploy via FileInputStream.
When it happens
Trigger: The try-with-resources block in addClasspathResource fails with IOException — typically when closing a stream backed by a jar/zip entry that is corrupted, or when a custom classloader throws while reading the resource.
Common situations: Corrupted jars in the classpath; resources inside nested jars handled by custom classloaders; JVM-level I/O problems (disk errors, security managers blocking reads); fat-jar packaging issues where entries cannot be reopened.
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
- could not get byte array from resource '${resourceName}'
- resource '${resource}' not found
- resource '${resource}' not found
- Failed to read resource
- resource '${resource}' not found
AI-assisted analysis of flowable/flowable-engine@d6d39ce1c6 (2026-09-11).
Data as JSON: /api/errors/7a5d19b23702d3bc.
Report an issue: GitHub.