docs: @Override
      protected void init() throws Exception {
          final boolean trace = TraceComponent.isAnyTracingEnabled();
  
          try {
              PropertyService vProps = new PropertyService();
              NavigableMap<String, Object> wProps = parseConfiguration(properties, vProps);
  
              // Clone properties so that we can later detect modifications from the current values
              vProps = (PropertyService) vProps.clone();
  
              String jndiName = (String) wProps.remove(JNDI_NAME);
              String type = (String) wProps.remove(DSConfig.TYPE);
  
              // Trace some of the most important config settings
              if (trace && tc.isDebugEnabled())
                  Tr.debug(this, tc, DATASOURCE, id, jndiName, type);
  
              // Get the connection manager service for this data source. If none is configured, then use defaults.
              conMgrSvc = (ConnectionManagerService) priv.locateService(componentContext,CONNECTION_MANAGER);
  
              boolean createdDefaultConnectionManager = false;
              
              if (conMgrSvc == null) {
                  if (wProps.containsKey(DSConfig.CONNECTION_MANAGER_REF)) {
                      SQLNonTransientException failure = connectorSvc.ignoreWarnOrFail(tc, null, SQLNonTransientException.class, "MISSING_RESOURCE_J2CA8030",
                                                                                      DSConfig.CONNECTION_MANAGER_REF, "", DATASOURCE, jndiName == null ? id : jndiName);
                      if (failure != null)
                          throw failure;
                  }
                  conMgrSvc = ConnectionManagerService.createDefaultService(id);
                  createdDefaultConnectionManager = true;
  
              }
              conMgrSvc.addObserver(this);
  
              // Obtain the data source from the JDBC driver
              // TODO: Switch to org.osgi.service.jdbc.DataSourceFactory for compatibility with OSGI JDBC drivers
              jdbcDriverSvc = (JDBCDriverService) priv.locateService(componentContext,JDBC_DRIVER);
  
              if (jdbcDriverSvc == null) {
                  Tr.error(tc, "DSRA4003.driver.null", jndiName == null ? id : jndiName);
  
                  throw new SQLNonTransientException(ConnectorService.getMessage("MISSING_RESOURCE_J2CA8030", DSConfig.JDBC_DRIVER_REF,
                                                                                 "", DATASOURCE, jndiName == null ? id : jndiName));
              }
              jdbcDriverSvc.addObserver(this);
  
              Object vendorImpl;
              Class<?> ifc;
  
              if(type == null){
                  boolean atLeastJDBC43 = jdbcRuntime.getVersion().compareTo(JDBCRuntimeVersion.VERSION_4_3) >= 0;
                  vendorImpl = atLeastJDBC43 || id != null && id.contains("dataSource[DefaultDataSource]")
                                  ? jdbcDriverSvc.createAnyPreferXADataSource(vProps, id)
                                  : jdbcDriverSvc.createAnyPreferLegacyOrder(vProps, id);
                  ifc = vendorImpl instanceof XADataSource ? XADataSource.class
                      : vendorImpl instanceof ConnectionPoolDataSource ? ConnectionPoolDataSource.class
                      : vendorImpl instanceof DataSource ? DataSource.class
                      : Driver.class;
              } else if (ConnectionPoolDataSource.class.getName().equals(type)) {
                  ifc = ConnectionPoolDataSource.class;
                  vendorImpl = jdbcDriverSvc.createConnectionPoolDataSource(vProps, id);
              } else if (XADataSource.class.getName().equals(type)) {
                  ifc = XADataSource.class;
                  vendorImpl = jdbcDriverSvc.createXADataSource(vProps, id);
              } else if (DataSource.class.getName().equals(type)) {
                  ifc = DataSource.class;
                  vendorImpl = jdbcDriverSvc.createDataSource(vProps, id);
              } else if (Driver.class.getName().equals(type)) {
                  ifc = Driver.class;
                  String url = vProps.getProperty("URL", vProps.getProperty("url"));
                  if (url != null && !"".equals(url)) {
                      vendorImpl = jdbcDriverSvc.getDriver(url, vProps, id);
                  } else 
                      throw new SQLNonTransientException(AdapterUtil.getNLSMessage("DSRA4014.URL.for.Driver.missing", jndiName == null ? id : jndiName));
              } else
                  throw new SQLNonTransientException(ConnectorService.getMessage("MISSING_RESOURCE_J2CA8030", DSConfig.TYPE, type, DATASOURCE, jndiName == null ? id : jndiName));
  
              // Convert isolationLevel constant name to integer
              vendorImplClassName = vendorImpl.getClass().getName();
              parseIsolationLevel(wProps, vendorImplClassName);
              
              Object objIsolationLevel = wProps.get(DataSourceDef.isolationLevel.name());
              int wIsolationLevel = objIsolationLevel == null ? -1 : (int) objIsolationLevel;
              
              if(wIsolationLevel == Connection.TRANSACTION_NONE) {
                  Object objTransactional = wProps.get(DataSourceDef.transactional.name());
                  boolean wTransactional = objTransactional == null ? true : (boolean) objTransactional;
                  
                  if (wTransactional) {
                      throw new SQLException(AdapterUtil.getNLSMessage("DSRA4009.tran.none.transactional.unsupported", id));
                  }
              }
  
              // Derby Embedded needs a reference count so that we can shutdown databases when no longer used.
              isDerbyEmbedded = vendorImplClassName.startsWith("org.apache.derby.jdbc.Embedded");
              if (isDerbyEmbedded) {
                  String dbName = (String) vProps.get(DataSourceDef.databaseName.name());
                  if (dbName != null) {
                      // Maintaining compatibility here. Variables are no longer normalized by default, but the ResourceFactoryBuilder is still
                      // using VariableRegistry.resolveString() to resolve variables in data source definitions. 
                      dbName = PathUtils.normalize(dbName);
                      embDerbyRefCount.add(dbName);
                      if (TraceComponent.isAnyTracingEnabled() && tc.isDebugEnabled())
                          Tr.debug(this, tc, "ref count for database shutdown", dbName, embDerbyRefCount);
                  }
              }
  
              isUCP = vendorImplClassName.startsWith("oracle.ucp");
              if (isUCP) {
                  if (!createdDefaultConnectionManager && !sentUCPConnMgrPropsIgnoredInfoMessage) {
                      Set<String> connMgrPropsAllowed = Collections.singleton("enableSharingForDirectLookups");
                      Tr.info(tc, "DSRA4013.ignored.connection.manager.config.used", connMgrPropsAllowed);
                      sentUCPConnMgrPropsIgnoredInfoMessage = true;
                  }
                  updateConfigForUCP(wProps);
              }
  
              dsConfigRef.set(new DSConfig(id, jndiName, wProps, vProps, connectorSvc));
  
              WSManagedConnectionFactoryImpl mcfImpl = new WSManagedConnectionFactoryImpl(dsConfigRef, ifc, vendorImpl, jdbcRuntime);
  
              if (jdbcDriverSvc.loadFromApp()) {
                  // data source class loaded from thread context class loader
                  mcf = null;
                  mcfPerClassLoader = new ConcurrentHashMap<String, WSManagedConnectionFactoryImpl>();
                  ClassLoader tccl = priv.getContextClassLoader();
                  String identifier = connectorSvc.getClassLoaderIdentifierService().getClassLoaderIdentifier(tccl);
                  mcfPerClassLoader.put(identifier, mcfImpl);
              } else {
                  // data source class loaded from shared library
                  mcf = mcfImpl;
                  mcfPerClassLoader = null;
              }
  
              isInitialized.set(true);
          } catch (Exception x) {
              FFDCFilter.processException(x, getClass().getName(), "587", this);
              // undo any partial initialization
              if (conMgrSvc != null)
                  conMgrSvc.deleteObserver(this);
              if (jdbcDriverSvc != null)
                  jdbcDriverSvc.deleteObserver(this);
              throw x;
          } catch (Error x) {
              FFDCFilter.processException(x, getClass().getName(), "591", this);
              // undo any partial initialization
              if (conMgrSvc != null)
                  conMgrSvc.deleteObserver(this);
              if (jdbcDriverSvc != null)
                  jdbcDriverSvc.deleteObserver(this);
              throw x;
          }
      }