flowable/flowable-engine · error · FlowableClassLoadingException

Could not load class: ${className} (or 'Class not found: ${c

Error message

Could not load class: ${className} (or 'Class not found: ${className}' when cause is ClassNotFoundException)

What it means

ReflectUtil.loadClass tries the context classloader, the current class's classloader, and other fallbacks to load a class by name; if all attempts fail it throws FlowableClassLoadingException with the message 'Could not load class: X' (or 'Class not found: X' when the root cause is a ClassNotFoundException). The real cause (LinkageError, security issue, etc.) is attached.

Source

Thrown at modules/flowable-engine-common/src/main/java/org/flowable/common/engine/impl/util/ReflectUtil.java:89

            } catch (Throwable t) {
                if (throwable == null) {
                    throwable = t;
                }
            }
            if (clazz == null) {
                try {
                    LOGGER.trace("Trying to load class with local classloader: {}", className);
                    clazz = loadClass(ReflectUtil.class.getClassLoader(), className);
                } catch (Throwable t) {
                    if (throwable == null) {
                        throwable = t;
                    }
                }
            }
        }

        if (clazz == null) {
            throw new FlowableClassLoadingException(className, throwable);
        }
        return clazz;
    }

    public static boolean isClassPresent(String className) {
        try {
            loadClass(className);
            return true;
        } catch (FlowableClassLoadingException ignored) {
            return false;
        }
    }

    public static InputStream getResourceAsStream(String name) {
        InputStream resourceStream = null;
        ClassLoader classLoader = getCustomClassLoader();
        if (classLoader != null) {
            resourceStream = classLoader.getResourceAsStream(name);

View on GitHub (pinned to d6d39ce1c6)

Solutions

  1. Verify the fully-qualified class name in your configuration is spelled correctly and case-exact.
  2. Confirm the class is on the runtime classpath (check the packaged jar/war, mvn dependency:tree).
  3. Inspect the 'cause' of FlowableClassLoadingException: ClassNotFoundException means missing; NoClassDefFoundError/LinkageError means dependency version conflict.
  4. Add the missing dependency or fix its scope (compile instead of provided/test).
  5. If using OSGi or custom classloaders, ensure ReflectUtil can find the class via the thread context classloader.

Example fix

// before
<flowable:class delegateExpression="com.acme.MyDelegate"/>  <!-- wrong name -->
// after
<!-- exact FQN of a class present on the runtime classpath -->
<flowable:class delegateExpression="com.acme.order.MyJavaDelegate"/>
Defensive patterns

Strategy: try-catch

Validate before calling

if (!ReflectUtil.isClassPresent(className)) {
    throw new IllegalStateException("Class not on classpath: " + className);
}

Try / catch

try {
    Class<?> c = ReflectUtil.loadClass(className);
} catch (FlowableClassLoadingException e) {
    LOGGER.error("Cannot load {}: {}", className, e.getCause(), e);
    throw newConfigurationException(className, e.getCause());
}

Prevention

When it happens

Trigger: Calling ReflectUtil.loadClass(className) or isClassPresent-dependent code paths with a class name that is misspelled, not on the classpath, or whose static initializer/linking fails.

Common situations: Configuring custom classes (delegates, listeners, serializers) in process XML or config with wrong fully-qualified names; dependencies missing at runtime in fat jars/containers; class exists in a provided-scope dependency not packaged; Java version mismatch breaking linking.

Related errors


AI-assisted analysis of flowable/flowable-engine@d6d39ce1c6 (2026-09-11). Data as JSON: /api/errors/968a3fc65f896354. Report an issue: GitHub.