From a5e6c8d1e270d6212686a6876b684c95d9f97d4a Mon Sep 17 00:00:00 2001 From: Jason Froehlich Date: Fri, 20 Dec 2024 12:25:24 -0500 Subject: [PATCH 1/4] Create rules for migration to Hibernate 5.6 #166 Signed-off-by: Jason Froehlich --- .../example/HibernateClobTestApplication.java | 66 +++++++++++++++++++ .../com/example/config/HibernateConfig.java | 54 +++++++++++++++ .../main/resources/META-INF/persistence.xml | 10 +++ .../src/main/resources/application.properties | 3 + .../src/main/resources/hibernate.cfg.xml | 13 ++++ .../src/main/resources/hibernate.properties | 1 + ...framework-5.x-to-6.0-data-access.test.yaml | 14 ++++ 7 files changed, 161 insertions(+) create mode 100644 default/generated/spring-framework/tests/data/data-access/src/main/java/com/example/HibernateClobTestApplication.java create mode 100644 default/generated/spring-framework/tests/data/data-access/src/main/java/com/example/config/HibernateConfig.java create mode 100644 default/generated/spring-framework/tests/data/data-access/src/main/resources/META-INF/persistence.xml create mode 100644 default/generated/spring-framework/tests/data/data-access/src/main/resources/application.properties create mode 100644 default/generated/spring-framework/tests/data/data-access/src/main/resources/hibernate.cfg.xml create mode 100644 default/generated/spring-framework/tests/data/data-access/src/main/resources/hibernate.properties diff --git a/default/generated/spring-framework/tests/data/data-access/src/main/java/com/example/HibernateClobTestApplication.java b/default/generated/spring-framework/tests/data/data-access/src/main/java/com/example/HibernateClobTestApplication.java new file mode 100644 index 0000000..902f91c --- /dev/null +++ b/default/generated/spring-framework/tests/data/data-access/src/main/java/com/example/HibernateClobTestApplication.java @@ -0,0 +1,66 @@ +package com.example.hibernateclobtest; + +import org.hibernate.annotations.DialectOverride; +import org.hibernate.dialect.PostgreSQL81Dialect; +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.data.jpa.repository.JpaRepository; +import org.springframework.stereotype.Repository; + +import javax.persistence.*; +import java.sql.Clob; + +@SpringBootApplication +public class HibernateClobTestApplication { + + public static void main(String[] args) { + SpringApplication.run(HibernateClobTestApplication.class, args); + } +} + +@Entity +@DialectOverride.Overrides({ + @DialectOverride(dialect = PostgreSQL81Dialect.class, overrides = { + @DialectOverride.Override(sqlType = "TEXT", type = String.class) + }) +}) +class MyEntity { + @Id + @GeneratedValue(strategy = GenerationType.IDENTITY) + private Long id; + + @Lob + private String largeText; + + private Clob clobData; + + + public Long getId() { + return id; + } + + public void setId(Long id) { + this.id = id; + } + + public String getLargeText() { + return largeText; + } + + public void setLargeText(String largeText) { + this.largeText = largeText; + } + + public Clob getClobData() { + return clobData; + } + + public void setClobData(Clob clobData) { + this.clobData = clobData; + } +} + +@Repository +interface MyEntityRepository extends JpaRepository { + +} \ No newline at end of file diff --git a/default/generated/spring-framework/tests/data/data-access/src/main/java/com/example/config/HibernateConfig.java b/default/generated/spring-framework/tests/data/data-access/src/main/java/com/example/config/HibernateConfig.java new file mode 100644 index 0000000..6cb575e --- /dev/null +++ b/default/generated/spring-framework/tests/data/data-access/src/main/java/com/example/config/HibernateConfig.java @@ -0,0 +1,54 @@ +package com.example.config; + +import org.apache.commons.dbcp2.BasicDataSource; // Or your preferred DataSource +import org.hibernate.SessionFactory; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.orm.hibernate5.HibernateTransactionManager; +import org.springframework.orm.hibernate5.LocalSessionFactoryBean; +import org.springframework.transaction.PlatformTransactionManager; +import org.springframework.transaction.annotation.EnableTransactionManagement; +import org.hibernate.bytecode.javassist.FieldHandled; + +import javax.sql.DataSource; +import java.util.Properties; + +@Configuration +@EnableTransactionManagement // Enable Spring's transaction management +public class HibernateConfig { + + @Bean + public LocalSessionFactoryBean sessionFactory() { + LocalSessionFactoryBean sessionFactoryBean = new LocalSessionFactoryBean(); + sessionFactoryBean.setDataSource(dataSource()); // Set the DataSource + sessionFactoryBean.setPackagesToScan("com.example.entity"); // Package containing your entities + + Properties properties = new Properties(); + properties.setProperty("hibernate.dialect", "org.hibernate.dialect.H2Dialect"); // Database dialect + properties.setProperty("hibernate.bytecode.provider", "javassist"); // Javassist Bytecode provider (For Testing) + properties.setProperty("hibernate.show_sql", "true"); // Show SQL queries in the console (for debugging) + properties.setProperty("hibernate.format_sql", "true"); // Format SQL queries for better readability + //Add other hibernate properties as needed + + sessionFactoryBean.setHibernateProperties(properties); + + return sessionFactoryBean; + } + + @Bean + public DataSource dataSource() { + BasicDataSource dataSource = new BasicDataSource(); + dataSource.setDriverClassName("org.h2.Driver"); + dataSource.setUrl("jdbc:h2:mem:testdb"); // In-memory H2 database + dataSource.setUsername("sa"); + dataSource.setPassword(""); + return dataSource; + } + + @Bean + public PlatformTransactionManager hibernateTransactionManager() { + HibernateTransactionManager transactionManager = new HibernateTransactionManager(); + transactionManager.setSessionFactory(sessionFactory().getObject()); + return transactionManager; + } +} \ No newline at end of file diff --git a/default/generated/spring-framework/tests/data/data-access/src/main/resources/META-INF/persistence.xml b/default/generated/spring-framework/tests/data/data-access/src/main/resources/META-INF/persistence.xml new file mode 100644 index 0000000..df8e423 --- /dev/null +++ b/default/generated/spring-framework/tests/data/data-access/src/main/resources/META-INF/persistence.xml @@ -0,0 +1,10 @@ + + + + + + + \ No newline at end of file diff --git a/default/generated/spring-framework/tests/data/data-access/src/main/resources/application.properties b/default/generated/spring-framework/tests/data/data-access/src/main/resources/application.properties new file mode 100644 index 0000000..3a1f4a6 --- /dev/null +++ b/default/generated/spring-framework/tests/data/data-access/src/main/resources/application.properties @@ -0,0 +1,3 @@ +spring.jpa.database-platform=org.hibernate.dialect.PostgreSQL81Dialect +spring.datasource.url=jdbc:postgresql://localhost:5432/your_database +spring.datasource.driver-class-name=org.postgresql.Driver \ No newline at end of file diff --git a/default/generated/spring-framework/tests/data/data-access/src/main/resources/hibernate.cfg.xml b/default/generated/spring-framework/tests/data/data-access/src/main/resources/hibernate.cfg.xml new file mode 100644 index 0000000..2c611fb --- /dev/null +++ b/default/generated/spring-framework/tests/data/data-access/src/main/resources/hibernate.cfg.xml @@ -0,0 +1,13 @@ + + + + + org.hibernate.cache.EHCacheProvider + org.hibernate.dialect.MySQL5InnoDBDialect + 10 + false + javassist + + \ No newline at end of file diff --git a/default/generated/spring-framework/tests/data/data-access/src/main/resources/hibernate.properties b/default/generated/spring-framework/tests/data/data-access/src/main/resources/hibernate.properties new file mode 100644 index 0000000..2409641 --- /dev/null +++ b/default/generated/spring-framework/tests/data/data-access/src/main/resources/hibernate.properties @@ -0,0 +1 @@ +hibernate.bytecode.provider=javassist \ No newline at end of file diff --git a/default/generated/spring-framework/tests/spring-framework-5.x-to-6.0-data-access.test.yaml b/default/generated/spring-framework/tests/spring-framework-5.x-to-6.0-data-access.test.yaml index 998032a..7fe8a0e 100644 --- a/default/generated/spring-framework/tests/spring-framework-5.x-to-6.0-data-access.test.yaml +++ b/default/generated/spring-framework/tests/spring-framework-5.x-to-6.0-data-access.test.yaml @@ -10,6 +10,20 @@ tests: mode: "source-only" hasIncidents: exactly: 1 +- ruleID: spring-framework-5.x-to-6.0-data-access-00002 + testCases: + - name: tc-1 + analysisParams: + mode: "source-only" + hasIncidents: + exactly: 5 +- ruleID: spring-framework-5.x-to-6.0-data-access-00003 + testCases: + - name: tc-1 + analysisParams: + mode: "source-only" + hasIncidents: + exactly: 4 - ruleID: spring-framework-5.x-to-6.0-data-access-00010 testCases: - name: tc-1 From b04e714eb4bb62a75c6edf0244388762af24eda8 Mon Sep 17 00:00:00 2001 From: Jason Froehlich Date: Fri, 20 Dec 2024 12:27:11 -0500 Subject: [PATCH 2/4] Create rules for migration to Hibernate 5.6 #166 Signed-off-by: Jason Froehlich --- ...ring-framework-5.x-to-6.0-data-access.yaml | 65 +++++++++++++++++++ 1 file changed, 65 insertions(+) diff --git a/default/generated/spring-framework/spring-framework-5.x-to-6.0-data-access.yaml b/default/generated/spring-framework/spring-framework-5.x-to-6.0-data-access.yaml index f852f9c..17ce0ee 100644 --- a/default/generated/spring-framework/spring-framework-5.x-to-6.0-data-access.yaml +++ b/default/generated/spring-framework/spring-framework-5.x-to-6.0-data-access.yaml @@ -29,6 +29,71 @@ - title: 'Spring 6.0 migration guide' url: https://github.com/spring-projects/spring-framework/wiki/Spring-Framework-6.0-Release-Notes#removed-apis +- ruleID: spring-framework-5.x-to-6.0-data-access-00002 + category: mandatory + effort: 1 + labels: + - konveyor.io/source=spring5 + - konveyor.io/target=spring6+ + - konveyor.io/target=hibernate6+ + when: + or: + - builtin.filecontent: + filePattern: (hibernate\.properties|persistence\.xml|cfg\.xml|application\.properties|application\.yaml) + pattern: hibernate.bytecode.provider=javassist + - as: hibernate_cfg + builtin.xml: + namespaces: + s: http://www.hibernate.org/xsd/hibernate-configuration + xpath: "/hibernate-configuration/session-factory/property[@name='hibernate.bytecode.provider' and text()='javassist']" + - as: persistence_files + builtin.xml: + namespaces: + s: http://java.sun.com/xml/ns/persistence + xpath: /persistence/persistence-unit/properties/property[@name='hibernate.bytecode.provider' and @value='javassist'] + - java.referenced: + pattern: org.hibernate.bytecode.javassist* + - builtin.filecontent: + filePattern: .*\.java + pattern: setProperty\(\"hibernate.bytecode.provider\", \"javassist\"\) + description: Javassist no longer supported + message: | + Explicit configuration of `hibernate.bytecode.provider=javassist` has been detected. Javassist is no longer supported by Hibernate 5.6 and later. + + The simplest and recommended solution is to remove this property entirely. Hibernate will automatically use Byte Buddy, which is the current default. + links: + - title: 'Hibernate 5.6 migration guide - Javassist removed' + url: https://github.com/hibernate/hibernate-orm/blob/5.6/migration-guide.adoc#javassist-removed + +- ruleID: spring-framework-5.x-to-6.0-data-access-00003 + category: potential + effort: 5 + labels: + - konveyor.io/source=spring5 + - konveyor.io/target=spring6+ + - konveyor.io/target=hibernate6+ + when: + and: + - or: # Check for Hibernate annotations or clob fields + - java.referenced: + location: ANNOTATION + pattern: javax.persistence.Lob + - java.referenced: + location: FIELD + pattern: java.sql.Clob + - as: config_files # Check for PostgreSQL 8.1 dialect + builtin.filecontent: + filePattern: .*\.(java|properties|xml) + pattern: org.hibernate.dialect.PostgreSQL81Dialect + description: Changes to the DDL type for CLOB + message: | + Using `@Lob` or `java.sql.Clob` with PostgreSQL 8.1 dialect might require DDL type changes for CLOBs. + + Consider reviewing DDL generation for CLOB columns and potential migration to 'oid' type if necessary. + links: + - title: 'Hibernate 5.6 migration guide - Changes to the DDL type for CLOB' + url: https://github.com/hibernate/hibernate-orm/blob/5.6/migration-guide.adoc#changes-to-the-ddl-type-for-clob-in-postgresql81dialect-and-its-subclasses + - ruleID: spring-framework-5.x-to-6.0-data-access-00010 category: mandatory effort: 3 From 5e52ba7fe319e4a00a4ff5dda9e7c4b719666718 Mon Sep 17 00:00:00 2001 From: Jason Froehlich Date: Mon, 13 Jan 2025 14:06:16 -0500 Subject: [PATCH 3/4] #166 updated based on PR comments (removed as, added java.dependency, and more detail in the message) Signed-off-by: Jason Froehlich --- ...ring-framework-5.x-to-6.0-data-access.yaml | 20 +++++++++++-------- 1 file changed, 12 insertions(+), 8 deletions(-) diff --git a/default/generated/spring-framework/spring-framework-5.x-to-6.0-data-access.yaml b/default/generated/spring-framework/spring-framework-5.x-to-6.0-data-access.yaml index 17ce0ee..26e5ecb 100644 --- a/default/generated/spring-framework/spring-framework-5.x-to-6.0-data-access.yaml +++ b/default/generated/spring-framework/spring-framework-5.x-to-6.0-data-access.yaml @@ -41,13 +41,11 @@ - builtin.filecontent: filePattern: (hibernate\.properties|persistence\.xml|cfg\.xml|application\.properties|application\.yaml) pattern: hibernate.bytecode.provider=javassist - - as: hibernate_cfg - builtin.xml: + - builtin.xml: namespaces: s: http://www.hibernate.org/xsd/hibernate-configuration xpath: "/hibernate-configuration/session-factory/property[@name='hibernate.bytecode.provider' and text()='javassist']" - - as: persistence_files - builtin.xml: + - builtin.xml: namespaces: s: http://java.sun.com/xml/ns/persistence xpath: /persistence/persistence-unit/properties/property[@name='hibernate.bytecode.provider' and @value='javassist'] @@ -81,15 +79,21 @@ - java.referenced: location: FIELD pattern: java.sql.Clob - - as: config_files # Check for PostgreSQL 8.1 dialect - builtin.filecontent: - filePattern: .*\.(java|properties|xml) - pattern: org.hibernate.dialect.PostgreSQL81Dialect + - or: + - builtin.filecontent: + filePattern: .*\.(java|properties|xml) + pattern: org.hibernate.dialect.PostgreSQL81Dialect + - java.dependency: + name: postgresql description: Changes to the DDL type for CLOB message: | Using `@Lob` or `java.sql.Clob` with PostgreSQL 8.1 dialect might require DDL type changes for CLOBs. Consider reviewing DDL generation for CLOB columns and potential migration to 'oid' type if necessary. + + All PostgreSQL JDBC drivers unfortunately just store the oid it created for a `java.sql.Clob` into the text column. Although reading back the value with the CLOB API works, PostgreSQL has no knowledge of the reference to the LOB, because the oid is not known to PostgreSQL, leading to data loss when vacuumlo (the utility to clean up unused LOBs) runs. To avoid the data loss, it is required to use the oid type so that vacuumlo can see the reference. + + Updating to 5.6.2 does not require any schema or application changes by default, but we highly recommend that you migrate existing text columns for LOBs to oid to prevent data loss due to the activity of vacuumlo. links: - title: 'Hibernate 5.6 migration guide - Changes to the DDL type for CLOB' url: https://github.com/hibernate/hibernate-orm/blob/5.6/migration-guide.adoc#changes-to-the-ddl-type-for-clob-in-postgresql81dialect-and-its-subclasses From 816c7e595838356aeb80b9730ae72edb6519f05e Mon Sep 17 00:00:00 2001 From: Jason Froehlich Date: Wed, 15 Jan 2025 13:00:09 -0500 Subject: [PATCH 4/4] #166 Added changes to make rules more robust Signed-off-by: Jason Froehlich --- ...spring-framework-5.x-to-6.0-data-access.yaml | 17 +++++++++-------- .../tests/data/data-access/pom.xml | 6 ++++++ .../src/main/resources/META-INF/persistence.xml | 10 ---------- ...g-framework-5.x-to-6.0-data-access.test.yaml | 4 ++-- 4 files changed, 17 insertions(+), 20 deletions(-) delete mode 100644 default/generated/spring-framework/tests/data/data-access/src/main/resources/META-INF/persistence.xml diff --git a/default/generated/spring-framework/spring-framework-5.x-to-6.0-data-access.yaml b/default/generated/spring-framework/spring-framework-5.x-to-6.0-data-access.yaml index 26e5ecb..c7f8a78 100644 --- a/default/generated/spring-framework/spring-framework-5.x-to-6.0-data-access.yaml +++ b/default/generated/spring-framework/spring-framework-5.x-to-6.0-data-access.yaml @@ -39,16 +39,12 @@ when: or: - builtin.filecontent: - filePattern: (hibernate\.properties|persistence\.xml|cfg\.xml|application\.properties|application\.yaml) + filePattern: .*\.properties pattern: hibernate.bytecode.provider=javassist - builtin.xml: namespaces: s: http://www.hibernate.org/xsd/hibernate-configuration xpath: "/hibernate-configuration/session-factory/property[@name='hibernate.bytecode.provider' and text()='javassist']" - - builtin.xml: - namespaces: - s: http://java.sun.com/xml/ns/persistence - xpath: /persistence/persistence-unit/properties/property[@name='hibernate.bytecode.provider' and @value='javassist'] - java.referenced: pattern: org.hibernate.bytecode.javassist* - builtin.filecontent: @@ -84,16 +80,21 @@ filePattern: .*\.(java|properties|xml) pattern: org.hibernate.dialect.PostgreSQL81Dialect - java.dependency: - name: postgresql + lowerbound: 0.0.0 + name: org.postgresql.postgresql description: Changes to the DDL type for CLOB message: | Using `@Lob` or `java.sql.Clob` with PostgreSQL 8.1 dialect might require DDL type changes for CLOBs. Consider reviewing DDL generation for CLOB columns and potential migration to 'oid' type if necessary. - All PostgreSQL JDBC drivers unfortunately just store the oid it created for a `java.sql.Clob` into the text column. Although reading back the value with the CLOB API works, PostgreSQL has no knowledge of the reference to the LOB, because the oid is not known to PostgreSQL, leading to data loss when vacuumlo (the utility to clean up unused LOBs) runs. To avoid the data loss, it is required to use the oid type so that vacuumlo can see the reference. + All PostgreSQL JDBC drivers unfortunately just store the oid it created for a `java.sql.Clob` into the text column. + Although reading back the value with the CLOB API works, PostgreSQL has no knowledge of the reference to the LOB, + because the oid is not known to PostgreSQL, leading to data loss when vacuumlo (the utility to clean up unused LOBs) runs. + To avoid the data loss, it is required to use the oid type so that vacuumlo can see the reference. - Updating to 5.6.2 does not require any schema or application changes by default, but we highly recommend that you migrate existing text columns for LOBs to oid to prevent data loss due to the activity of vacuumlo. + Updating to 5.6.2 does not require any schema or application changes by default, but we highly recommend that you migrate + existing text columns for LOBs to oid to prevent data loss due to the activity of vacuumlo. links: - title: 'Hibernate 5.6 migration guide - Changes to the DDL type for CLOB' url: https://github.com/hibernate/hibernate-orm/blob/5.6/migration-guide.adoc#changes-to-the-ddl-type-for-clob-in-postgresql81dialect-and-its-subclasses diff --git a/default/generated/spring-framework/tests/data/data-access/pom.xml b/default/generated/spring-framework/tests/data/data-access/pom.xml index 92531b1..3bc6642 100644 --- a/default/generated/spring-framework/tests/data/data-access/pom.xml +++ b/default/generated/spring-framework/tests/data/data-access/pom.xml @@ -70,6 +70,12 @@ 8.0.30 + + org.postgresql + postgresql + 42.5.4 + + org.slf4j diff --git a/default/generated/spring-framework/tests/data/data-access/src/main/resources/META-INF/persistence.xml b/default/generated/spring-framework/tests/data/data-access/src/main/resources/META-INF/persistence.xml deleted file mode 100644 index df8e423..0000000 --- a/default/generated/spring-framework/tests/data/data-access/src/main/resources/META-INF/persistence.xml +++ /dev/null @@ -1,10 +0,0 @@ - - - - - - - \ No newline at end of file diff --git a/default/generated/spring-framework/tests/spring-framework-5.x-to-6.0-data-access.test.yaml b/default/generated/spring-framework/tests/spring-framework-5.x-to-6.0-data-access.test.yaml index 7fe8a0e..e30fd9d 100644 --- a/default/generated/spring-framework/tests/spring-framework-5.x-to-6.0-data-access.test.yaml +++ b/default/generated/spring-framework/tests/spring-framework-5.x-to-6.0-data-access.test.yaml @@ -16,14 +16,14 @@ tests: analysisParams: mode: "source-only" hasIncidents: - exactly: 5 + exactly: 4 - ruleID: spring-framework-5.x-to-6.0-data-access-00003 testCases: - name: tc-1 analysisParams: mode: "source-only" hasIncidents: - exactly: 4 + exactly: 5 - ruleID: spring-framework-5.x-to-6.0-data-access-00010 testCases: - name: tc-1