{"record":{"id":"ce7c3fff89c2ddb6","repo":"pentaho/pentaho-kettle","slug":"the-plugin-id-attribute-could-not-be-determined-using-driver","errorCode":null,"errorMessage":"The 'plugin_id' attribute could not be determined using 'driver_class' value '${driverClassName}'","messagePattern":"The 'plugin_id' attribute could not be determined using 'driver_class' value '(.+?)'","errorType":"exception","errorClass":"KettlePluginException","httpStatus":null,"severity":"error","filePath":"core/src/main/java/org/pentaho/di/metastore/DatabaseMetaStoreUtil.java","lineNumber":207,"sourceCode":"    //\n    String pluginId = getChildString( element, MetaStoreConst.DB_ATTR_ID_PLUGIN_ID );\n    String driverClassName = getChildString( element, MetaStoreConst.DB_ATTR_DRIVER_CLASS );\n    if ( Utils.isEmpty( pluginId ) && Utils.isEmpty( driverClassName ) ) {\n      throw new KettlePluginException( \"The attributes 'plugin_id' and 'driver_class' can't be both empty\" );\n    }\n    if ( Utils.isEmpty( pluginId ) ) {\n      // Determine pluginId using the plugin registry.\n      //\n      List<PluginInterface> plugins = pluginRegistry.getPlugins( DatabasePluginType.class );\n      for ( PluginInterface plugin : plugins ) {\n        DatabaseInterface databaseInterface = (DatabaseInterface) pluginRegistry.loadClass( plugin );\n        if ( driverClassName.equalsIgnoreCase( databaseInterface.getDriverClass() ) ) {\n          pluginId = plugin.getIds()[0];\n        }\n      }\n    }\n    if ( Utils.isEmpty( pluginId ) ) {\n      throw new KettlePluginException(\n        \"The 'plugin_id' attribute could not be determined using 'driver_class' value '\" + driverClassName + \"'\" );\n    }\n\n    // Look for the plugin\n    //\n    PluginInterface plugin = PluginRegistry.getInstance().getPlugin( DatabasePluginType.class, pluginId );\n    DatabaseInterface databaseInterface = (DatabaseInterface) PluginRegistry.getInstance().loadClass( plugin );\n    databaseInterface.setPluginId( pluginId );\n    databaseMeta.setDatabaseInterface( databaseInterface );\n\n    databaseMeta.setObjectId( new StringObjectId( element.getId() ) );\n    databaseMeta.setName( element.getName() );\n    databaseMeta.setDescription( getChildString( element, MetaStoreConst.DB_ATTR_ID_DESCRIPTION ) );\n\n    String accessTypeString = getChildString( element, MetaStoreConst.DB_ATTR_ID_ACCESS_TYPE );\n    if ( Utils.isEmpty( accessTypeString ) ) {\n      accessTypeString = DatabaseMeta.getAccessTypeDesc( DatabaseMeta.TYPE_ACCESS_NATIVE );\n    }","sourceCodeStart":189,"sourceCodeEnd":225,"githubUrl":"https://github.com/pentaho/pentaho-kettle/blob/f3058517a153da500bf4551f46d79b91bf8ec552/core/src/main/java/org/pentaho/di/metastore/DatabaseMetaStoreUtil.java#L189-L225","documentation":"If plugin_id is empty, the loader tries to infer it by matching the stored driver_class against every registered database plugin's getDriverClass(). When no plugin matches, pluginId remains empty and this KettlePluginException is thrown naming the driver class that could not be mapped.","triggerScenarios":"Loading an element whose driver_class attribute does not equal any registered database plugin's driver class (pluginId still empty after the registry loop).","commonSituations":"Driver string from a different vendor/version (e.g. old 'com.mysql.jdbc.Driver' vs new 'com.mysql.cj.jdbc.Driver'); third-party JDBC driver with no corresponding Kettle database plugin; typo in the stored driver class.","solutions":["Correct the driver_class attribute to the exact class name of a registered database plugin","Set plugin_id directly so no inference is needed","Install/register a database plugin that supports that driver class"],"exampleFix":"// before\n<attr id=\"DRIVER_CLASS\">com.mysql.jdbc.Driver</attr> // no plugin matches\n// after\n<attr id=\"DRIVER_CLASS\">com.mysql.cj.jdbc.Driver</attr>\n<attr id=\"PLUGIN_ID\">MySQL</attr>","handlingStrategy":"validation","validationCode":"PluginRegistry registry = PluginRegistry.getInstance();\nboolean matched = registry.getPlugins( DatabasePluginType.class ).stream()\n  .anyMatch( p -> driverClassName.equalsIgnoreCase(\n    registry.getDatabase( p ).getDriverClass() ) );\nif ( !matched && pluginId.isEmpty() ) throw new IllegalStateException( \"No plugin for driver \" + driverClassName );","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Store plugin_id explicitly rather than relying on driver_class inference","Keep driver class names in sync with driver version upgrades","Register third-party database plugins for custom drivers"],"tags":["metastore","plugin","driver-class"],"backgroundTag":"missing-dependency","analyzedSha":"f3058517a153da500bf4551f46d79b91bf8ec552","analyzedAt":"2026-09-13T14:04:16.340Z","contentChangedAt":"2026-09-13T14:04:16.340Z","schemaVersion":2},"datasetVersion":"2026-09-20T23:17:15.980Z"}