Hello,
Im using 8.3 version of IIQ.
I have created a plugin and would like to use Hibernate with JPA as the ORM tool instead of the default JDBC, as I am dealing with some levels of relationships between entities. I have successfully created the EntityManager and mapped the entities that I need to persist and manage. When testing locally with the IIQ database properties, everything works correctly. However, when I deploy the plugin and call the test() method within ScriptsTesting, I receive the following error:java.lang.IllegalArgumentException: Unknown entity:.TestingEntity
Here are the relevant parts of my code:
My manifest:
<?xml version='1.0' encoding='UTF-8' standalone="no"?>
<!DOCTYPE Plugin PUBLIC "sailpoint.dtd" "sailpoint.dtd">
<Plugin certificationLevel="None"
displayName="RolePropagationPlugin"
minSystemVersion="7.1"
name="RolePropagationPlugin"
version="1.0.35">
<Attributes>
<Map>
<entry key="minUpgradableVersion" value="1.0" />
<entry key="fullPage">
<value>
<FullPage title="Role Propagation"/>
</value>
</entry>
<entry key="scriptPackages">
<value>
<List>
<String>***.scripts</String>
<String>***.entities</String>
</List>
</value>
</entry>
<entry key="settings">
<value>
<List>
<Setting dataType="string" helpText="Driver JDBC" label="jdbcDriver" name="jdbcDriver" defaultValue="oracle.jdbc.driver.OracleDriver"/>
<Setting dataType="string" helpText="String Connection JDBC" label="connectionString" name="connectionString" defaultValue="****"/>
<Setting dataType="string" helpText="DataBase User" label="dbUser" name="dbUser" defaultValue="****"/>
<Setting dataType="string" helpText="DataBase Password" label="dbPass" name="dbPass" defaultValue="*****"/>
<Setting dataType="string" helpText="Hibernate Dialect" label="hbDialect" name="hbDialect" defaultValue="org.hibernate.dialect.Oracle12cDialect"/>
</List>
</value>
</entry>
</Map>
</Attributes>
</Plugin>
The entity:
@Entity
@Table(name = "testing")
public class TestingEntity implements Serializable{
public TestingEntity() {
}
public TestingEntity(String testKey, String testValue) {
this.testKey = testKey;
this.testValue = testValue;
}
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Column(name = "test_key")
private String testKey;
@Column(name = "test_value")
private String testValue;
public String getTestKey() {
return testKey;
}
public void setTestKey(String testKey) {
this.testKey = testKey;
}
public String getTestValue() {
return testValue;
}
public void setTestValue(String testValue) {
this.testValue = testValue;
}
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
}
My DAO:
public class TestingDAO {
private EntityManager entityManager;
public TestingDAO() throws SQLException {
this.entityManager = new EntityManagerHolder(TestingEntity.class).getEntityManager();
}
public void save(TestingEntity entity) {
entityManager.getTransaction().begin();
entityManager.persist(entity);
entityManager.getTransaction().commit();
}
}
My EntityManagerHolder:
public class EntityManagerHolder {
private EntityManager entityManager;
public EntityManagerHolder(Class<?> class1) throws SQLException {
this.entityManager = new JpaEntityManagerFactory(new Class[]{class1}).getEntityManager();
}
public EntityManager getEntityManager() {
return entityManager;
}
}
My JpaEntityManagerFactory:
public class JpaEntityManagerFactory {
private String DB_URL;
private String DB_USER_NAME;
private String DB_PASSWORD;
private Class[] entityClasses;
public JpaEntityManagerFactory(Class[] entityClasses) throws GeneralException {
this.entityClasses = entityClasses;
this.DB_URL = PluginBaseHelper.getSettingSecret(context(), "RolePropagationPlugin", "connectionString");
this.DB_USER_NAME = PluginBaseHelper.getSettingSecret(context(), "RolePropagationPlugin", "dbUser");
this.DB_PASSWORD = PluginBaseHelper.getSettingSecret(context(), "RolePropagationPlugin", "dbPass");
}
private SailPointContext context() throws GeneralException {
return SailPointFactory.getCurrentContext();
}
public EntityManager getEntityManager() throws SQLException {
return getEntityManagerFactory().createEntityManager();
}
protected EntityManagerFactory getEntityManagerFactory() throws SQLException {
PersistenceUnitInfo persistenceUnitInfo = getPersistenceUnitInfo(
getClass().getSimpleName());
persistenceUnitInfo.getManagedClassNames().stream().forEach(x->{
});
Map<String, Object> configuration = new HashMap<>();
return new EntityManagerFactoryBuilderImpl(
new PersistenceUnitInfoDescriptor(persistenceUnitInfo), configuration)
.build();
}
protected CustomPersistenceUnitInfo getPersistenceUnitInfo(String name) throws SQLException {
return new CustomPersistenceUnitInfo(name, getEntityClassNames(), getProperties());
}
protected List<String> getEntityClassNames() {
return Arrays.asList(getEntities())
.stream()
.map(Class::getName)
.collect(Collectors.toList());
}
protected Properties getProperties() throws SQLException {
Properties properties = new Properties();
properties.put("hibernate.dialect", "org.hibernate.dialect.Oracle12cDialect");
properties.put("hibernate.id.new_generator_mappings", false);
properties.put("hibernate.connection.datasource", getOracleDataSource());
properties.put("hibernate.hbm2ddl.auto", "update");
return properties;
}
protected Class[] getEntities() {
return entityClasses;
}
protected DataSource getOracleDataSource() throws SQLException {
OracleDataSource oracleDataSource = new OracleDataSource();
oracleDataSource.setURL(DB_URL);
oracleDataSource.setUser(DB_USER_NAME);
oracleDataSource.setPassword(DB_PASSWORD);
return oracleDataSource;
}
}
My CustomPersistenceUnitInfo:
public class CustomPersistenceUnitInfo implements PersistenceUnitInfo{
public static String JPA_VERSION = "2.1";
private String persistenceUnitName;
private PersistenceUnitTransactionType transactionType
= PersistenceUnitTransactionType.RESOURCE_LOCAL;
private List<String> managedClassNames;
private List<String> mappingFileNames = new ArrayList<>();
private Properties properties;
private DataSource jtaDataSource;
private DataSource nonjtaDataSource;
private List<ClassTransformer> transformers = new ArrayList<>();
public CustomPersistenceUnitInfo(
String persistenceUnitName, List<String> managedClassNames, Properties properties) {
this.persistenceUnitName = persistenceUnitName;
this.managedClassNames = managedClassNames;
this.properties = properties;
}
@Override
public String getPersistenceUnitName() {
return this.persistenceUnitName;
}
@Override
public String getPersistenceProviderClassName() {
return "org.hibernate.jpa.HibernatePersistenceProvider";
}
@Override
public PersistenceUnitTransactionType getTransactionType() {
return this.transactionType;
}
@Override
public DataSource getJtaDataSource() {
return this.jtaDataSource;
}
@Override
public DataSource getNonJtaDataSource() {
return this.nonjtaDataSource;
}
@Override
public List<String> getMappingFileNames() {
return new ArrayList<>();
}
@Override
public List<URL> getJarFileUrls() {
return new ArrayList<>(); // Return an empty list or populate with actual URLs as needed
}
@Override
public URL getPersistenceUnitRootUrl() {
return null; // Return null or an appropriate URL based on your application's requirements
}
@Override
public List<String> getManagedClassNames() {
return this.managedClassNames;
}
@Override
public boolean excludeUnlistedClasses() {
return false;
}
@Override
public SharedCacheMode getSharedCacheMode() {
return SharedCacheMode.UNSPECIFIED;
}
@Override
public ValidationMode getValidationMode() {
return ValidationMode.AUTO;
}
@Override
public Properties getProperties() {
return this.properties;
}
@Override
public String getPersistenceXMLSchemaVersion() {
return JPA_VERSION;
}
@Override
public ClassLoader getClassLoader() {
return Thread.currentThread().getContextClassLoader();
}
@Override
public void addTransformer(ClassTransformer transformer) {
this.transformers.add(transformer);
}
@Override
public ClassLoader getNewTempClassLoader() {
return new ClassLoader() {
@Override
protected Class<?> findClass(String name) throws ClassNotFoundException {
return Thread.currentThread().getContextClassLoader().loadClass(name);
}
};
}
}
My ScriptsTesting:
public class ScriptsTesting {
public ScriptsTesting() {
super();
}
public void test() throws SQLException {
TestingEntity entity = new TestingEntity();
entity.setTestKey("keyteste123");
entity.setTestValue("valueteste123");
TestingDAO dao = new TestingDAO();
dao.save(entity);
}
}
My pom.xml
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>****</groupId>
<artifactId>****</artifactId>
<version>1.0.36</version>
<properties>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
<jarName>****</jarName>
</properties>
<dependencies>
<dependency>
<artifactId>sailpoint</artifactId>
<groupId>com.sailpoint</groupId>
<version>8.3</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>javax.persistence</groupId>
<artifactId>javax.persistence-api</artifactId>
<version>2.2</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<version>5.4.32.Final</version>
<exclusions>
<exclusion>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-jcache</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>5.4.32.Final</version>
</dependency>
<dependency>
<groupId>com.oracle.database.jdbc</groupId>
<artifactId>ojdbc8</artifactId>
<version>19.8.0.0</version>
</dependency>
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjrt</artifactId>
<version>1.9.6</version>
</dependency>
</dependencies>
<build>
<finalName>${project.artifactId}.${project.version}</finalName>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-antrun-plugin</artifactId>
<version>1.8</version>
<executions>
<execution>
<phase>prepare-package</phase>
<configuration>
<tasks>
<replaceregexp file="manifest.xml" match="version="[^\"]*"" replace="version="${project.version}"" byline="true"/>
</tasks>
</configuration>
<goals>
<goal>run</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-assembly-plugin</artifactId>
<version>3.1.1</version>
<configuration>
<descriptors>
<descriptor>src/assembly/assembly.xml</descriptor>
</descriptors>
<descriptorRefs>
<descriptorRef>jar-with-dependencies</descriptorRef>
</descriptorRefs>
<appendAssemblyId>false</appendAssemblyId>
</configuration>
<executions>
<execution>
<id>make-assembly</id>
<phase>package</phase>
<goals>
<goal>single</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
<profiles>
<profile>
<id>windows</id>
<activation>
<os>
<family>Windows</family>
</os>
</activation>
<build>
<plugins>
<plugin>
<groupId>org.codehaus.mojo</groupId>
<artifactId>exec-maven-plugin</artifactId>
<version>3.0.0</version>
<executions>
<execution>
<id>increment-build-number</id>
<phase>validate</phase>
<goals>
<goal>exec</goal>
</goals>
<configuration>
<executable>cmd</executable>
<arguments>
<argument>/c</argument>
<argument>increment-build-number.bat</argument>
</arguments>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</profile>
</profiles>
</project>