diff --git a/pom.xml b/pom.xml index 0a08385c42d198d7594843b31c8f534f3967139a..5e5c18f965655f170b60b34317af1ff7fa2a0f69 100644 --- a/pom.xml +++ b/pom.xml @@ -23,6 +23,12 @@ <version>4.13.2</version> <scope>test</scope> </dependency> + <dependency> + <groupId>com.h2database</groupId> + <artifactId>h2</artifactId> + <version>1.4.200</version> + <scope>test</scope> + </dependency> <dependency> <groupId>com.oracle.database.jdbc</groupId> <artifactId>ojdbc8</artifactId> @@ -37,6 +43,7 @@ <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> <version>1.18.22</version> + <scope>compile</scope> </dependency> </dependencies> diff --git a/src/main/java/edu/hsh/dbs2/imdb/logic/GenreManager.java b/src/main/java/edu/hsh/dbs2/imdb/logic/GenreManager.java index 4408f488ded14e085a7c361e60d7db2442bada8b..1191fb21a04dd21822fc923f3c15ef66360136bb 100644 --- a/src/main/java/edu/hsh/dbs2/imdb/logic/GenreManager.java +++ b/src/main/java/edu/hsh/dbs2/imdb/logic/GenreManager.java @@ -7,7 +7,7 @@ import java.util.Collection; import java.util.List; import java.util.stream.Collectors; -public class GenreManager extends Manager { +public class GenreManager extends Manager<Genre> { GenreManager(EntityManagerFactory sessionFactory) { super(sessionFactory); @@ -19,7 +19,7 @@ public class GenreManager extends Manager { } Collection<Genre> getGenreImpl() { - return query(Genre.class, (cb, cq) -> cq.select(cq.from(Genre.class))); + return query((cb, cq) -> cq.select(cq.from(Genre.class))); } } diff --git a/src/main/java/edu/hsh/dbs2/imdb/logic/Manager.java b/src/main/java/edu/hsh/dbs2/imdb/logic/Manager.java index ceefb4096d579b247672bbb41bc42d7ca72e5d5e..87d91efc000e91634afc5ac6e806d8a55a31e2f7 100644 --- a/src/main/java/edu/hsh/dbs2/imdb/logic/Manager.java +++ b/src/main/java/edu/hsh/dbs2/imdb/logic/Manager.java @@ -6,27 +6,31 @@ import jakarta.persistence.RollbackException; import jakarta.persistence.criteria.CriteriaBuilder; import jakarta.persistence.criteria.CriteriaQuery; +import java.lang.reflect.ParameterizedType; import java.util.List; import java.util.function.BiConsumer; import java.util.function.Consumer; -public class Manager { +public class Manager<T> { private final ThreadLocal<EntityManager> localManager; + private final Class<T> type; + @SuppressWarnings("unchecked") protected Manager(EntityManagerFactory sessionFactory) { this.localManager = ThreadLocal.withInitial(sessionFactory::createEntityManager); + this.type = (Class<T>) ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0]; } - protected <T> List<T> queryNoClose(Class<T> type, BiConsumer<CriteriaBuilder, CriteriaQuery<T>> function) { + protected List<T> queryNoClose(BiConsumer<CriteriaBuilder, CriteriaQuery<T>> function) { var manager = getEntityManager(); var cb = manager.getCriteriaBuilder(); var cq = cb.createQuery(type); function.accept(cb, cq); return manager.createQuery(cq).getResultList(); } - protected <T> List<T> query(Class<T> type, BiConsumer<CriteriaBuilder, CriteriaQuery<T>> function) { - var result = queryNoClose(type, function); + protected List<T> query(BiConsumer<CriteriaBuilder, CriteriaQuery<T>> function) { + var result = queryNoClose(function); closeEntityManager(); return result; } @@ -55,7 +59,7 @@ public class Manager { } } - protected <T> T mergeIfDetached(T entity) { + protected <E> E mergeIfDetached(E entity) { var manager = getEntityManager(); if (!manager.contains(entity)) return manager.merge(entity); diff --git a/src/main/java/edu/hsh/dbs2/imdb/logic/MovieManager.java b/src/main/java/edu/hsh/dbs2/imdb/logic/MovieManager.java index 6cff03c8d44f9775f2c01eee1da21c86d56aa190..6015352f51cdc4bf49386aa2f42ef72ad097cacd 100644 --- a/src/main/java/edu/hsh/dbs2/imdb/logic/MovieManager.java +++ b/src/main/java/edu/hsh/dbs2/imdb/logic/MovieManager.java @@ -10,7 +10,7 @@ import java.util.List; import java.util.Optional; import java.util.stream.Collectors; -public class MovieManager extends Manager { +public class MovieManager extends Manager<Movie> { private final GenreManager genreManager; private final PersonManager personManager; private final MovieMapper mapper = new MovieMapper(); @@ -22,7 +22,7 @@ public class MovieManager extends Manager { } public List<MovieDTO> getMovieList(final String search) { - var movies = query(Movie.class, (cb, cq) -> { + var movies = query((cb, cq) -> { var root = cq.from(Movie.class); cq.select(root); if (search != null && search.length() > 0) @@ -73,7 +73,7 @@ public class MovieManager extends Manager { } private Optional<Movie> findMovieById(final long id) { - return queryNoClose(Movie.class, (cb, cq) -> { + return queryNoClose((cb, cq) -> { var root = cq.from(Movie.class); cq.select(root).where(cb.equal(root.get("id"), id)); }).stream().findAny(); diff --git a/src/main/java/edu/hsh/dbs2/imdb/logic/PersonManager.java b/src/main/java/edu/hsh/dbs2/imdb/logic/PersonManager.java index c4eda31dc93ffab84fe2a8b3996cb85b9c9c8476..bdb59efd8edfd3e5ec90d1dd4961dcadfc617bef 100644 --- a/src/main/java/edu/hsh/dbs2/imdb/logic/PersonManager.java +++ b/src/main/java/edu/hsh/dbs2/imdb/logic/PersonManager.java @@ -7,7 +7,7 @@ import java.util.Collection; import java.util.List; import java.util.stream.Collectors; -public class PersonManager extends Manager { +public class PersonManager extends Manager<Person> { PersonManager(EntityManagerFactory sessionFactory) { super(sessionFactory); @@ -19,7 +19,7 @@ public class PersonManager extends Manager { } Collection<Person> getPeopleImpl(final String text) { - return query(Person.class, (cb, cq) -> { + return query((cb, cq) -> { var root = cq.from(Person.class); cq.select(root); if (text != null && text.length() > 0) diff --git a/src/test/java/edu/hsh/dbs2/imdb/TestDB.java b/src/test/java/edu/hsh/dbs2/imdb/TestDB.java index a2973159e5615f25082708901cd68000874b85a8..b96fa615c10f984731b792152301e510adc8cc39 100644 --- a/src/test/java/edu/hsh/dbs2/imdb/TestDB.java +++ b/src/test/java/edu/hsh/dbs2/imdb/TestDB.java @@ -7,7 +7,6 @@ import edu.hsh.dbs2.imdb.logic.ManagerFactory; import edu.hsh.dbs2.imdb.logic.MovieManager; import edu.hsh.dbs2.imdb.logic.dto.CharacterDTO; import edu.hsh.dbs2.imdb.logic.dto.MovieDTO; -import edu.hsh.dbs2.imdb.util.Util; import jakarta.persistence.EntityManagerFactory; import jakarta.persistence.Persistence; import jakarta.persistence.PersistenceException; @@ -24,7 +23,7 @@ public class TestDB { @BeforeClass public static void setUp() { - sessionFactory = Persistence.createEntityManagerFactory("edu.hsh.dbs2.imdb", Util.getTestDataProperty()); + sessionFactory = Persistence.createEntityManagerFactory("edu.hsh.dbs2.imdb"); ManagerFactory.instance.setSessionFactory(sessionFactory); movieManager = ManagerFactory.instance.getMovieManager(); } diff --git a/src/test/resources/META-INF/persistence.xml b/src/test/resources/META-INF/persistence.xml new file mode 100644 index 0000000000000000000000000000000000000000..fedb5f8f69d493b42709107c96d8cdbd6b769d35 --- /dev/null +++ b/src/test/resources/META-INF/persistence.xml @@ -0,0 +1,26 @@ +<?xml version="1.0" encoding="UTF-8" standalone="yes"?> +<persistence xmlns="https://jakarta.ee/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="3.0" + xsi:schemaLocation="https://jakarta.ee/xml/ns/persistence https://jakarta.ee/xml/ns/persistence/persistence_3_0.xsd"> + <persistence-unit name="edu.hsh.dbs2.imdb" transaction-type="RESOURCE_LOCAL"> + <provider>org.hibernate.jpa.HibernatePersistenceProvider</provider> + <class>edu.hsh.dbs2.imdb.entity.Movie</class> + <class>edu.hsh.dbs2.imdb.entity.Genre</class> + <class>edu.hsh.dbs2.imdb.entity.Person</class> + <class>edu.hsh.dbs2.imdb.entity.MovieCharacter</class> + <properties> + <property name="jakarta.persistence.jdbc.driver" value="org.h2.Driver"/> + <property name="jakarta.persistence.jdbc.url" value="jdbc:h2:mem:myDb;DB_CLOSE_DELAY=-1"/> + <property name="jakarta.persistence.jdbc.user" value="sa"/> + <property name="jakarta.persistence.jdbc.password" value=""/> + <property name="jakarta.persistence.schema-generation.database.action" value="create" /> + <property name="jakarta.persistence.schema-generation.create-source" value="script"/> + <property name="jakarta.persistence.schema-generation.create-script-source" value="src/main/resources/Schema.sql"/> + <property name="jakarta.persistence.sql-load-script-source" value="src/main/resources/TestData.sql"/> + <property name="hibernate.check_nullability" value="true"/> + <property name="hibernate.hbm2ddl.auto" value="validate"/> + <property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect"/> + <property name="hibernate.show_sql" value="true"/> + <property name="hibernate.format_sql" value="true"/> + </properties> + </persistence-unit> +</persistence> \ No newline at end of file