hibernate/hibernate-orm · error · HibernateException
Unable to instantiate ScanningProvider `%s`
Error message
Unable to instantiate ScanningProvider `%s`
What it means
During bootstrap Hibernate resolves the configured ScanningProvider (setting 'hibernate.archive.scanning', see PersistenceSettings.SCANNING). The setting may be an instance, a Class, or a class-name String. Here the setting was a Class, so ScanningHelper calls implClass.getDeclaredConstructor().newInstance() reflectively; any failure (missing or inaccessible no-arg constructor, abstract class or interface, constructor that throws, or the created object not being a ScanningProvider causing a ClassCastException) is wrapped in this HibernateException.
Source
Thrown at hibernate-core/src/main/java/org/hibernate/boot/scan/internal/ScanningHelper.java:115
private static ScanningProvider determineScanningProviderFromSetting(
@Nonnull ConfigurationService configurationService,
@Nonnull ClassLoaderService classLoaderService) {
var providerSetting = configurationService.getSettings().get( PersistenceSettings.SCANNING );
if ( providerSetting == null ) {
return null;
}
// might be any of the 3 standard forms
if ( providerSetting instanceof ScanningProvider instance ) {
return instance;
}
else if ( providerSetting instanceof Class<?> implClass ) {
try {
return (ScanningProvider) implClass.getDeclaredConstructor().newInstance();
}
catch (Exception e) {
throw new HibernateException(
String.format( Locale.ROOT,
"Unable to instantiate ScanningProvider `%s`",
implClass.getName()
),
e
);
}
}
else {
var implClassName = providerSetting.toString();
var implClass = classLoaderService.classForName( implClassName );
try {
return (ScanningProvider) implClass.getDeclaredConstructor().newInstance();
}
catch (Exception e) {
throw new HibernateException(
String.format( Locale.ROOT,
"Unable to instantiate ScanningProvider `%s`",View on GitHub (pinned to fad1729dce)
Solutions
- Give the implementation a public no-arg constructor (or a declared constructor accessible to the caller) so getDeclaredConstructor().newInstance() succeeds.
- Pass an instance instead of a Class: builder.applySetting(PersistenceSettings.SCANNING, new MyScanningProvider(...)) - the 'instanceof ScanningProvider' branch returns it directly with no reflection.
- Inspect the wrapped cause (e) in the stack trace - InstantiationException means abstract/interface, NoSuchMethodException means no no-arg constructor, ClassCastException means wrong interface, InvocationTargetException means your constructor threw.
- Verify the class actually implements org.hibernate.boot.scan.spi.ScanningProvider from the same Hibernate version, and that its module exports the package when running on the module path.
Example fix
// before
builder.applySetting( PersistenceSettings.SCANNING, MyScanningProvider.class );
// MyScanningProvider(String cfg) only -> no no-arg constructor -> error
// after
public MyScanningProvider() {
this(defaultConfig());
}
// or skip reflection entirely:
builder.applySetting( PersistenceSettings.SCANNING, new MyScanningProvider(cfg) ); Defensive patterns
Strategy: validation
Validate before calling
Class<?> impl = MyScanningProvider.class;
if ( !org.hibernate.boot.scan.spi.ScanningProvider.class.isAssignableFrom( impl ) ) {
throw new IllegalStateException( impl + " is not a ScanningProvider" );
}
try { impl.getDeclaredConstructor(); } // NoSuchMethodException here = would fail in Hibernate
catch ( NoSuchMethodException e ) { throw new IllegalStateException( impl + " needs a no-arg constructor" ); } Type guard
static boolean instantiableScanningProvider(Object setting) {
if ( setting instanceof org.hibernate.boot.scan.spi.ScanningProvider ) return true; // instance form: safe
Class<?> c = setting instanceof Class<?> k ? k : null;
return c != null
&& org.hibernate.boot.scan.spi.ScanningProvider.class.isAssignableFrom( c )
&& java.lang.reflect.Modifier.isPublic( c.getModifiers() );
} Try / catch
try {
Metadata metadata = new MetadataSources( ssr ).buildMetadata();
}
catch ( HibernateException e ) {
if ( e.getMessage() != null && e.getMessage().startsWith( "Unable to instantiate ScanningProvider" ) ) {
// e.getCause(): NoSuchMethodException / InstantiationException / InvocationTargetException / ClassCastException
throw new BootstrapException( "Bad hibernate.archive.scanning setting", e.getCause() );
}
throw e;
} Prevention
- Prefer passing an instance for hibernate.archive.scanning - the instanceof branch bypasses reflection entirely.
- Keep a public no-arg constructor on every provider/scanner class you register; put required setup in static config instead of constructor args.
- Assert in unit tests that the provider class has a no-arg constructor and implements the expected SPI interface for the Hibernate version on the classpath.
When it happens
Trigger: Setting PersistenceSettings.SCANNING ('hibernate.archive.scanning') to a Class object whose declared no-arg constructor cannot be invoked: constructor is private/protected, the class is abstract or an interface, the constructor throws (e.g. looks up env/config), or the class does not implement ScanningProvider so the (ScanningProvider) cast fails inside the try block.
Common situations: Custom scanning provider that only has constructor-arg constructors; a provider whose no-arg constructor does environment lookups that fail in CI; passing a class that implements the SPI from a different Hibernate version where the interface moved; access-control failure under JPMS because the package is not exported/opened.
Related errors
- Unable to instantiate Scanner `%s`
- Unable to instantiate configured ArchiveDescriptorFactory -
- Unable to instantiate specified event listener class:
- Could not instantiate event listener '{}'
- Unable to instantiate StatementObserver - {}
AI-assisted analysis of hibernate/hibernate-orm@fad1729dce (2026-08-22).
Data as JSON: /api/errors/837d94cbd40e713b.
Report an issue: GitHub.