Merge branch 'master' into master
This commit is contained in:
@@ -1,17 +0,0 @@
|
||||
|
||||
## Persistence Modules
|
||||
|
||||
|
||||
### Relevant Articles:
|
||||
|
||||
- [Introduction to Hibernate Search](http://www.baeldung.com/hibernate-search)
|
||||
- [Bootstrapping Hibernate 5 with Spring](http://www.baeldung.com/hibernate-5-spring)
|
||||
- [Introduction to Lettuce – the Java Redis Client](http://www.baeldung.com/java-redis-lettuce)
|
||||
- [A Guide to Jdbi](http://www.baeldung.com/jdbi)
|
||||
- [Pessimistic Locking in JPA](http://www.baeldung.com/jpa-pessimistic-locking)
|
||||
- [Get All Data from a Table with Hibernate](https://www.baeldung.com/hibernate-select-all)
|
||||
- [Spring Data with Reactive Cassandra](https://www.baeldung.com/spring-data-cassandra-reactive)
|
||||
- [Spring Data JPA – Derived Delete Methods](https://www.baeldung.com/spring-data-jpa-deleteby)
|
||||
- [Difference Between save() and saveAndFlush() in Spring Data JPA](https://www.baeldung.com/spring-data-jpa-save-saveandflush)
|
||||
- [Persisting Maps with Hibernate](https://www.baeldung.com/hibernate-persisting-maps)
|
||||
- [Difference Between @Size, @Length, and @Column(length=value)](https://www.baeldung.com/jpa-size-length-column-differences)
|
||||
@@ -0,0 +1,5 @@
|
||||
|
||||
### Relevant Articles:
|
||||
|
||||
- [Persisting Maps with Hibernate](https://www.baeldung.com/hibernate-persisting-maps)
|
||||
- [Difference Between @Size, @Length, and @Column(length=value)](https://www.baeldung.com/jpa-size-length-column-differences)
|
||||
@@ -5,9 +5,9 @@
|
||||
|
||||
<parent>
|
||||
<groupId>com.baeldung</groupId>
|
||||
<artifactId>parent-modules</artifactId>
|
||||
<artifactId>persistence-modules</artifactId>
|
||||
<version>1.0.0-SNAPSHOT</version>
|
||||
<relativePath>../../</relativePath>
|
||||
<relativePath>..</relativePath>
|
||||
</parent>
|
||||
|
||||
<artifactId>hibernate-mapping</artifactId>
|
||||
@@ -31,22 +31,28 @@
|
||||
<artifactId>h2</artifactId>
|
||||
<version>${h2.version}</version>
|
||||
</dependency>
|
||||
<!-- validation -->
|
||||
<!-- validation -->
|
||||
<dependency>
|
||||
<groupId>org.hibernate</groupId>
|
||||
<artifactId>hibernate-validator</artifactId>
|
||||
<version>${hibernate-validator.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>javax.el</groupId>
|
||||
<artifactId>javax.el-api</artifactId>
|
||||
<version>${javax.el-api.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.glassfish</groupId>
|
||||
<artifactId>javax.el</artifactId>
|
||||
<version>${org.glassfish.javax.el.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>javax.money</groupId>
|
||||
<artifactId>money-api</artifactId>
|
||||
<version>1.0.3</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.javamoney</groupId>
|
||||
<artifactId>moneta</artifactId>
|
||||
<version>1.3</version>
|
||||
<type>pom</type>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
<build>
|
||||
@@ -60,11 +66,10 @@
|
||||
</build>
|
||||
|
||||
<properties>
|
||||
<hibernate.version>5.3.7.Final</hibernate.version>
|
||||
<hibernate.version>5.3.10.Final</hibernate.version>
|
||||
<assertj-core.version>3.8.0</assertj-core.version>
|
||||
<hibernate-validator.version>5.3.3.Final</hibernate-validator.version>
|
||||
<javax.el-api.version>2.2.5</javax.el-api.version>
|
||||
<org.glassfish.javax.el.version>3.0.1-b08</org.glassfish.javax.el.version>
|
||||
<hibernate-validator.version>6.0.16.Final</hibernate-validator.version>
|
||||
<org.glassfish.javax.el.version>3.0.1-b11</org.glassfish.javax.el.version>
|
||||
</properties>
|
||||
|
||||
</project>
|
||||
</project>
|
||||
|
||||
+1
-5
@@ -12,16 +12,12 @@ import java.net.URL;
|
||||
import java.util.Properties;
|
||||
|
||||
public class HibernateUtil {
|
||||
private static SessionFactory sessionFactory;
|
||||
|
||||
private HibernateUtil() {
|
||||
}
|
||||
|
||||
public static SessionFactory getSessionFactory(Strategy strategy) {
|
||||
if (sessionFactory == null) {
|
||||
sessionFactory = buildSessionFactory(strategy);
|
||||
}
|
||||
return sessionFactory;
|
||||
return buildSessionFactory(strategy);
|
||||
}
|
||||
|
||||
private static SessionFactory buildSessionFactory(Strategy strategy) {
|
||||
|
||||
+2
-2
@@ -2,12 +2,12 @@ package com.baeldung.hibernate;
|
||||
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
public enum Strategy {
|
||||
//See that the classes belongs to different packages
|
||||
MAP_KEY_COLUMN_BASED(Collections.singletonList(com.baeldung.hibernate.persistmaps.mapkeycolumn.Order.class)),
|
||||
MAP_KEY_COLUMN_BASED(Arrays.asList(com.baeldung.hibernate.persistmaps.mapkeycolumn.Order.class,
|
||||
com.baeldung.hibernate.basicannotation.Course.class)),
|
||||
MAP_KEY_BASED(Arrays.asList(com.baeldung.hibernate.persistmaps.mapkey.Item.class,
|
||||
com.baeldung.hibernate.persistmaps.mapkey.Order.class,com.baeldung.hibernate.persistmaps.mapkey.User.class)),
|
||||
MAP_KEY_JOIN_COLUMN_BASED(Arrays.asList(com.baeldung.hibernate.persistmaps.mapkeyjoincolumn.Seller.class,
|
||||
|
||||
+3
-1
@@ -4,8 +4,11 @@ import javax.persistence.Column;
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.Id;
|
||||
import javax.validation.constraints.Size;
|
||||
import javax.money.MonetaryAmount;
|
||||
|
||||
import org.hibernate.validator.constraints.Length;
|
||||
import org.hibernate.validator.constraints.CreditCardNumber;
|
||||
import org.hibernate.validator.constraints.Currency;
|
||||
|
||||
@Entity
|
||||
public class User {
|
||||
@@ -62,5 +65,4 @@ public class User {
|
||||
public void setCity(String city) {
|
||||
this.city = city;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+9
-8
@@ -1,18 +1,19 @@
|
||||
package com.baeldung.hibernate.basicannotation;
|
||||
|
||||
import com.baeldung.hibernate.HibernateUtil;
|
||||
import com.baeldung.hibernate.basicannotation.Course;
|
||||
import com.baeldung.hibernate.Strategy;
|
||||
import org.hibernate.PropertyValueException;
|
||||
import java.io.IOException;
|
||||
|
||||
import javax.persistence.PersistenceException;
|
||||
|
||||
import org.hibernate.Session;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.hibernate.Transaction;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Test;
|
||||
|
||||
import java.io.IOException;
|
||||
import com.baeldung.hibernate.HibernateUtil;
|
||||
import com.baeldung.hibernate.Strategy;
|
||||
|
||||
public class BasicAnnotationIntegrationTest {
|
||||
|
||||
@@ -48,7 +49,7 @@ public class BasicAnnotationIntegrationTest {
|
||||
|
||||
}
|
||||
|
||||
@Test(expected = PropertyValueException.class)
|
||||
@Test(expected = PersistenceException.class)
|
||||
public void givenACourse_whenCourseNameAbsent_shouldFail() {
|
||||
Course course = new Course();
|
||||
|
||||
|
||||
+290
@@ -0,0 +1,290 @@
|
||||
package com.baeldung.hibernate.validation;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.time.Duration;
|
||||
import java.util.Set;
|
||||
|
||||
import javax.money.CurrencyContextBuilder;
|
||||
import javax.money.Monetary;
|
||||
import javax.money.MonetaryAmount;
|
||||
import javax.validation.ConstraintViolation;
|
||||
import javax.validation.Validation;
|
||||
import javax.validation.Validator;
|
||||
import javax.validation.ValidatorFactory;
|
||||
|
||||
import org.hibernate.validator.constraints.CodePointLength;
|
||||
import org.hibernate.validator.constraints.CreditCardNumber;
|
||||
import org.hibernate.validator.constraints.Currency;
|
||||
import org.hibernate.validator.constraints.Length;
|
||||
import org.hibernate.validator.constraints.LuhnCheck;
|
||||
import org.hibernate.validator.constraints.Range;
|
||||
import org.hibernate.validator.constraints.SafeHtml;
|
||||
import org.hibernate.validator.constraints.ScriptAssert;
|
||||
import org.hibernate.validator.constraints.URL;
|
||||
import org.hibernate.validator.constraints.time.DurationMax;
|
||||
import org.hibernate.validator.constraints.time.DurationMin;
|
||||
import org.javamoney.moneta.CurrencyUnitBuilder;
|
||||
import org.javamoney.moneta.Money;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Test;
|
||||
|
||||
public class UserAdditionalValidationUnitTest {
|
||||
|
||||
private static Validator validator;
|
||||
private Set<ConstraintViolation<AdditionalValidations>> constraintViolations;
|
||||
|
||||
@BeforeClass
|
||||
public static void before() {
|
||||
ValidatorFactory config = Validation.buildDefaultValidatorFactory();
|
||||
validator = config.getValidator();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenValidationWithCCNAndNullCCN_thenNoConstraintViolation() {
|
||||
AdditionalValidations validations = new AdditionalValidations();
|
||||
constraintViolations = validator.validateProperty(validations, "creditCardNumber");
|
||||
assertTrue(constraintViolations.isEmpty());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenValidationWithCCNAndValidCCN_thenNoConstraintViolation() {
|
||||
AdditionalValidations validations = new AdditionalValidations();
|
||||
validations.setCreditCardNumber("79927398713");
|
||||
constraintViolations = validator.validateProperty(validations, "creditCardNumber");
|
||||
assertTrue(constraintViolations.isEmpty());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenValidationWithCCNAndInvalidCCN_thenConstraintViolation() {
|
||||
AdditionalValidations validations = new AdditionalValidations();
|
||||
validations.setCreditCardNumber("79927398714");
|
||||
constraintViolations = validator.validateProperty(validations, "creditCardNumber");
|
||||
assertEquals(constraintViolations.size(), 2);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenValidationWithCCNAndValidCCNWithDashes_thenConstraintViolation() {
|
||||
AdditionalValidations validations = new AdditionalValidations();
|
||||
validations.setCreditCardNumber("7992-7398-713");
|
||||
constraintViolations = validator.validateProperty(validations, "creditCardNumber");
|
||||
assertEquals(1, constraintViolations.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenValidationWithLenientCCNAndValidCCNWithDashes_thenNoConstraintViolation() {
|
||||
AdditionalValidations validations = new AdditionalValidations();
|
||||
validations.setLenientCreditCardNumber("7992-7398-713");
|
||||
constraintViolations = validator.validateProperty(validations, "lenientCreditCardNumber");
|
||||
assertTrue(constraintViolations.isEmpty());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenMonetaryAmountWithRightCurrency_thenNoConstraintViolation() {
|
||||
AdditionalValidations bean = new AdditionalValidations();
|
||||
bean.setBalance(Money.of(new BigDecimal(100.0), Monetary.getCurrency("EUR")));
|
||||
constraintViolations = validator.validateProperty(bean, "balance");
|
||||
assertEquals(0, constraintViolations.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenMonetaryAmountWithWrongCurrency_thenConstraintViolation() {
|
||||
AdditionalValidations validations = new AdditionalValidations();
|
||||
validations.setBalance(Money.of(new BigDecimal(100.0), Monetary.getCurrency("USD")));
|
||||
constraintViolations = validator.validateProperty(validations, "balance");
|
||||
assertEquals(1, constraintViolations.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenDurationShorterThanMin_thenConstraintViolation() {
|
||||
AdditionalValidations bean = new AdditionalValidations();
|
||||
bean.setDuration(Duration.ofDays(1).plusHours(1));
|
||||
constraintViolations = validator.validateProperty(bean, "duration");
|
||||
assertEquals(1, constraintViolations.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenDurationLongerThanMax_thenConstraintViolation() {
|
||||
AdditionalValidations bean = new AdditionalValidations();
|
||||
bean.setDuration(Duration.ofDays(2).plusHours(3));
|
||||
constraintViolations = validator.validateProperty(bean, "duration");
|
||||
assertEquals(1, constraintViolations.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenDurationBetweenMinAndMax_thenNoConstraintViolation() {
|
||||
AdditionalValidations bean = new AdditionalValidations();
|
||||
bean.setDuration(Duration.ofDays(2));
|
||||
constraintViolations = validator.validateProperty(bean, "duration");
|
||||
assertEquals(0, constraintViolations.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenValueBelowRangeMin_thenConstraintViolation() {
|
||||
AdditionalValidations bean = new AdditionalValidations();
|
||||
bean.setPercent(new BigDecimal("-1.4"));
|
||||
constraintViolations = validator.validateProperty(bean, "percent");
|
||||
assertEquals(1, constraintViolations.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenValueAboveRangeMax_thenConstraintViolation() {
|
||||
AdditionalValidations bean = new AdditionalValidations();
|
||||
bean.setPercent(new BigDecimal("100.03"));
|
||||
constraintViolations = validator.validateProperty(bean, "percent");
|
||||
assertEquals(1, constraintViolations.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenValueInRange_thenNoConstraintViolation() {
|
||||
AdditionalValidations bean = new AdditionalValidations();
|
||||
bean.setPercent(new BigDecimal("53.23"));
|
||||
constraintViolations = validator.validateProperty(bean, "percent");
|
||||
assertEquals(0, constraintViolations.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenLengthInRange_thenNoConstraintViolation() {
|
||||
AdditionalValidations bean = new AdditionalValidations();
|
||||
bean.setSomeString("aaa");
|
||||
constraintViolations = validator.validateProperty(bean, "someString");
|
||||
assertEquals(0, constraintViolations.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenCodePointLengthNotInRange_thenConstraintViolation() {
|
||||
AdditionalValidations bean = new AdditionalValidations();
|
||||
bean.setSomeString("aa\uD835\uDD0A");
|
||||
constraintViolations = validator.validateProperty(bean, "someString");
|
||||
assertEquals(1, constraintViolations.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenValidUrlWithWrongProtocol_thenConstraintViolation() {
|
||||
AdditionalValidations bean = new AdditionalValidations();
|
||||
|
||||
bean.setUrl("https://www.google.com/");
|
||||
constraintViolations = validator.validateProperty(bean, "url");
|
||||
assertEquals(0, constraintViolations.size());
|
||||
|
||||
bean.setUrl("http://www.google.com/");
|
||||
constraintViolations = validator.validateProperty(bean, "url");
|
||||
assertEquals(1, constraintViolations.size());
|
||||
|
||||
bean.setUrl("https://foo:bar");
|
||||
constraintViolations = validator.validateProperty(bean, "url");
|
||||
assertEquals(1, constraintViolations.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenScriptAssertFails_thenConstraintViolation() {
|
||||
AdditionalValidations bean = new AdditionalValidations();
|
||||
|
||||
constraintViolations = validator.validate(bean);
|
||||
assertEquals(0, constraintViolations.size());
|
||||
|
||||
bean.setValid(false);
|
||||
|
||||
constraintViolations = validator.validate(bean);
|
||||
assertEquals(1, constraintViolations.size());
|
||||
|
||||
constraintViolations = validator.validateProperty(bean, "valid");
|
||||
assertEquals(0, constraintViolations.size());
|
||||
}
|
||||
|
||||
@ScriptAssert(lang = "nashorn", script = "_this.valid")
|
||||
public class AdditionalValidations {
|
||||
private boolean valid = true;
|
||||
|
||||
@CreditCardNumber
|
||||
@LuhnCheck(startIndex = 0, endIndex = Integer.MAX_VALUE, checkDigitIndex = -1)
|
||||
private String creditCardNumber;
|
||||
|
||||
@CreditCardNumber(ignoreNonDigitCharacters = true)
|
||||
private String lenientCreditCardNumber;
|
||||
|
||||
@Currency("EUR")
|
||||
private MonetaryAmount balance;
|
||||
|
||||
@DurationMin(days = 1, hours = 2)
|
||||
@DurationMax(days = 2, hours = 1)
|
||||
private Duration duration;
|
||||
|
||||
@Range(min = 0, max = 100)
|
||||
private BigDecimal percent;
|
||||
|
||||
@Length(min = 1, max = 3)
|
||||
@CodePointLength(min = 1, max = 3)
|
||||
private String someString;
|
||||
|
||||
@URL(protocol = "https")
|
||||
private String url;
|
||||
|
||||
public String getCreditCardNumber() {
|
||||
return creditCardNumber;
|
||||
}
|
||||
|
||||
public void setCreditCardNumber(String creditCardNumber) {
|
||||
this.creditCardNumber = creditCardNumber;
|
||||
}
|
||||
|
||||
public String getLenientCreditCardNumber() {
|
||||
return lenientCreditCardNumber;
|
||||
}
|
||||
|
||||
public void setLenientCreditCardNumber(String lenientCreditCardNumber) {
|
||||
this.lenientCreditCardNumber = lenientCreditCardNumber;
|
||||
}
|
||||
|
||||
public MonetaryAmount getBalance() {
|
||||
return balance;
|
||||
}
|
||||
|
||||
public void setBalance(MonetaryAmount balance) {
|
||||
this.balance = balance;
|
||||
}
|
||||
|
||||
public Duration getDuration() {
|
||||
return duration;
|
||||
}
|
||||
|
||||
public void setDuration(Duration duration) {
|
||||
this.duration = duration;
|
||||
}
|
||||
|
||||
public BigDecimal getPercent() {
|
||||
return percent;
|
||||
}
|
||||
|
||||
public void setPercent(BigDecimal percent) {
|
||||
this.percent = percent;
|
||||
}
|
||||
|
||||
public String getSomeString() {
|
||||
return someString;
|
||||
}
|
||||
|
||||
public void setSomeString(String someString) {
|
||||
this.someString = someString;
|
||||
}
|
||||
|
||||
public String getUrl() {
|
||||
return url;
|
||||
}
|
||||
|
||||
public void setUrl(String url) {
|
||||
this.url = url;
|
||||
}
|
||||
|
||||
public boolean isValid() {
|
||||
return valid;
|
||||
}
|
||||
|
||||
public void setValid(boolean valid) {
|
||||
this.valid = valid;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -37,6 +37,11 @@
|
||||
<artifactId>hibernate-spatial</artifactId>
|
||||
<version>${hibernate.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.opengeo</groupId>
|
||||
<artifactId>geodb</artifactId>
|
||||
<version>${geodb.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.hibernate</groupId>
|
||||
<artifactId>hibernate-c3p0</artifactId>
|
||||
@@ -99,6 +104,14 @@
|
||||
</resource>
|
||||
</resources>
|
||||
</build>
|
||||
|
||||
<repositories>
|
||||
<repository>
|
||||
<id>geodb-repo</id>
|
||||
<name>GeoDB repository</name>
|
||||
<url>http://repo.boundlessgeo.com/main/</url>
|
||||
</repository>
|
||||
</repositories>
|
||||
|
||||
<properties>
|
||||
<hibernate.version>5.3.7.Final</hibernate.version>
|
||||
@@ -106,6 +119,7 @@
|
||||
<mariaDB4j.version>2.2.3</mariaDB4j.version>
|
||||
<assertj-core.version>3.8.0</assertj-core.version>
|
||||
<openjdk-jmh.version>1.21</openjdk-jmh.version>
|
||||
<geodb.version>0.9</geodb.version>
|
||||
</properties>
|
||||
|
||||
</project>
|
||||
|
||||
+17
-18
@@ -5,27 +5,25 @@ import java.io.IOException;
|
||||
import java.net.URL;
|
||||
import java.util.Properties;
|
||||
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.hibernate.boot.Metadata;
|
||||
import org.hibernate.boot.MetadataSources;
|
||||
import org.hibernate.boot.registry.StandardServiceRegistryBuilder;
|
||||
import org.hibernate.service.ServiceRegistry;
|
||||
|
||||
import com.baeldung.hibernate.customtypes.LocalDateStringType;
|
||||
import com.baeldung.hibernate.customtypes.OfficeEmployee;
|
||||
import com.baeldung.hibernate.entities.DeptEmployee;
|
||||
import com.baeldung.hibernate.joincolumn.Email;
|
||||
import com.baeldung.hibernate.joincolumn.Office;
|
||||
import com.baeldung.hibernate.joincolumn.OfficeAddress;
|
||||
import com.baeldung.hibernate.optimisticlocking.OptimisticLockingCourse;
|
||||
import com.baeldung.hibernate.optimisticlocking.OptimisticLockingStudent;
|
||||
import com.baeldung.hibernate.pessimisticlocking.Individual;
|
||||
import com.baeldung.hibernate.pessimisticlocking.PessimisticLockingCourse;
|
||||
import com.baeldung.hibernate.pessimisticlocking.PessimisticLockingEmployee;
|
||||
import com.baeldung.hibernate.pessimisticlocking.PessimisticLockingStudent;
|
||||
import com.baeldung.hibernate.pojo.*;
|
||||
import com.baeldung.hibernate.pojo.Person;
|
||||
import com.baeldung.hibernate.pojo.inheritance.*;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.hibernate.boot.Metadata;
|
||||
import org.hibernate.boot.MetadataBuilder;
|
||||
import org.hibernate.boot.MetadataSources;
|
||||
import org.hibernate.boot.registry.StandardServiceRegistryBuilder;
|
||||
import org.hibernate.cfg.Configuration;
|
||||
import org.hibernate.service.ServiceRegistry;
|
||||
|
||||
import com.baeldung.hibernate.pojo.Course;
|
||||
import com.baeldung.hibernate.pojo.Employee;
|
||||
import com.baeldung.hibernate.pojo.EntityDescription;
|
||||
@@ -36,6 +34,7 @@ import com.baeldung.hibernate.pojo.Person;
|
||||
import com.baeldung.hibernate.pojo.Phone;
|
||||
import com.baeldung.hibernate.pojo.PointEntity;
|
||||
import com.baeldung.hibernate.pojo.PolygonEntity;
|
||||
import com.baeldung.hibernate.pojo.Post;
|
||||
import com.baeldung.hibernate.pojo.Product;
|
||||
import com.baeldung.hibernate.pojo.Student;
|
||||
import com.baeldung.hibernate.pojo.TemporalValues;
|
||||
@@ -52,7 +51,6 @@ import com.baeldung.hibernate.pojo.inheritance.Pet;
|
||||
import com.baeldung.hibernate.pojo.inheritance.Vehicle;
|
||||
|
||||
public class HibernateUtil {
|
||||
private static SessionFactory sessionFactory;
|
||||
private static String PROPERTY_FILE_NAME;
|
||||
|
||||
public static SessionFactory getSessionFactory() throws IOException {
|
||||
@@ -61,11 +59,8 @@ public class HibernateUtil {
|
||||
|
||||
public static SessionFactory getSessionFactory(String propertyFileName) throws IOException {
|
||||
PROPERTY_FILE_NAME = propertyFileName;
|
||||
if (sessionFactory == null) {
|
||||
ServiceRegistry serviceRegistry = configureServiceRegistry();
|
||||
sessionFactory = makeSessionFactory(serviceRegistry);
|
||||
}
|
||||
return sessionFactory;
|
||||
ServiceRegistry serviceRegistry = configureServiceRegistry();
|
||||
return makeSessionFactory(serviceRegistry);
|
||||
}
|
||||
|
||||
public static SessionFactory getSessionFactoryByProperties(Properties properties) throws IOException {
|
||||
@@ -114,6 +109,10 @@ public class HibernateUtil {
|
||||
metadataSources.addAnnotatedClass(OptimisticLockingStudent.class);
|
||||
metadataSources.addAnnotatedClass(OfficeEmployee.class);
|
||||
metadataSources.addAnnotatedClass(Post.class);
|
||||
metadataSources.addAnnotatedClass(com.baeldung.hibernate.joincolumn.OfficialEmployee.class);
|
||||
metadataSources.addAnnotatedClass(Email.class);
|
||||
metadataSources.addAnnotatedClass(Office.class);
|
||||
metadataSources.addAnnotatedClass(OfficeAddress.class);
|
||||
|
||||
Metadata metadata = metadataSources.getMetadataBuilder()
|
||||
.applyBasicType(LocalDateStringType.INSTANCE)
|
||||
|
||||
+3
-3
@@ -19,7 +19,7 @@ public class Email {
|
||||
|
||||
@ManyToOne(fetch = FetchType.LAZY)
|
||||
@JoinColumn(name = "employee_id")
|
||||
private Employee employee;
|
||||
private OfficialEmployee employee;
|
||||
|
||||
public Long getId() {
|
||||
return id;
|
||||
@@ -37,11 +37,11 @@ public class Email {
|
||||
this.address = address;
|
||||
}
|
||||
|
||||
public Employee getEmployee() {
|
||||
public OfficialEmployee getEmployee() {
|
||||
return employee;
|
||||
}
|
||||
|
||||
public void setEmployee(Employee employee) {
|
||||
public void setEmployee(OfficialEmployee employee) {
|
||||
this.employee = employee;
|
||||
}
|
||||
}
|
||||
+3
-3
@@ -21,7 +21,7 @@ public class Office {
|
||||
@JoinColumn(name="ADDR_ID", referencedColumnName="ID"),
|
||||
@JoinColumn(name="ADDR_ZIP", referencedColumnName="ZIP")
|
||||
})
|
||||
private Address address;
|
||||
private OfficeAddress address;
|
||||
|
||||
public Long getId() {
|
||||
return id;
|
||||
@@ -31,11 +31,11 @@ public class Office {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public Address getAddress() {
|
||||
public OfficeAddress getAddress() {
|
||||
return address;
|
||||
}
|
||||
|
||||
public void setAddress(Address address) {
|
||||
public void setAddress(OfficeAddress address) {
|
||||
this.address = address;
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -7,7 +7,7 @@ import javax.persistence.GenerationType;
|
||||
import javax.persistence.Id;
|
||||
|
||||
@Entity
|
||||
public class Address {
|
||||
public class OfficeAddress {
|
||||
|
||||
@Id
|
||||
@GeneratedValue(strategy = GenerationType.AUTO)
|
||||
+1
-1
@@ -9,7 +9,7 @@ import javax.persistence.Id;
|
||||
import javax.persistence.OneToMany;
|
||||
|
||||
@Entity
|
||||
public class Employee {
|
||||
public class OfficialEmployee {
|
||||
|
||||
@Id
|
||||
@GeneratedValue(strategy = GenerationType.AUTO)
|
||||
+1
-4
@@ -19,10 +19,7 @@ public class HibernateUtil {
|
||||
}
|
||||
|
||||
public static SessionFactory getSessionFactory(Strategy strategy) {
|
||||
if (sessionFactory == null) {
|
||||
sessionFactory = buildSessionFactory(strategy);
|
||||
}
|
||||
return sessionFactory;
|
||||
return buildSessionFactory(strategy);
|
||||
}
|
||||
|
||||
private static SessionFactory buildSessionFactory(Strategy strategy) {
|
||||
|
||||
+2
@@ -2,6 +2,7 @@ package com.baeldung.hibernate.pojo;
|
||||
|
||||
import com.vividsolutions.jts.geom.Point;
|
||||
|
||||
import javax.persistence.Column;
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.GeneratedValue;
|
||||
import javax.persistence.Id;
|
||||
@@ -13,6 +14,7 @@ public class PointEntity {
|
||||
@GeneratedValue
|
||||
private Long id;
|
||||
|
||||
@Column(columnDefinition="BINARY(2048)")
|
||||
private Point point;
|
||||
|
||||
public PointEntity() {
|
||||
|
||||
+1
-5
@@ -122,11 +122,7 @@ public class DynamicMappingIntegrationTest {
|
||||
Employee employee = session.get(Employee.class, 1);
|
||||
assertThat(employee.getGrossIncome()).isEqualTo(10_000);
|
||||
|
||||
session.close();
|
||||
|
||||
session = HibernateUtil.getSessionFactory().openSession();
|
||||
transaction = session.beginTransaction();
|
||||
|
||||
session.disableFilter("incomeLevelFilter");
|
||||
employees = session.createQuery("from Employee").getResultList();
|
||||
|
||||
assertThat(employees).hasSize(3);
|
||||
|
||||
+17
@@ -4,7 +4,10 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
|
||||
import java.io.FileInputStream;
|
||||
import java.io.IOException;
|
||||
import java.net.URL;
|
||||
import java.util.Properties;
|
||||
|
||||
import javax.persistence.Query;
|
||||
|
||||
@@ -24,6 +27,8 @@ import com.vividsolutions.jts.io.ParseException;
|
||||
import com.vividsolutions.jts.io.WKTReader;
|
||||
import com.vividsolutions.jts.util.GeometricShapeFactory;
|
||||
|
||||
import geodb.GeoDB;
|
||||
|
||||
public class HibernateSpatialIntegrationTest {
|
||||
|
||||
private Session session;
|
||||
@@ -34,6 +39,7 @@ public class HibernateSpatialIntegrationTest {
|
||||
session = HibernateUtil.getSessionFactory("hibernate-spatial.properties")
|
||||
.openSession();
|
||||
transaction = session.beginTransaction();
|
||||
session.doWork(conn -> { GeoDB.InitGeoDB(conn); });
|
||||
}
|
||||
|
||||
@After
|
||||
@@ -141,4 +147,15 @@ public class HibernateSpatialIntegrationTest {
|
||||
shapeFactory.setSize(radius * 2);
|
||||
return shapeFactory.createCircle();
|
||||
}
|
||||
|
||||
public static Properties getProperties(String propertyFile) throws IOException {
|
||||
Properties properties = new Properties();
|
||||
URL propertiesURL = Thread.currentThread()
|
||||
.getContextClassLoader()
|
||||
.getResource(propertyFile);
|
||||
try (FileInputStream inputStream = new FileInputStream(propertiesURL.getFile())) {
|
||||
properties.load(inputStream);
|
||||
}
|
||||
return properties;
|
||||
}
|
||||
}
|
||||
|
||||
+1
-1
@@ -45,7 +45,7 @@ public class TypeSafeCriteriaIntegrationTest {
|
||||
CriteriaQuery<Student> criteriaQuery = cb.createQuery(Student.class);
|
||||
|
||||
Root<Student> root = criteriaQuery.from(Student.class);
|
||||
criteriaQuery.select(root).where(cb.equal(root.get(Student_.gradYear), 1965));
|
||||
criteriaQuery.select(root).where(cb.equal(root.get("gradYear"), 1965));
|
||||
|
||||
Query<Student> query = session.createQuery(criteriaQuery);
|
||||
List<Student> results = query.getResultList();
|
||||
|
||||
+2
-2
@@ -32,7 +32,7 @@ public class JoinColumnIntegrationTest {
|
||||
public void givenOfficeEntity_setAddress_shouldPersist() {
|
||||
Office office = new Office();
|
||||
|
||||
Address address = new Address();
|
||||
OfficeAddress address = new OfficeAddress();
|
||||
address.setZipCode("11-111");
|
||||
office.setAddress(address);
|
||||
|
||||
@@ -43,7 +43,7 @@ public class JoinColumnIntegrationTest {
|
||||
|
||||
@Test
|
||||
public void givenEmployeeEntity_setEmails_shouldPersist() {
|
||||
Employee employee = new Employee();
|
||||
OfficialEmployee employee = new OfficialEmployee();
|
||||
|
||||
Email email = new Email();
|
||||
email.setAddress("example@email.com");
|
||||
|
||||
+22
-10
@@ -1,17 +1,23 @@
|
||||
package com.baeldung.hibernate.optimisticlocking;
|
||||
|
||||
import com.baeldung.hibernate.HibernateUtil;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
import java.io.IOException;
|
||||
import java.util.Arrays;
|
||||
|
||||
import javax.persistence.EntityManager;
|
||||
import javax.persistence.LockModeType;
|
||||
import javax.persistence.OptimisticLockException;
|
||||
import java.io.IOException;
|
||||
import java.util.Arrays;
|
||||
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.junit.After;
|
||||
import org.junit.AfterClass;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
|
||||
import com.baeldung.hibernate.HibernateUtil;
|
||||
|
||||
public class OptimisticLockingIntegrationTest {
|
||||
|
||||
private static SessionFactory sessionFactory;
|
||||
|
||||
@Before
|
||||
public void setUp() throws IOException {
|
||||
@@ -124,11 +130,17 @@ public class OptimisticLockingIntegrationTest {
|
||||
|
||||
protected static EntityManager getEntityManagerWithOpenTransaction() throws IOException {
|
||||
String propertyFileName = "hibernate-pessimistic-locking.properties";
|
||||
EntityManager entityManager = HibernateUtil.getSessionFactory(propertyFileName)
|
||||
.openSession();
|
||||
entityManager.getTransaction()
|
||||
.begin();
|
||||
if (sessionFactory == null) {
|
||||
sessionFactory = HibernateUtil.getSessionFactory(propertyFileName);
|
||||
}
|
||||
EntityManager entityManager = sessionFactory.openSession();
|
||||
entityManager.getTransaction().begin();
|
||||
|
||||
return entityManager;
|
||||
}
|
||||
|
||||
@AfterClass
|
||||
public static void afterTests() {
|
||||
sessionFactory.close();
|
||||
}
|
||||
}
|
||||
|
||||
+15
-4
@@ -2,6 +2,9 @@ package com.baeldung.hibernate.pessimisticlocking;
|
||||
|
||||
import com.baeldung.hibernate.HibernateUtil;
|
||||
import com.vividsolutions.jts.util.Assert;
|
||||
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.junit.AfterClass;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Test;
|
||||
|
||||
@@ -10,6 +13,8 @@ import java.io.IOException;
|
||||
import java.util.Arrays;
|
||||
|
||||
public class BasicPessimisticLockingIntegrationTest {
|
||||
|
||||
private static SessionFactory sessionFactory;
|
||||
|
||||
@BeforeClass
|
||||
public static void setUp() throws IOException {
|
||||
@@ -140,12 +145,18 @@ public class BasicPessimisticLockingIntegrationTest {
|
||||
|
||||
protected static EntityManager getEntityManagerWithOpenTransaction() throws IOException {
|
||||
String propertyFileName = "hibernate-pessimistic-locking.properties";
|
||||
EntityManager entityManager = HibernateUtil.getSessionFactory(propertyFileName)
|
||||
.openSession();
|
||||
entityManager.getTransaction()
|
||||
.begin();
|
||||
if (sessionFactory == null) {
|
||||
sessionFactory = HibernateUtil.getSessionFactory(propertyFileName);
|
||||
}
|
||||
EntityManager entityManager = sessionFactory.openSession();
|
||||
entityManager.getTransaction().begin();
|
||||
|
||||
return entityManager;
|
||||
}
|
||||
|
||||
@AfterClass
|
||||
public static void afterTests() {
|
||||
sessionFactory.close();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+15
-5
@@ -1,6 +1,9 @@
|
||||
package com.baeldung.hibernate.pessimisticlocking;
|
||||
|
||||
import com.baeldung.hibernate.HibernateUtil;
|
||||
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.junit.AfterClass;
|
||||
import org.junit.Test;
|
||||
|
||||
import javax.persistence.EntityManager;
|
||||
@@ -13,6 +16,8 @@ import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
public class PessimisticLockScopesIntegrationTest {
|
||||
|
||||
private static SessionFactory sessionFactory;
|
||||
|
||||
@Test
|
||||
public void givenEclipseEntityWithJoinInheritance_whenNormalLock_thenShouldChildAndParentEntity() throws IOException {
|
||||
@@ -104,12 +109,17 @@ public class PessimisticLockScopesIntegrationTest {
|
||||
|
||||
protected EntityManager getEntityManagerWithOpenTransaction() throws IOException {
|
||||
String propertyFileName = "hibernate-pessimistic-locking.properties";
|
||||
EntityManager entityManager = HibernateUtil.getSessionFactory(propertyFileName)
|
||||
.openSession();
|
||||
entityManager.getTransaction()
|
||||
.begin();
|
||||
if (sessionFactory == null) {
|
||||
sessionFactory = HibernateUtil.getSessionFactory(propertyFileName);
|
||||
}
|
||||
EntityManager entityManager = sessionFactory.openSession();
|
||||
entityManager.getTransaction().begin();
|
||||
|
||||
return entityManager;
|
||||
}
|
||||
|
||||
|
||||
@AfterClass
|
||||
public static void afterTests() {
|
||||
sessionFactory.close();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,10 +1,14 @@
|
||||
hibernate.connection.driver_class=org.postgresql.Driver
|
||||
hibernate.connection.url=jdbc:postgresql://localhost:5432/test
|
||||
hibernate.connection.username=postgres
|
||||
hibernate.connection.password=thule
|
||||
hibernate.connection.driver_class=org.h2.Driver
|
||||
hibernate.connection.url=jdbc:h2:mem:mydb1;DB_CLOSE_DELAY=-1
|
||||
hibernate.connection.username=sa
|
||||
hibernate.connection.autocommit=true
|
||||
jdbc.password=thule
|
||||
jdbc.password=
|
||||
|
||||
hibernate.dialect=org.hibernate.dialect.PostgreSQLDialect
|
||||
hibernate.dialect=org.hibernate.dialect.H2Dialect
|
||||
hibernate.show_sql=true
|
||||
hibernate.hbm2ddl.auto=create-drop
|
||||
hibernate.hbm2ddl.auto=create-drop
|
||||
|
||||
hibernate.c3p0.min_size=5
|
||||
hibernate.c3p0.max_size=20
|
||||
hibernate.c3p0.acquire_increment=5
|
||||
hibernate.c3p0.timeout=1800
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
hibernate.connection.driver_class=org.h2.Driver
|
||||
hibernate.connection.url=jdbc:h2:mem:mydb1;DB_CLOSE_DELAY=-1;LOCK_TIMEOUT=100;MVCC=FALSE
|
||||
hibernate.connection.url=jdbc:h2:mem:mydb3;DB_CLOSE_DELAY=-1;LOCK_TIMEOUT=100;MVCC=FALSE
|
||||
hibernate.connection.username=sa
|
||||
hibernate.connection.autocommit=true
|
||||
hibernate.dialect=org.hibernate.dialect.H2Dialect
|
||||
|
||||
@@ -1,10 +1,14 @@
|
||||
hibernate.dialect=org.hibernate.spatial.dialect.mysql.MySQL56SpatialDialect
|
||||
hibernate.connection.driver_class=com.mysql.jdbc.Driver
|
||||
hibernate.connection.url=jdbc:mysql://localhost:3306/hibernate-spatial
|
||||
hibernate.connection.username=root
|
||||
hibernate.connection.password=pass
|
||||
hibernate.connection.pool_size=5
|
||||
hibernate.connection.driver_class=org.h2.Driver
|
||||
hibernate.connection.url=jdbc:h2:mem:mydb1;DB_CLOSE_DELAY=-1
|
||||
hibernate.connection.username=sa
|
||||
hibernate.connection.autocommit=true
|
||||
jdbc.password=
|
||||
|
||||
hibernate.dialect=org.hibernate.spatial.dialect.h2geodb.GeoDBDialect
|
||||
hibernate.show_sql=true
|
||||
hibernate.format_sql=true
|
||||
hibernate.max_fetch_depth=5
|
||||
hibernate.hbm2ddl.auto=create-drop
|
||||
hibernate.hbm2ddl.auto=create-drop
|
||||
|
||||
hibernate.c3p0.min_size=5
|
||||
hibernate.c3p0.max_size=20
|
||||
hibernate.c3p0.acquire_increment=5
|
||||
hibernate.c3p0.timeout=1800
|
||||
|
||||
@@ -1 +1,3 @@
|
||||
### Relevant Articles:
|
||||
|
||||
- [A Guide to Jdbi](http://www.baeldung.com/jdbi)
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
- [A Guide to SqlResultSetMapping](http://www.baeldung.com/jpa-sql-resultset-mapping)
|
||||
- [A Guide to Stored Procedures with JPA](http://www.baeldung.com/jpa-stored-procedures)
|
||||
- [Fixing the JPA error “java.lang.String cannot be cast to [Ljava.lang.String;”]](https://www.baeldung.com/jpa-error-java-lang-string-cannot-be-cast)
|
||||
- [Fixing the JPA error “java.lang.String cannot be cast to Ljava.lang.String;”](https://www.baeldung.com/jpa-error-java-lang-string-cannot-be-cast)
|
||||
- [JPA Entity Graph](https://www.baeldung.com/jpa-entity-graph)
|
||||
- [JPA 2.2 Support for Java 8 Date/Time Types](https://www.baeldung.com/jpa-java-time)
|
||||
- [Converting Between LocalDate and SQL Date](https://www.baeldung.com/java-convert-localdate-sql-date)
|
||||
@@ -10,3 +10,6 @@
|
||||
- [Types of JPA Queries](https://www.baeldung.com/jpa-queries)
|
||||
- [JPA/Hibernate Projections](https://www.baeldung.com/jpa-hibernate-projections)
|
||||
- [Composite Primary Keys in JPA](https://www.baeldung.com/jpa-composite-primary-keys)
|
||||
- [Defining JPA Entities](https://www.baeldung.com/jpa-entities)
|
||||
- [JPA @Basic Annotation](https://www.baeldung.com/jpa-basic-annotation)
|
||||
- [Default Column Values in JPA](https://www.baeldung.com/jpa-default-column-values)
|
||||
|
||||
@@ -0,0 +1,43 @@
|
||||
package com.baeldung.jpa.entity;
|
||||
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.Id;
|
||||
import javax.persistence.IdClass;
|
||||
|
||||
@Entity
|
||||
@IdClass(AccountId.class)
|
||||
public class Account {
|
||||
|
||||
@Id
|
||||
private String accountNumber;
|
||||
|
||||
@Id
|
||||
private String accountType;
|
||||
|
||||
private String description;
|
||||
|
||||
public String getAccountNumber() {
|
||||
return accountNumber;
|
||||
}
|
||||
|
||||
public void setAccountNumber(String accountNumber) {
|
||||
this.accountNumber = accountNumber;
|
||||
}
|
||||
|
||||
public String getAccountType() {
|
||||
return accountType;
|
||||
}
|
||||
|
||||
public void setAccountType(String accountType) {
|
||||
this.accountType = accountType;
|
||||
}
|
||||
|
||||
public String getDescription() {
|
||||
return description;
|
||||
}
|
||||
|
||||
public void setDescription(String description) {
|
||||
this.description = description;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,52 @@
|
||||
package com.baeldung.jpa.entity;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
public class AccountId implements Serializable {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
private String accountNumber;
|
||||
private String accountType;
|
||||
|
||||
public AccountId() {
|
||||
|
||||
}
|
||||
|
||||
public AccountId(String accountNumber, String accountType) {
|
||||
this.accountNumber = accountNumber;
|
||||
this.accountType = accountType;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
final int prime = 31;
|
||||
int result = 1;
|
||||
result = prime * result + ((accountNumber == null) ? 0 : accountNumber.hashCode());
|
||||
result = prime * result + ((accountType == null) ? 0 : accountType.hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object obj) {
|
||||
if (this == obj)
|
||||
return true;
|
||||
if (obj == null)
|
||||
return false;
|
||||
if (getClass() != obj.getClass())
|
||||
return false;
|
||||
AccountId other = (AccountId) obj;
|
||||
if (accountNumber == null) {
|
||||
if (other.accountNumber != null)
|
||||
return false;
|
||||
} else if (!accountNumber.equals(other.accountNumber))
|
||||
return false;
|
||||
if (accountType == null) {
|
||||
if (other.accountType != null)
|
||||
return false;
|
||||
} else if (!accountType.equals(other.accountType))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
package com.baeldung.jpa.entity;
|
||||
|
||||
import javax.persistence.EmbeddedId;
|
||||
import javax.persistence.Entity;
|
||||
|
||||
@Entity
|
||||
public class Book {
|
||||
|
||||
@EmbeddedId
|
||||
private BookId bookId;
|
||||
|
||||
private String description;
|
||||
|
||||
public Book() {
|
||||
|
||||
}
|
||||
|
||||
public Book(BookId bookId) {
|
||||
this.bookId = bookId;
|
||||
}
|
||||
|
||||
public BookId getBookId() {
|
||||
return bookId;
|
||||
}
|
||||
|
||||
public String getDescription() {
|
||||
return description;
|
||||
}
|
||||
|
||||
public void setDescription(String description) {
|
||||
this.description = description;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,62 @@
|
||||
package com.baeldung.jpa.entity;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
import javax.persistence.Embeddable;
|
||||
|
||||
@Embeddable
|
||||
public class BookId implements Serializable {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
private String title;
|
||||
private String language;
|
||||
|
||||
public BookId() {
|
||||
|
||||
}
|
||||
|
||||
public BookId(String title, String language) {
|
||||
this.title = title;
|
||||
this.language = language;
|
||||
}
|
||||
|
||||
public String getTitle() {
|
||||
return title;
|
||||
}
|
||||
|
||||
public String getLanguage() {
|
||||
return language;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
final int prime = 31;
|
||||
int result = 1;
|
||||
result = prime * result + ((language == null) ? 0 : language.hashCode());
|
||||
result = prime * result + ((title == null) ? 0 : title.hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object obj) {
|
||||
if (this == obj)
|
||||
return true;
|
||||
if (obj == null)
|
||||
return false;
|
||||
if (getClass() != obj.getClass())
|
||||
return false;
|
||||
BookId other = (BookId) obj;
|
||||
if (language == null) {
|
||||
if (other.language != null)
|
||||
return false;
|
||||
} else if (!language.equals(other.language))
|
||||
return false;
|
||||
if (title == null) {
|
||||
if (other.title != null)
|
||||
return false;
|
||||
} else if (!title.equals(other.title))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,75 @@
|
||||
package com.baeldung.jpa.entity;
|
||||
|
||||
import java.util.Date;
|
||||
|
||||
import javax.persistence.Column;
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.EnumType;
|
||||
import javax.persistence.Enumerated;
|
||||
import javax.persistence.GeneratedValue;
|
||||
import javax.persistence.GenerationType;
|
||||
import javax.persistence.Id;
|
||||
import javax.persistence.Table;
|
||||
import javax.persistence.Temporal;
|
||||
import javax.persistence.TemporalType;
|
||||
import javax.persistence.Transient;
|
||||
|
||||
import com.baeldung.util.Gender;
|
||||
|
||||
@Entity
|
||||
@Table(name="STUDENT")
|
||||
public class Student {
|
||||
|
||||
@Id
|
||||
@GeneratedValue(strategy = GenerationType.AUTO)
|
||||
private Long id;
|
||||
@Column(name = "STUDENT_NAME", length = 50, nullable = false, unique = false)
|
||||
private String name;
|
||||
@Transient
|
||||
private Integer age;
|
||||
@Temporal(TemporalType.DATE)
|
||||
private Date birthDate;
|
||||
@Enumerated(EnumType.STRING)
|
||||
private Gender gender;
|
||||
|
||||
public Long getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(Long id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public Integer getAge() {
|
||||
return age;
|
||||
}
|
||||
|
||||
public void setAge(Integer age) {
|
||||
this.age = age;
|
||||
}
|
||||
|
||||
public Date getBirthDate() {
|
||||
return birthDate;
|
||||
}
|
||||
|
||||
public void setBirthDate(Date birthDate) {
|
||||
this.birthDate = birthDate;
|
||||
}
|
||||
|
||||
public Gender getGender() {
|
||||
return gender;
|
||||
}
|
||||
|
||||
public void setGender(Gender gender) {
|
||||
this.gender = gender;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,91 @@
|
||||
package com.baeldung.jpa.enums;
|
||||
|
||||
import javax.persistence.*;
|
||||
|
||||
@Entity
|
||||
public class Article {
|
||||
|
||||
@Id
|
||||
private int id;
|
||||
|
||||
private String title;
|
||||
|
||||
@Enumerated(EnumType.ORDINAL)
|
||||
private Status status;
|
||||
|
||||
@Enumerated(EnumType.STRING)
|
||||
private Type type;
|
||||
|
||||
@Basic
|
||||
private int priorityValue;
|
||||
|
||||
@Transient
|
||||
private Priority priority;
|
||||
|
||||
private Category category;
|
||||
|
||||
public Article() {
|
||||
}
|
||||
|
||||
@PostLoad
|
||||
void fillTransient() {
|
||||
if (priorityValue > 0) {
|
||||
this.priority = Priority.of(priorityValue);
|
||||
}
|
||||
}
|
||||
|
||||
@PrePersist
|
||||
void fillPersistent() {
|
||||
if (priority != null) {
|
||||
this.priorityValue = priority.getPriority();
|
||||
}
|
||||
}
|
||||
|
||||
public int getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(int id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public String getTitle() {
|
||||
return title;
|
||||
}
|
||||
|
||||
public void setTitle(String title) {
|
||||
this.title = title;
|
||||
}
|
||||
|
||||
public Status getStatus() {
|
||||
return status;
|
||||
}
|
||||
|
||||
public void setStatus(Status status) {
|
||||
this.status = status;
|
||||
}
|
||||
|
||||
public Type getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
public void setType(Type type) {
|
||||
this.type = type;
|
||||
}
|
||||
|
||||
public Priority getPriority() {
|
||||
return priority;
|
||||
}
|
||||
|
||||
public void setPriority(Priority priority) {
|
||||
this.priority = priority;
|
||||
}
|
||||
|
||||
public Category getCategory() {
|
||||
return category;
|
||||
}
|
||||
|
||||
public void setCategory(Category category) {
|
||||
this.category = category;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
package com.baeldung.jpa.enums;
|
||||
|
||||
import java.util.stream.Stream;
|
||||
|
||||
public enum Category {
|
||||
SPORT("S"), MUSIC("M"), TECHNOLOGY("T");
|
||||
|
||||
private String code;
|
||||
|
||||
Category(String code) {
|
||||
this.code = code;
|
||||
}
|
||||
|
||||
public String getCode() {
|
||||
return code;
|
||||
}
|
||||
}
|
||||
+28
@@ -0,0 +1,28 @@
|
||||
package com.baeldung.jpa.enums;
|
||||
|
||||
import javax.persistence.AttributeConverter;
|
||||
import javax.persistence.Converter;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
@Converter(autoApply = true)
|
||||
public class CategoryConverter implements AttributeConverter<Category, String> {
|
||||
@Override
|
||||
public String convertToDatabaseColumn(Category category) {
|
||||
if (category == null) {
|
||||
return null;
|
||||
}
|
||||
return category.getCode();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Category convertToEntityAttribute(final String code) {
|
||||
if (code == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return Stream.of(Category.values())
|
||||
.filter(c -> c.getCode().equals(code))
|
||||
.findFirst()
|
||||
.orElseThrow(IllegalArgumentException::new);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,24 @@
|
||||
package com.baeldung.jpa.enums;
|
||||
|
||||
import java.util.stream.Stream;
|
||||
|
||||
public enum Priority {
|
||||
LOW(100), MEDIUM(200), HIGH(300);
|
||||
|
||||
private int priority;
|
||||
|
||||
private Priority(int priority) {
|
||||
this.priority = priority;
|
||||
}
|
||||
|
||||
public int getPriority() {
|
||||
return priority;
|
||||
}
|
||||
|
||||
public static Priority of(int priority) {
|
||||
return Stream.of(Priority.values())
|
||||
.filter(p -> p.getPriority() == priority)
|
||||
.findFirst()
|
||||
.orElseThrow(IllegalArgumentException::new);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
package com.baeldung.jpa.enums;
|
||||
|
||||
public enum Status {
|
||||
OPEN, REVIEW, APPROVED, REJECTED;
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
package com.baeldung.jpa.enums;
|
||||
|
||||
enum Type {
|
||||
INTERNAL, EXTERNAL;
|
||||
}
|
||||
@@ -0,0 +1,50 @@
|
||||
package com.baeldung.jpa.projections;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.GeneratedValue;
|
||||
import javax.persistence.GenerationType;
|
||||
import javax.persistence.Id;
|
||||
|
||||
@Entity
|
||||
public class Product {
|
||||
@Id
|
||||
private long id;
|
||||
private String name;
|
||||
private String description;
|
||||
private String category;
|
||||
private BigDecimal unitPrice;
|
||||
|
||||
public long getId() {
|
||||
return id;
|
||||
}
|
||||
public void setId(long id) {
|
||||
this.id = id;
|
||||
}
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
public String getDescription() {
|
||||
return description;
|
||||
}
|
||||
public void setDescription(String description) {
|
||||
this.description = description;
|
||||
}
|
||||
public String getCategory() {
|
||||
return category;
|
||||
}
|
||||
public void setCategory(String category) {
|
||||
this.category = category;
|
||||
}
|
||||
public BigDecimal getUnitPrice() {
|
||||
return unitPrice;
|
||||
}
|
||||
public void setUnitPrice(BigDecimal unitPrice) {
|
||||
this.unitPrice = unitPrice;
|
||||
}
|
||||
|
||||
}
|
||||
+93
@@ -0,0 +1,93 @@
|
||||
package com.baeldung.jpa.projections;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import javax.persistence.EntityManager;
|
||||
import javax.persistence.EntityManagerFactory;
|
||||
import javax.persistence.Persistence;
|
||||
import javax.persistence.Query;
|
||||
import javax.persistence.Tuple;
|
||||
import javax.persistence.criteria.CriteriaBuilder;
|
||||
import javax.persistence.criteria.CriteriaQuery;
|
||||
import javax.persistence.criteria.Root;
|
||||
|
||||
public class ProductRepository {
|
||||
private EntityManager entityManager;
|
||||
|
||||
public ProductRepository() {
|
||||
EntityManagerFactory factory = Persistence.createEntityManagerFactory("jpa-projections");
|
||||
entityManager = factory.createEntityManager();
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public List<Object> findAllNamesUsingJPQL() {
|
||||
Query query = entityManager.createQuery("select name from Product");
|
||||
List<Object> resultList = query.getResultList();
|
||||
return resultList;
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public List<Object> findAllIdsUsingJPQL() {
|
||||
Query query = entityManager.createQuery("select id from Product");
|
||||
List<Object> resultList = query.getResultList();
|
||||
return resultList;
|
||||
}
|
||||
|
||||
public List<String> findAllNamesUsingCriteriaBuilder() {
|
||||
CriteriaBuilder builder = entityManager.getCriteriaBuilder();
|
||||
CriteriaQuery<String> query = builder.createQuery(String.class);
|
||||
Root<Product> product = query.from(Product.class);
|
||||
query.select(product.get("name"));
|
||||
List<String> resultList = entityManager.createQuery(query).getResultList();
|
||||
return resultList;
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public List<Object[]> findAllIdAndNamesUsingJPQL() {
|
||||
Query query = entityManager.createQuery("select id, name from Product");
|
||||
List<Object[]> resultList = query.getResultList();
|
||||
return resultList;
|
||||
}
|
||||
|
||||
public List<Object[]> findAllIdAndNamesUsingCriteriaBuilderArray() {
|
||||
CriteriaBuilder builder = entityManager.getCriteriaBuilder();
|
||||
CriteriaQuery<Object[]> query = builder.createQuery(Object[].class);
|
||||
Root<Product> product = query.from(Product.class);
|
||||
query.select(builder.array(product.get("id"), product.get("name")));
|
||||
List<Object[]> resultList = entityManager.createQuery(query).getResultList();
|
||||
return resultList;
|
||||
}
|
||||
|
||||
public List<Object[]> findAllIdNameUnitPriceUsingCriteriaQueryMultiselect() {
|
||||
CriteriaBuilder builder = entityManager.getCriteriaBuilder();
|
||||
CriteriaQuery<Object[]> query = builder.createQuery(Object[].class);
|
||||
Root<Product> product = query.from(Product.class);
|
||||
query.multiselect(product.get("id"), product.get("name"), product.get("unitPrice"));
|
||||
List<Object[]> resultList = entityManager.createQuery(query).getResultList();
|
||||
return resultList;
|
||||
}
|
||||
|
||||
public List<Tuple> findAllIdAndNamesUsingCriteriaBuilderTuple() {
|
||||
CriteriaBuilder builder = entityManager.getCriteriaBuilder();
|
||||
CriteriaQuery<Tuple> query = builder.createQuery(Tuple.class);
|
||||
Root<Product> product = query.from(Product.class);
|
||||
query.select(builder.tuple(product.get("id"), product.get("name")));
|
||||
List<Tuple> resultList = entityManager.createQuery(query).getResultList();
|
||||
return resultList;
|
||||
}
|
||||
|
||||
public List<Object[]> findCountByCategoryUsingJPQL() {
|
||||
Query query = entityManager.createQuery("select p.category, count(p) from Product p group by p.category");
|
||||
return query.getResultList();
|
||||
}
|
||||
|
||||
public List<Object[]> findCountByCategoryUsingCriteriaBuilder() {
|
||||
CriteriaBuilder builder = entityManager.getCriteriaBuilder();
|
||||
CriteriaQuery<Object[]> query = builder.createQuery(Object[].class);
|
||||
Root<Product> product = query.from(Product.class);
|
||||
query.multiselect(product.get("category"), builder.count(product));
|
||||
query.groupBy(product.get("category"));
|
||||
List<Object[]> resultList = entityManager.createQuery(query).getResultList();
|
||||
return resultList;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
package com.baeldung.util;
|
||||
|
||||
public enum Gender {
|
||||
MALE,
|
||||
FEMALE
|
||||
}
|
||||
@@ -1,149 +1,227 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<persistence xmlns="http://xmlns.jcp.org/xml/ns/persistence"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/persistence
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/persistence
|
||||
http://xmlns.jcp.org/xml/ns/persistence/persistence_2_2.xsd"
|
||||
version="2.2">
|
||||
version="2.2">
|
||||
|
||||
<persistence-unit name="java-jpa-scheduled-day">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.sqlresultsetmapping.ScheduledDay</class>
|
||||
<class>com.baeldung.sqlresultsetmapping.Employee</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver" value="org.h2.Driver"/>
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:h2:mem:test;INIT=RUNSCRIPT FROM 'classpath:database.sql'"/>
|
||||
<property name="javax.persistence.jdbc.user" value="sa"/>
|
||||
<property name="javax.persistence.jdbc.password" value=""/>
|
||||
<property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect"/>
|
||||
<!--<property name="hibernate.hbm2ddl.auto" value="create-drop" />-->
|
||||
<property name="show_sql" value="true"/>
|
||||
<property name="hibernate.temp.use_jdbc_metadata_defaults" value="false"/>
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
<persistence-unit name="java-jpa-scheduled-day">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.sqlresultsetmapping.ScheduledDay</class>
|
||||
<class>com.baeldung.sqlresultsetmapping.Employee</class>
|
||||
<class>com.baeldung.jpa.basicannotation.Course</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver"
|
||||
value="org.h2.Driver" />
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:h2:mem:test;INIT=RUNSCRIPT FROM 'classpath:database.sql'" />
|
||||
<property name="javax.persistence.jdbc.user" value="sa" />
|
||||
<property name="javax.persistence.jdbc.password" value="" />
|
||||
<property name="hibernate.dialect"
|
||||
value="org.hibernate.dialect.H2Dialect" />
|
||||
<!--<property name="hibernate.hbm2ddl.auto" value="create-drop" /> -->
|
||||
<property name="show_sql" value="true" />
|
||||
<property name="hibernate.temp.use_jdbc_metadata_defaults"
|
||||
value="false" />
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
|
||||
<persistence-unit name="jpa-h2">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.stringcast.Message</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver" value="org.h2.Driver"/>
|
||||
<property name="javax.persistence.jdbc.url" value="jdbc:h2:mem:test"/>
|
||||
<property name="javax.persistence.jdbc.user" value="sa"/>
|
||||
<property name="javax.persistence.jdbc.password" value=""/>
|
||||
<property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect"/>
|
||||
<property name="hibernate.hbm2ddl.auto" value="create-drop"/>
|
||||
<property name="show_sql" value="true"/>
|
||||
<property name="hibernate.temp.use_jdbc_metadata_defaults" value="false"/>
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
<persistence-unit name="jpa-h2">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.stringcast.Message</class>
|
||||
<class>com.baeldung.jpa.enums.Article</class>
|
||||
<class>com.baeldung.jpa.enums.CategoryConverter</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver"
|
||||
value="org.h2.Driver" />
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:h2:mem:test" />
|
||||
<property name="javax.persistence.jdbc.user" value="sa" />
|
||||
<property name="javax.persistence.jdbc.password" value="" />
|
||||
<property name="hibernate.dialect"
|
||||
value="org.hibernate.dialect.H2Dialect" />
|
||||
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
|
||||
<property name="show_sql" value="true" />
|
||||
<property name="hibernate.temp.use_jdbc_metadata_defaults"
|
||||
value="false" />
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
|
||||
<persistence-unit name="jpa-db">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.model.Car</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver" value="com.mysql.jdbc.Driver"/>
|
||||
<property name="javax.persistence.jdbc.url" value="jdbc:mysql://127.0.0.1:3306/baeldung"/>
|
||||
<property name="javax.persistence.jdbc.user" value="baeldung"/>
|
||||
<property name="javax.persistence.jdbc.password" value="YourPassword"/>
|
||||
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQLDialect"/>
|
||||
<property name="hibernate.show_sql" value="true"/>
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
<persistence-unit name="jpa-db">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.model.Car</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver"
|
||||
value="com.mysql.jdbc.Driver" />
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:mysql://127.0.0.1:3306/baeldung" />
|
||||
<property name="javax.persistence.jdbc.user"
|
||||
value="baeldung" />
|
||||
<property name="javax.persistence.jdbc.password"
|
||||
value="YourPassword" />
|
||||
<property name="hibernate.dialect"
|
||||
value="org.hibernate.dialect.MySQLDialect" />
|
||||
<property name="hibernate.show_sql" value="true" />
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
|
||||
<persistence-unit name="entity-graph-pu" transaction-type="RESOURCE_LOCAL">
|
||||
<class>com.baeldung.jpa.entitygraph.model.Post</class>
|
||||
<class>com.baeldung.jpa.entitygraph.model.User</class>
|
||||
<class>com.baeldung.jpa.entitygraph.model.Comment</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<persistence-unit name="entity-graph-pu"
|
||||
transaction-type="RESOURCE_LOCAL">
|
||||
<class>com.baeldung.jpa.entitygraph.model.Post</class>
|
||||
<class>com.baeldung.jpa.entitygraph.model.User</class>
|
||||
<class>com.baeldung.jpa.entitygraph.model.Comment</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
|
||||
<!--H2-->
|
||||
<property name="javax.persistence.jdbc.driver" value="org.h2.Driver"/>
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:h2:mem:entitygraphdb;DB_CLOSE_DELAY=-1;DB_CLOSE_ON_EXIT=FALSE"/>
|
||||
<!--H2 -->
|
||||
<property name="javax.persistence.jdbc.driver"
|
||||
value="org.h2.Driver" />
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:h2:mem:entitygraphdb;DB_CLOSE_DELAY=-1;DB_CLOSE_ON_EXIT=FALSE" />
|
||||
|
||||
<property name="javax.persistence.schema-generation.database.action" value="drop-and-create"/>
|
||||
<property name="javax.persistence.sql-load-script-source" value="data-init.sql"/>
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
<property
|
||||
name="javax.persistence.schema-generation.database.action"
|
||||
value="drop-and-create" />
|
||||
<property name="javax.persistence.sql-load-script-source"
|
||||
value="data-init.sql" />
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
|
||||
<persistence-unit name="java8-datetime-postgresql" transaction-type="RESOURCE_LOCAL">
|
||||
<provider>org.eclipse.persistence.jpa.PersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.datetime.JPA22DateTimeEntity</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver" value="org.postgresql.Driver"/>
|
||||
<property name="javax.persistence.jdbc.url" value="jdbc:postgresql://localhost:5432/java8-datetime2"/>
|
||||
<property name="javax.persistence.jdbc.user" value="postgres"/>
|
||||
<property name="javax.persistence.jdbc.password" value="postgres"/>
|
||||
<property name="javax.persistence.schema-generation.database.action" value="drop-and-create"/>
|
||||
<persistence-unit name="java8-datetime-postgresql"
|
||||
transaction-type="RESOURCE_LOCAL">
|
||||
<provider>org.eclipse.persistence.jpa.PersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.datetime.JPA22DateTimeEntity</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver"
|
||||
value="org.postgresql.Driver" />
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:postgresql://localhost:5432/java8-datetime2" />
|
||||
<property name="javax.persistence.jdbc.user"
|
||||
value="postgres" />
|
||||
<property name="javax.persistence.jdbc.password"
|
||||
value="postgres" />
|
||||
<property
|
||||
name="javax.persistence.schema-generation.database.action"
|
||||
value="drop-and-create" />
|
||||
|
||||
<!-- configure logging -->
|
||||
<property name="eclipselink.logging.level" value="INFO"/>
|
||||
<property name="eclipselink.logging.level.sql" value="FINE"/>
|
||||
<property name="eclipselink.logging.parameters" value="true"/>
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
<!-- configure logging -->
|
||||
<property name="eclipselink.logging.level" value="INFO" />
|
||||
<property name="eclipselink.logging.level.sql" value="FINE" />
|
||||
<property name="eclipselink.logging.parameters" value="true" />
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
|
||||
<persistence-unit name="jpa-h2-criteria">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.criteria.entity.Item</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver"
|
||||
value="org.h2.Driver" />
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:h2:mem:test" />
|
||||
<property name="javax.persistence.jdbc.user" value="sa" />
|
||||
<property name="javax.persistence.jdbc.password" value="" />
|
||||
<property name="hibernate.dialect"
|
||||
value="org.hibernate.dialect.H2Dialect" />
|
||||
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
|
||||
<property name="show_sql" value="true" />
|
||||
<property name="hibernate.temp.use_jdbc_metadata_defaults"
|
||||
value="false" />
|
||||
<property name="javax.persistence.sql-load-script-source" value="item.sql"/>
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
<persistence-unit name="jpa-h2-criteria">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.criteria.entity.Item</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver"
|
||||
value="org.h2.Driver" />
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:h2:mem:test" />
|
||||
<property name="javax.persistence.jdbc.user" value="sa" />
|
||||
<property name="javax.persistence.jdbc.password" value="" />
|
||||
<property name="hibernate.dialect"
|
||||
value="org.hibernate.dialect.H2Dialect" />
|
||||
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
|
||||
<property name="show_sql" value="true" />
|
||||
<property name="hibernate.temp.use_jdbc_metadata_defaults"
|
||||
value="false" />
|
||||
<property name="javax.persistence.sql-load-script-source"
|
||||
value="item.sql" />
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
|
||||
<persistence-unit name="jpa-query-types">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.querytypes.UserEntity</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver"
|
||||
value="org.h2.Driver" />
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:h2:mem:test" />
|
||||
<property name="javax.persistence.jdbc.user" value="sa" />
|
||||
<property name="javax.persistence.jdbc.password" value="" />
|
||||
<property name="hibernate.dialect"
|
||||
value="org.hibernate.dialect.H2Dialect" />
|
||||
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
|
||||
<property name="show_sql" value="true" />
|
||||
<property name="hibernate.temp.use_jdbc_metadata_defaults"
|
||||
value="false" />
|
||||
<property name="javax.persistence.sql-load-script-source" value="users.sql"/>
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
<persistence-unit name="jpa-query-types">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.querytypes.UserEntity</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver"
|
||||
value="org.h2.Driver" />
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:h2:mem:test" />
|
||||
<property name="javax.persistence.jdbc.user" value="sa" />
|
||||
<property name="javax.persistence.jdbc.password" value="" />
|
||||
<property name="hibernate.dialect"
|
||||
value="org.hibernate.dialect.H2Dialect" />
|
||||
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
|
||||
<property name="show_sql" value="true" />
|
||||
<property name="hibernate.temp.use_jdbc_metadata_defaults"
|
||||
value="false" />
|
||||
<property name="javax.persistence.sql-load-script-source"
|
||||
value="users.sql" />
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
|
||||
<persistence-unit name="entity-default-values">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.defaultvalues.User</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver" value="org.h2.Driver" />
|
||||
<property name="javax.persistence.jdbc.url" value="jdbc:h2:mem:test" />
|
||||
<property name="javax.persistence.jdbc.user" value="sa" />
|
||||
<property name="javax.persistence.jdbc.password" value="" />
|
||||
<property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect" />
|
||||
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
|
||||
<property name="show_sql" value="true" />
|
||||
<property name="hibernate.temp.use_jdbc_metadata_defaults" value="false" />
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
<persistence-unit name="entity-default-values">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.defaultvalues.User</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver"
|
||||
value="org.h2.Driver" />
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:h2:mem:test" />
|
||||
<property name="javax.persistence.jdbc.user" value="sa" />
|
||||
<property name="javax.persistence.jdbc.password" value="" />
|
||||
<property name="hibernate.dialect"
|
||||
value="org.hibernate.dialect.H2Dialect" />
|
||||
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
|
||||
<property name="show_sql" value="true" />
|
||||
<property name="hibernate.temp.use_jdbc_metadata_defaults"
|
||||
value="false" />
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
|
||||
</persistence>
|
||||
<persistence-unit name="jpa-entity-definition">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.entity.Student</class>
|
||||
<class>com.baeldung.jpa.entity.Book</class>
|
||||
<class>com.baeldung.jpa.entity.BookId</class>
|
||||
<class>com.baeldung.jpa.entity.Account</class>
|
||||
<class>com.baeldung.jpa.entity.AccountId</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver"
|
||||
value="org.h2.Driver" />
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:h2:mem:test" />
|
||||
<property name="javax.persistence.jdbc.user" value="sa" />
|
||||
<property name="javax.persistence.jdbc.password" value="" />
|
||||
<property name="hibernate.dialect"
|
||||
value="org.hibernate.dialect.H2Dialect" />
|
||||
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
|
||||
<property name="show_sql" value="true" />
|
||||
<property name="hibernate.temp.use_jdbc_metadata_defaults"
|
||||
value="false" />
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
|
||||
<persistence-unit name="jpa-projections">
|
||||
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
|
||||
<class>com.baeldung.jpa.projections.Product</class>
|
||||
<exclude-unlisted-classes>true</exclude-unlisted-classes>
|
||||
<properties>
|
||||
<property name="javax.persistence.jdbc.driver"
|
||||
value="org.h2.Driver" />
|
||||
<property name="javax.persistence.jdbc.url"
|
||||
value="jdbc:h2:mem:test" />
|
||||
<property name="javax.persistence.jdbc.user" value="sa" />
|
||||
<property name="javax.persistence.jdbc.password" value="" />
|
||||
<property name="hibernate.dialect"
|
||||
value="org.hibernate.dialect.H2Dialect" />
|
||||
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
|
||||
<property name="show_sql" value="true" />
|
||||
<property name="hibernate.temp.use_jdbc_metadata_defaults"
|
||||
value="false" />
|
||||
<property name="javax.persistence.sql-load-script-source"
|
||||
value="products_jpa.sql" />
|
||||
</properties>
|
||||
</persistence-unit>
|
||||
</persistence>
|
||||
@@ -15,3 +15,7 @@ INSERT INTO SCHEDULE_DAYS (employeeId, dayOfWeek) VALUES (1, 'FRIDAY');
|
||||
INSERT INTO SCHEDULE_DAYS (employeeId, dayOfWeek) VALUES (2, 'SATURDAY');
|
||||
INSERT INTO SCHEDULE_DAYS (employeeId, dayOfWeek) VALUES (3, 'MONDAY');
|
||||
INSERT INTO SCHEDULE_DAYS (employeeId, dayOfWeek) VALUES (3, 'FRIDAY');
|
||||
|
||||
CREATE TABLE COURSE
|
||||
(id BIGINT,
|
||||
name VARCHAR(10));
|
||||
@@ -0,0 +1,4 @@
|
||||
insert into product(id, name, description, category) values (1,'Product Name 1','This is Product 1', 'category1');
|
||||
insert into product(id, name, description, category) values (2,'Product Name 2','This is Product 2', 'category1');
|
||||
insert into product(id, name, description, category) values (3,'Product Name 3','This is Product 3', 'category2');
|
||||
insert into product(id, name, description, category) values (4,'Product Name 4','This is Product 4', 'category3');
|
||||
+8
-10
@@ -1,16 +1,13 @@
|
||||
package com.baeldung.jpa.basicannotation;
|
||||
|
||||
import org.hibernate.PropertyValueException;
|
||||
import javax.persistence.EntityManager;
|
||||
import javax.persistence.EntityManagerFactory;
|
||||
import javax.persistence.Persistence;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.AfterClass;
|
||||
import org.junit.Test;
|
||||
import javax.persistence.PersistenceException;
|
||||
|
||||
import java.io.IOException;
|
||||
import org.junit.AfterClass;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Test;
|
||||
|
||||
public class BasicAnnotationIntegrationTest {
|
||||
|
||||
@@ -18,9 +15,10 @@ public class BasicAnnotationIntegrationTest {
|
||||
private static EntityManagerFactory entityManagerFactory;
|
||||
|
||||
@BeforeClass
|
||||
public void setup() {
|
||||
public static void setup() {
|
||||
entityManagerFactory = Persistence.createEntityManagerFactory("java-jpa-scheduled-day");
|
||||
entityManager = entityManagerFactory.createEntityManager();
|
||||
entityManager.getTransaction().begin();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -34,7 +32,7 @@ public class BasicAnnotationIntegrationTest {
|
||||
|
||||
}
|
||||
|
||||
@Test(expected = PropertyValueException.class)
|
||||
@Test(expected = PersistenceException.class)
|
||||
public void givenACourse_whenCourseNameAbsent_shouldFail() {
|
||||
Course course = new Course();
|
||||
|
||||
@@ -44,7 +42,7 @@ public class BasicAnnotationIntegrationTest {
|
||||
}
|
||||
|
||||
@AfterClass
|
||||
public void destroy() {
|
||||
public static void destroy() {
|
||||
|
||||
if (entityManager != null) {
|
||||
entityManager.close();
|
||||
|
||||
+114
@@ -0,0 +1,114 @@
|
||||
package com.baeldung.jpa.entity;
|
||||
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
import javax.persistence.EntityManager;
|
||||
import javax.persistence.EntityManagerFactory;
|
||||
import javax.persistence.Persistence;
|
||||
|
||||
import org.junit.AfterClass;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Test;
|
||||
|
||||
public class CompositeKeysIntegrationTest {
|
||||
|
||||
private static final String SAVINGS_ACCOUNT = "Savings";
|
||||
private static final String ACCOUNT_NUMBER = "JXSDF324234";
|
||||
private static final String ENGLISH = "English";
|
||||
private static final String WAR_AND_PEACE = "War and Peace";
|
||||
|
||||
private static EntityManagerFactory emf;
|
||||
private static EntityManager em;
|
||||
|
||||
@BeforeClass
|
||||
public static void setup() {
|
||||
emf = Persistence.createEntityManagerFactory("jpa-entity-definition");
|
||||
em = emf.createEntityManager();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void persistBookWithCompositeKeyThenRetrieveDetails() {
|
||||
Book warAndPeace = createBook();
|
||||
persist(warAndPeace);
|
||||
clearThePersistenceContext();
|
||||
Book book = findBookByBookId();
|
||||
verifyAssertionsWith(book);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void persistAccountWithCompositeKeyThenRetrieveDetails() {
|
||||
Account savingsAccount = createAccount();
|
||||
persist(savingsAccount);
|
||||
clearThePersistenceContext();
|
||||
Account account = findAccountByAccountId();
|
||||
verifyAssertionsWith(account);
|
||||
}
|
||||
|
||||
@AfterClass
|
||||
public static void destroy() {
|
||||
if (em != null) {
|
||||
em.close();
|
||||
}
|
||||
if (emf != null) {
|
||||
emf.close();
|
||||
}
|
||||
}
|
||||
|
||||
private Account createAccount() {
|
||||
Account savingsAccount = new Account();
|
||||
savingsAccount.setAccountNumber(ACCOUNT_NUMBER);
|
||||
savingsAccount.setAccountType(SAVINGS_ACCOUNT);
|
||||
savingsAccount.setDescription("Savings account");
|
||||
return savingsAccount;
|
||||
}
|
||||
|
||||
private void verifyAssertionsWith(Account account) {
|
||||
assertEquals(ACCOUNT_NUMBER, account.getAccountNumber());
|
||||
assertEquals(SAVINGS_ACCOUNT, account.getAccountType());
|
||||
}
|
||||
|
||||
private Account findAccountByAccountId() {
|
||||
return em.find(Account.class, new AccountId(ACCOUNT_NUMBER, SAVINGS_ACCOUNT));
|
||||
}
|
||||
|
||||
private void persist(Account account) {
|
||||
em.getTransaction()
|
||||
.begin();
|
||||
em.persist(account);
|
||||
em.getTransaction()
|
||||
.commit();
|
||||
}
|
||||
|
||||
private Book findBookByBookId() {
|
||||
return em.find(Book.class, new BookId(WAR_AND_PEACE, ENGLISH));
|
||||
}
|
||||
|
||||
private Book createBook() {
|
||||
BookId bookId = new BookId(WAR_AND_PEACE, ENGLISH);
|
||||
Book warAndPeace = new Book(bookId);
|
||||
warAndPeace.setDescription("Novel and Historical Fiction");
|
||||
return warAndPeace;
|
||||
}
|
||||
|
||||
private void verifyAssertionsWith(Book book) {
|
||||
assertNotNull(book);
|
||||
assertNotNull(book.getBookId());
|
||||
assertEquals(WAR_AND_PEACE, book.getBookId()
|
||||
.getTitle());
|
||||
assertEquals(ENGLISH, book.getBookId()
|
||||
.getLanguage());
|
||||
}
|
||||
|
||||
private void persist(Book book) {
|
||||
em.getTransaction()
|
||||
.begin();
|
||||
em.persist(book);
|
||||
em.getTransaction()
|
||||
.commit();
|
||||
}
|
||||
|
||||
private void clearThePersistenceContext() {
|
||||
em.clear();
|
||||
}
|
||||
}
|
||||
+91
@@ -0,0 +1,91 @@
|
||||
package com.baeldung.jpa.entity;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
|
||||
import java.time.LocalDate;
|
||||
import java.time.ZoneId;
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
|
||||
import javax.persistence.EntityManager;
|
||||
import javax.persistence.EntityManagerFactory;
|
||||
import javax.persistence.Persistence;
|
||||
import javax.persistence.TypedQuery;
|
||||
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
|
||||
import com.baeldung.util.Gender;
|
||||
|
||||
public class StudentEntityIntegrationTest {
|
||||
|
||||
private EntityManagerFactory emf;
|
||||
private EntityManager em;
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
emf = Persistence.createEntityManagerFactory("jpa-entity-definition");
|
||||
em = emf.createEntityManager();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void persistStudentThenRetrieveTheDetails() {
|
||||
Student student = createStudentWithRelevantDetails();
|
||||
persist(student);
|
||||
clearThePersistenceContext();
|
||||
List<Student> students = getStudentsFromTable();
|
||||
checkAssertionsWith(students);
|
||||
}
|
||||
|
||||
@After
|
||||
public void destroy() {
|
||||
if (em != null) {
|
||||
em.close();
|
||||
}
|
||||
if (emf != null) {
|
||||
emf.close();
|
||||
}
|
||||
}
|
||||
|
||||
private void clearThePersistenceContext() {
|
||||
em.clear();
|
||||
}
|
||||
|
||||
private void checkAssertionsWith(List<Student> students) {
|
||||
assertEquals(1, students.size());
|
||||
Student john = students.get(0);
|
||||
assertEquals(1L, john.getId().longValue());
|
||||
assertEquals(null, john.getAge());
|
||||
assertEquals("John", john.getName());
|
||||
}
|
||||
|
||||
private List<Student> getStudentsFromTable() {
|
||||
String selectQuery = "SELECT student FROM Student student";
|
||||
TypedQuery<Student> selectFromStudentTypedQuery = em.createQuery(selectQuery, Student.class);
|
||||
List<Student> students = selectFromStudentTypedQuery.getResultList();
|
||||
return students;
|
||||
}
|
||||
|
||||
private void persist(Student student) {
|
||||
em.getTransaction().begin();
|
||||
em.persist(student);
|
||||
em.getTransaction().commit();
|
||||
}
|
||||
|
||||
private Student createStudentWithRelevantDetails() {
|
||||
Student student = new Student();
|
||||
student.setAge(20); // the 'age' field has been annotated with @Transient
|
||||
student.setName("John");
|
||||
Date date = getDate();
|
||||
student.setBirthDate(date);
|
||||
student.setGender(Gender.MALE);
|
||||
return student;
|
||||
}
|
||||
|
||||
private Date getDate() {
|
||||
LocalDate localDate = LocalDate.of(2008, 7, 20);
|
||||
return Date.from(localDate.atStartOfDay(ZoneId.systemDefault()).toInstant());
|
||||
}
|
||||
|
||||
}
|
||||
+118
@@ -0,0 +1,118 @@
|
||||
package com.baeldung.jpa.enums;
|
||||
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Test;
|
||||
|
||||
import javax.persistence.EntityManager;
|
||||
import javax.persistence.EntityManagerFactory;
|
||||
import javax.persistence.EntityTransaction;
|
||||
import javax.persistence.Persistence;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
public class ArticleUnitTest {
|
||||
|
||||
private static EntityManager em;
|
||||
private static EntityManagerFactory emFactory;
|
||||
|
||||
@BeforeClass
|
||||
public static void setup() {
|
||||
Map properties = new HashMap();
|
||||
properties.put("hibernate.show_sql", "true");
|
||||
properties.put("hibernate.format_sql", "true");
|
||||
emFactory = Persistence.createEntityManagerFactory("jpa-h2", properties);
|
||||
em = emFactory.createEntityManager();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldPersistStatusEnumOrdinalValue() {
|
||||
// given
|
||||
Article article = new Article();
|
||||
article.setId(1);
|
||||
article.setTitle("ordinal title");
|
||||
article.setStatus(Status.OPEN);
|
||||
|
||||
// when
|
||||
EntityTransaction tx = em.getTransaction();
|
||||
tx.begin();
|
||||
em.persist(article);
|
||||
tx.commit();
|
||||
|
||||
// then
|
||||
Article persistedArticle = em.find(Article.class, 1);
|
||||
|
||||
assertEquals(1, persistedArticle.getId());
|
||||
assertEquals("ordinal title", persistedArticle.getTitle());
|
||||
assertEquals(Status.OPEN, persistedArticle.getStatus());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldPersistTypeEnumStringValue() {
|
||||
// given
|
||||
Article article = new Article();
|
||||
article.setId(2);
|
||||
article.setTitle("string title");
|
||||
article.setType(Type.EXTERNAL);
|
||||
|
||||
// when
|
||||
EntityTransaction tx = em.getTransaction();
|
||||
tx.begin();
|
||||
em.persist(article);
|
||||
tx.commit();
|
||||
|
||||
// then
|
||||
Article persistedArticle = em.find(Article.class, 2);
|
||||
|
||||
assertEquals(2, persistedArticle.getId());
|
||||
assertEquals("string title", persistedArticle.getTitle());
|
||||
assertEquals(Type.EXTERNAL, persistedArticle.getType());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldPersistPriorityIntValue() {
|
||||
// given
|
||||
Article article = new Article();
|
||||
article.setId(3);
|
||||
article.setTitle("callback title");
|
||||
article.setPriority(Priority.HIGH);
|
||||
|
||||
// when
|
||||
EntityTransaction tx = em.getTransaction();
|
||||
tx.begin();
|
||||
em.persist(article);
|
||||
tx.commit();
|
||||
|
||||
// then
|
||||
Article persistedArticle = em.find(Article.class, 3);
|
||||
|
||||
assertEquals(3, persistedArticle.getId());
|
||||
assertEquals("callback title", persistedArticle.getTitle());
|
||||
assertEquals(Priority.HIGH, persistedArticle.getPriority());
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldPersistCategoryEnumConvertedValue() {
|
||||
// given
|
||||
Article article = new Article();
|
||||
article.setId(4);
|
||||
article.setTitle("converted title");
|
||||
article.setCategory(Category.MUSIC);
|
||||
|
||||
// when
|
||||
EntityTransaction tx = em.getTransaction();
|
||||
tx.begin();
|
||||
em.persist(article);
|
||||
tx.commit();
|
||||
|
||||
// then
|
||||
Article persistedArticle = em.find(Article.class, 4);
|
||||
|
||||
assertEquals(4, persistedArticle.getId());
|
||||
assertEquals("converted title", persistedArticle.getTitle());
|
||||
assertEquals(Category.MUSIC, persistedArticle.getCategory());
|
||||
}
|
||||
|
||||
}
|
||||
+133
@@ -0,0 +1,133 @@
|
||||
package com.baeldung.jpa.projections;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.hibernate.Criteria;
|
||||
import org.hibernate.Session;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.hibernate.Transaction;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.cfg.Configuration;
|
||||
import org.hibernate.criterion.Order;
|
||||
import org.hibernate.criterion.Projections;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Test;
|
||||
|
||||
public class HibernateProjectionsIntegrationTest {
|
||||
private static Session session;
|
||||
private static SessionFactory sessionFactory;
|
||||
private Transaction transaction;
|
||||
|
||||
@BeforeClass
|
||||
public static void init() {
|
||||
Configuration configuration = getConfiguration();
|
||||
configuration.addAnnotatedClass(Product.class);
|
||||
sessionFactory = configuration.buildSessionFactory();
|
||||
}
|
||||
|
||||
@Before
|
||||
public void before() {
|
||||
session = sessionFactory.getCurrentSession();
|
||||
transaction = session.beginTransaction();
|
||||
}
|
||||
|
||||
@After
|
||||
public void after() {
|
||||
if(transaction.isActive()) {
|
||||
transaction.rollback();
|
||||
}
|
||||
}
|
||||
|
||||
private static Configuration getConfiguration() {
|
||||
Configuration cfg = new Configuration();
|
||||
cfg.setProperty(AvailableSettings.DIALECT,
|
||||
"org.hibernate.dialect.H2Dialect");
|
||||
cfg.setProperty(AvailableSettings.HBM2DDL_AUTO, "none");
|
||||
cfg.setProperty(AvailableSettings.DRIVER, "org.h2.Driver");
|
||||
cfg.setProperty(AvailableSettings.URL,
|
||||
"jdbc:h2:mem:myexceptiondb2;DB_CLOSE_DELAY=-1;;INIT=RUNSCRIPT FROM 'src/test/resources/products.sql'");
|
||||
cfg.setProperty(AvailableSettings.USER, "sa");
|
||||
cfg.setProperty(AvailableSettings.PASS, "");
|
||||
cfg.setProperty(AvailableSettings.CURRENT_SESSION_CONTEXT_CLASS, "thread");
|
||||
return cfg;
|
||||
}
|
||||
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
@Test
|
||||
public void givenProductData_whenIdAndNameProjectionUsingCriteria_thenListOfObjectArrayReturned() {
|
||||
Criteria criteria = session.createCriteria(Product.class);
|
||||
criteria = criteria.setProjection(Projections.projectionList()
|
||||
.add(Projections.id())
|
||||
.add(Projections.property("name")));
|
||||
List<Object[]> resultList = criteria.list();
|
||||
|
||||
assertNotNull(resultList);
|
||||
assertEquals(4, resultList.size());
|
||||
assertEquals(1L, resultList.get(0)[0]);
|
||||
assertEquals("Product Name 1", resultList.get(0)[1]);
|
||||
assertEquals(2L, resultList.get(1)[0]);
|
||||
assertEquals("Product Name 2", resultList.get(1)[1]);
|
||||
assertEquals(3L, resultList.get(2)[0]);
|
||||
assertEquals("Product Name 3", resultList.get(2)[1]);
|
||||
assertEquals(4L, resultList.get(3)[0]);
|
||||
assertEquals("Product Name 4", resultList.get(3)[1]);
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void givenProductData_whenNameProjectionUsingCriteria_thenListOfStringReturned() {
|
||||
Criteria criteria = session.createCriteria(Product.class);
|
||||
criteria = criteria.setProjection(Projections.property("name"));
|
||||
List resultList = criteria.list();
|
||||
|
||||
assertNotNull(resultList);
|
||||
assertEquals(4, resultList.size());
|
||||
assertEquals("Product Name 1", resultList.get(0));
|
||||
assertEquals("Product Name 2", resultList.get(1));
|
||||
assertEquals("Product Name 3", resultList.get(2));
|
||||
assertEquals("Product Name 4", resultList.get(3));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenProductData_whenCountByCategoryUsingCriteria_thenOK() {
|
||||
Criteria criteria = session.createCriteria(Product.class);
|
||||
criteria = criteria.setProjection(Projections.projectionList()
|
||||
.add(Projections.groupProperty("category"))
|
||||
.add(Projections.rowCount()));
|
||||
List<Object[]> resultList = criteria.list();
|
||||
|
||||
assertNotNull(resultList);
|
||||
assertEquals(3, resultList.size());
|
||||
assertEquals("category1", resultList.get(0)[0]);
|
||||
assertEquals(2L, resultList.get(0)[1]);
|
||||
assertEquals("category2", resultList.get(1)[0]);
|
||||
assertEquals(1L, resultList.get(1)[1]);
|
||||
assertEquals("category3", resultList.get(2)[0]);
|
||||
assertEquals(1L, resultList.get(2)[1]);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenProductData_whenCountByCategoryWithAliasUsingCriteria_thenOK() {
|
||||
Criteria criteria = session.createCriteria(Product.class);
|
||||
criteria = criteria.setProjection(Projections.projectionList()
|
||||
.add(Projections.groupProperty("category"))
|
||||
.add(Projections.alias(Projections.rowCount(), "count")));
|
||||
criteria.addOrder(Order.asc("count"));
|
||||
List<Object[]> resultList = criteria.list();
|
||||
|
||||
assertNotNull(resultList);
|
||||
assertEquals(3, resultList.size());
|
||||
assertEquals("category2", resultList.get(0)[0]);
|
||||
assertEquals(1L, resultList.get(0)[1]);
|
||||
assertEquals("category3", resultList.get(1)[0]);
|
||||
assertEquals(1L, resultList.get(1)[1]);
|
||||
assertEquals("category1", resultList.get(2)[0]);
|
||||
assertEquals(2L, resultList.get(2)[1]);
|
||||
}
|
||||
}
|
||||
+105
@@ -0,0 +1,105 @@
|
||||
package com.baeldung.jpa.projections;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.List;
|
||||
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Test;
|
||||
|
||||
|
||||
public class ProductRepositoryIntegrationTest {
|
||||
private static ProductRepository productRepository;
|
||||
|
||||
@BeforeClass
|
||||
public static void once() throws IOException {
|
||||
productRepository = new ProductRepository();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenProductData_whenIdAndNameProjectionUsingJPQL_thenListOfObjectArrayReturned() {
|
||||
List<Object[]> resultList = productRepository.findAllIdAndNamesUsingJPQL();
|
||||
|
||||
assertNotNull(resultList);
|
||||
assertEquals(4, resultList.size());
|
||||
assertEquals(1L, resultList.get(0)[0]);
|
||||
assertEquals("Product Name 1", resultList.get(0)[1]);
|
||||
assertEquals(2L, resultList.get(1)[0]);
|
||||
assertEquals("Product Name 2", resultList.get(1)[1]);
|
||||
assertEquals(3L, resultList.get(2)[0]);
|
||||
assertEquals("Product Name 3", resultList.get(2)[1]);
|
||||
assertEquals(4L, resultList.get(3)[0]);
|
||||
assertEquals("Product Name 4", resultList.get(3)[1]);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenProductData_whenIdAndNameProjectionUsingCriteriaBuilder_thenListOfObjectArrayReturned() {
|
||||
List<Object[]> resultList = productRepository.findAllIdAndNamesUsingCriteriaBuilderArray();
|
||||
|
||||
assertNotNull(resultList);
|
||||
assertEquals(4, resultList.size());
|
||||
assertEquals(1L, resultList.get(0)[0]);
|
||||
assertEquals("Product Name 1", resultList.get(0)[1]);
|
||||
assertEquals(2L, resultList.get(1)[0]);
|
||||
assertEquals("Product Name 2", resultList.get(1)[1]);
|
||||
assertEquals(3L, resultList.get(2)[0]);
|
||||
assertEquals("Product Name 3", resultList.get(2)[1]);
|
||||
assertEquals(4L, resultList.get(3)[0]);
|
||||
assertEquals("Product Name 4", resultList.get(3)[1]);
|
||||
}
|
||||
|
||||
@SuppressWarnings("rawtypes")
|
||||
@Test
|
||||
public void givenProductData_whenNameProjectionUsingJPQL_thenListOfStringReturned() {
|
||||
List resultList = productRepository.findAllNamesUsingJPQL();
|
||||
|
||||
assertNotNull(resultList);
|
||||
assertEquals(4, resultList.size());
|
||||
assertEquals("Product Name 1", resultList.get(0));
|
||||
assertEquals("Product Name 2", resultList.get(1));
|
||||
assertEquals("Product Name 3", resultList.get(2));
|
||||
assertEquals("Product Name 4", resultList.get(3));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenProductData_whenNameProjectionUsingCriteriaBuilder_thenListOfStringReturned() {
|
||||
List<String> resultList = productRepository.findAllNamesUsingCriteriaBuilder();
|
||||
|
||||
assertNotNull(resultList);
|
||||
assertEquals(4, resultList.size());
|
||||
assertEquals("Product Name 1", resultList.get(0));
|
||||
assertEquals("Product Name 2", resultList.get(1));
|
||||
assertEquals("Product Name 3", resultList.get(2));
|
||||
assertEquals("Product Name 4", resultList.get(3));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenProductData_whenCountByCategoryUsingJPQL_thenOK() {
|
||||
List<Object[]> resultList = productRepository.findCountByCategoryUsingJPQL();
|
||||
|
||||
assertNotNull(resultList);
|
||||
assertEquals(3, resultList.size());
|
||||
assertEquals("category1", resultList.get(0)[0]);
|
||||
assertEquals(2L, resultList.get(0)[1]);
|
||||
assertEquals("category2", resultList.get(1)[0]);
|
||||
assertEquals(1L, resultList.get(1)[1]);
|
||||
assertEquals("category3", resultList.get(2)[0]);
|
||||
assertEquals(1L, resultList.get(2)[1]);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenProductData_whenCountByCategoryUsingCriteriaBuider_thenOK() {
|
||||
List<Object[]> resultList = productRepository.findCountByCategoryUsingCriteriaBuilder();
|
||||
|
||||
assertNotNull(resultList);
|
||||
assertEquals(3, resultList.size());
|
||||
assertEquals("category1", resultList.get(0)[0]);
|
||||
assertEquals(2L, resultList.get(0)[1]);
|
||||
assertEquals("category2", resultList.get(1)[0]);
|
||||
assertEquals(1L, resultList.get(1)[1]);
|
||||
assertEquals("category3", resultList.get(2)[0]);
|
||||
assertEquals(1L, resultList.get(2)[1]);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
create table Product (id bigint not null, category varchar(255), description varchar(255), name varchar(255), unitPrice decimal(19,2), primary key (id));
|
||||
insert into product(id, name, description, category) values (1,'Product Name 1','This is Product 1', 'category1');
|
||||
insert into product(id, name, description, category) values (2,'Product Name 2','This is Product 2', 'category1');
|
||||
insert into product(id, name, description, category) values (3,'Product Name 3','This is Product 3', 'category2');
|
||||
insert into product(id, name, description, category) values (4,'Product Name 4','This is Product 4', 'category3');
|
||||
@@ -3,3 +3,4 @@
|
||||
- [A Guide to MongoDB with Java](http://www.baeldung.com/java-mongodb)
|
||||
- [A Simple Tagging Implementation with MongoDB](http://www.baeldung.com/mongodb-tagging)
|
||||
- [MongoDB BSON Guide](https://www.baeldung.com/mongodb-bson)
|
||||
- [Geospatial Support in MongoDB](https://www.baeldung.com/mongodb-geospatial-support)
|
||||
|
||||
+1
-1
@@ -19,7 +19,7 @@ import de.flapdoodle.embedmongo.config.MongodConfig;
|
||||
import de.flapdoodle.embedmongo.distribution.Version;
|
||||
import de.flapdoodle.embedmongo.runtime.Network;
|
||||
|
||||
public class AppIntegrationTest {
|
||||
public class AppLiveTest {
|
||||
|
||||
private static final String DB_NAME = "myMongoDb";
|
||||
private MongodExecutable mongodExe;
|
||||
+110
@@ -0,0 +1,110 @@
|
||||
package com.baeldung.geo;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
import static org.junit.Assert.assertNull;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
import org.bson.Document;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
|
||||
import com.mongodb.MongoClient;
|
||||
import com.mongodb.client.FindIterable;
|
||||
import com.mongodb.client.MongoCollection;
|
||||
import com.mongodb.client.MongoDatabase;
|
||||
import com.mongodb.client.model.Filters;
|
||||
import com.mongodb.client.model.Indexes;
|
||||
import com.mongodb.client.model.geojson.Point;
|
||||
import com.mongodb.client.model.geojson.Polygon;
|
||||
import com.mongodb.client.model.geojson.Position;
|
||||
|
||||
public class MongoGeospatialLiveTest {
|
||||
|
||||
private MongoClient mongoClient;
|
||||
private MongoDatabase db;
|
||||
private MongoCollection<Document> collection;
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
if (mongoClient == null) {
|
||||
mongoClient = new MongoClient();
|
||||
db = mongoClient.getDatabase("myMongoDb");
|
||||
collection = db.getCollection("places");
|
||||
collection.deleteMany(new Document());
|
||||
collection.createIndex(Indexes.geo2dsphere("location"));
|
||||
collection.insertOne(Document.parse("{'name':'Big Ben','location': {'coordinates':[-0.1268194,51.5007292],'type':'Point'}}"));
|
||||
collection.insertOne(Document.parse("{'name':'Hyde Park','location': {'coordinates': [[[-0.159381,51.513126],[-0.189615,51.509928],[-0.187373,51.502442], [-0.153019,51.503464],[-0.159381,51.513126]]],'type':'Polygon'}}"));
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenNearbyLocation_whenSearchNearby_thenFound() {
|
||||
Point currentLoc = new Point(new Position(-0.126821, 51.495885));
|
||||
FindIterable<Document> result = collection.find(Filters.near("location", currentLoc, 1000.0, 10.0));
|
||||
|
||||
assertNotNull(result.first());
|
||||
assertEquals("Big Ben", result.first().get("name"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenFarLocation_whenSearchNearby_thenNotFound() {
|
||||
Point currentLoc = new Point(new Position(-0.5243333, 51.4700223));
|
||||
FindIterable<Document> result = collection.find(Filters.near("location", currentLoc, 5000.0, 10.0));
|
||||
|
||||
assertNull(result.first());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenNearbyLocation_whenSearchWithinCircleSphere_thenFound() {
|
||||
double distanceInRad = 5.0 / 6371;
|
||||
FindIterable<Document> result = collection.find(Filters.geoWithinCenterSphere("location", -0.1435083, 51.4990956, distanceInRad));
|
||||
|
||||
assertNotNull(result.first());
|
||||
assertEquals("Big Ben", result.first().get("name"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenNearbyLocation_whenSearchWithinBox_thenFound() {
|
||||
double lowerLeftX = -0.1427638;
|
||||
double lowerLeftY = 51.4991288;
|
||||
double upperRightX = -0.1256209;
|
||||
double upperRightY = 51.5030272;
|
||||
|
||||
FindIterable<Document> result = collection.find(Filters.geoWithinBox("location", lowerLeftX, lowerLeftY, upperRightX, upperRightY));
|
||||
|
||||
assertNotNull(result.first());
|
||||
assertEquals("Big Ben", result.first().get("name"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenNearbyLocation_whenSearchWithinPolygon_thenFound() {
|
||||
ArrayList<List<Double>> points = new ArrayList<List<Double>>();
|
||||
points.add(Arrays.asList(-0.1439, 51.4952)); // victoria station
|
||||
points.add(Arrays.asList(-0.1121, 51.4989));// Lambeth North
|
||||
points.add(Arrays.asList(-0.13, 51.5163));// Tottenham Court Road
|
||||
points.add(Arrays.asList(-0.1439, 51.4952)); // victoria station
|
||||
FindIterable<Document> result = collection.find(Filters.geoWithinPolygon("location", points));
|
||||
|
||||
assertNotNull(result.first());
|
||||
assertEquals("Big Ben", result.first().get("name"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenNearbyLocation_whenSearchUsingIntersect_thenFound() {
|
||||
ArrayList<Position> positions = new ArrayList<Position>();
|
||||
positions.add(new Position(-0.1439, 51.4952));
|
||||
positions.add(new Position(-0.1346, 51.4978));
|
||||
positions.add(new Position(-0.2177, 51.5135));
|
||||
positions.add(new Position(-0.1439, 51.4952));
|
||||
Polygon geometry = new Polygon(positions);
|
||||
FindIterable<Document> result = collection.find(Filters.geoIntersects("location", geometry));
|
||||
|
||||
assertNotNull(result.first());
|
||||
assertEquals("Hyde Park", result.first().get("name"));
|
||||
}
|
||||
|
||||
}
|
||||
+1
-1
@@ -16,7 +16,7 @@ import org.junit.Test;
|
||||
* @author Donato Rimenti
|
||||
*
|
||||
*/
|
||||
public class TaggingIntegrationTest {
|
||||
public class TaggingLiveTest {
|
||||
|
||||
/**
|
||||
* Object to test.
|
||||
@@ -1,15 +1,14 @@
|
||||
=========
|
||||
|
||||
## Spring Data JPA Example Project
|
||||
|
||||
### Relevant Articles:
|
||||
- [Spring Data JPA – Derived Delete Methods](https://www.baeldung.com/spring-data-jpa-deleteby)
|
||||
- [The Exists Query in Spring Data](https://www.baeldung.com/spring-data-exists-query)
|
||||
- [Case Insensitive Queries with Spring Data Repository](https://www.baeldung.com/spring-data-case-insensitive-queries)
|
||||
- [JPA Join Types](https://www.baeldung.com/jpa-join-types)
|
||||
- [JPA @Embedded And @Embeddable](https://www.baeldung.com/jpa-embedded-embeddable)
|
||||
- [Spring Data JPA Projections](https://www.baeldung.com/spring-data-jpa-projections)
|
||||
- [Spring Data JPA and Null Parameters](https://www.baeldung.com/spring-data-jpa-null-parameters)
|
||||
- [Spring Data JPA Repository Populators](https://www.baeldung.com/spring-data-jpa-repository-populators)
|
||||
- [Spring Data JPA Delete and Relationships](https://www.baeldung.com/spring-data-jpa-delete)
|
||||
- [Derived Query Methods in Spring Data JPA Repositories](https://www.baeldung.com/spring-data-derived-queries)
|
||||
### Relevant Articles:
|
||||
- [Spring Data JPA – Derived Delete Methods](https://www.baeldung.com/spring-data-jpa-deleteby)
|
||||
- [JPA Join Types](https://www.baeldung.com/jpa-join-types)
|
||||
- [Case Insensitive Queries with Spring Data Repository](https://www.baeldung.com/spring-data-case-insensitive-queries)
|
||||
- [The Exists Query in Spring Data](https://www.baeldung.com/spring-data-exists-query)
|
||||
- [Spring Data JPA Repository Populators](https://www.baeldung.com/spring-data-jpa-repository-populators)
|
||||
- [Spring Data JPA and Null Parameters](https://www.baeldung.com/spring-data-jpa-null-parameters)
|
||||
- [Spring Data JPA Projections](https://www.baeldung.com/spring-data-jpa-projections)
|
||||
- [JPA @Embedded And @Embeddable](https://www.baeldung.com/jpa-embedded-embeddable)
|
||||
- [Spring Data JPA Delete and Relationships](https://www.baeldung.com/spring-data-jpa-delete)
|
||||
- [Spring Data JPA and Named Entity Graphs](https://www.baeldung.com/spring-data-jpa-named-entity-graphs)
|
||||
- [Batch Insert/Update with Hibernate/JPA](https://www.baeldung.com/jpa-hibernate-batch-insert-update)
|
||||
- [Difference Between save() and saveAndFlush() in Spring Data JPA](https://www.baeldung.com/spring-data-jpa-save-saveandflush)
|
||||
- [Derived Query Methods in Spring Data JPA Repositories](https://www.baeldung.com/spring-data-derived-queries)
|
||||
|
||||
+58
@@ -0,0 +1,58 @@
|
||||
package com.baeldung.like.model;
|
||||
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.GeneratedValue;
|
||||
import javax.persistence.GenerationType;
|
||||
import javax.persistence.Id;
|
||||
|
||||
@Entity
|
||||
public class Movie {
|
||||
@Id
|
||||
@GeneratedValue(strategy = GenerationType.SEQUENCE)
|
||||
private Long id;
|
||||
private String title;
|
||||
private String director;
|
||||
private String rating;
|
||||
private int duration;
|
||||
|
||||
public Long getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(Long id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public String getTitle() {
|
||||
return title;
|
||||
}
|
||||
|
||||
public void setTitle(String title) {
|
||||
this.title = title;
|
||||
}
|
||||
|
||||
public String getDirector() {
|
||||
return director;
|
||||
}
|
||||
|
||||
public void setDirector(String director) {
|
||||
this.director = director;
|
||||
}
|
||||
|
||||
public String getRating() {
|
||||
return rating;
|
||||
}
|
||||
|
||||
public void setRating(String rating) {
|
||||
this.rating = rating;
|
||||
}
|
||||
|
||||
public int getDuration() {
|
||||
return duration;
|
||||
}
|
||||
|
||||
public void setDuration(int duration) {
|
||||
this.duration = duration;
|
||||
}
|
||||
|
||||
}
|
||||
+41
@@ -0,0 +1,41 @@
|
||||
package com.baeldung.like.repository;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.springframework.data.jpa.repository.Query;
|
||||
import org.springframework.data.repository.CrudRepository;
|
||||
import org.springframework.data.repository.query.Param;
|
||||
|
||||
import com.baeldung.like.model.Movie;
|
||||
|
||||
public interface MovieRepository extends CrudRepository<Movie, Long> {
|
||||
|
||||
List<Movie> findByTitleContaining(String title);
|
||||
|
||||
List<Movie> findByTitleLike(String title);
|
||||
|
||||
List<Movie> findByTitleContains(String title);
|
||||
|
||||
List<Movie> findByTitleIsContaining(String title);
|
||||
|
||||
List<Movie> findByRatingStartsWith(String rating);
|
||||
|
||||
List<Movie> findByDirectorEndsWith(String director);
|
||||
|
||||
List<Movie> findByTitleContainingIgnoreCase(String title);
|
||||
|
||||
List<Movie> findByRatingNotContaining(String rating);
|
||||
|
||||
List<Movie> findByDirectorNotLike(String director);
|
||||
|
||||
@Query("SELECT m FROM Movie m WHERE m.title LIKE %:title%")
|
||||
List<Movie> searchByTitleLike(@Param("title") String title);
|
||||
|
||||
@Query("SELECT m FROM Movie m WHERE m.rating LIKE ?1%")
|
||||
List<Movie> searchByRatingStartsWith(String rating);
|
||||
|
||||
//Escaping works in SpringBoot >= 2.4.1
|
||||
//@Query("SELECT m FROM Movie m WHERE m.director LIKE %?#{escape([0])} escape ?#{escapeCharacter()}")
|
||||
@Query("SELECT m FROM Movie m WHERE m.director LIKE %:#{[0]}")
|
||||
List<Movie> searchByDirectorEndsWith(String director);
|
||||
}
|
||||
+5
-5
@@ -43,22 +43,22 @@ public class DeleteFromRepositoryUnitTest {
|
||||
public void whenDeleteByIdFromRepository_thenDeletingShouldBeSuccessful() {
|
||||
repository.deleteById(book1.getId());
|
||||
|
||||
assertThat(repository.count() == 1).isTrue();
|
||||
assertThat(repository.count()).isEqualTo(1);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenDeleteAllFromRepository_thenRepositoryShouldBeEmpty() {
|
||||
repository.deleteAll();
|
||||
|
||||
assertThat(repository.count() == 0).isTrue();
|
||||
assertThat(repository.count()).isEqualTo(0);
|
||||
}
|
||||
|
||||
@Test
|
||||
@Transactional
|
||||
public void whenDeleteFromDerivedQuery_thenDeletingShouldBeSuccessful() {
|
||||
repository.deleteByTitle("The Hobbit");
|
||||
long deletedRecords = repository.deleteByTitle("The Hobbit");
|
||||
|
||||
assertThat(repository.count() == 1).isTrue();
|
||||
assertThat(deletedRecords).isEqualTo(1);
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -66,7 +66,7 @@ public class DeleteFromRepositoryUnitTest {
|
||||
public void whenDeleteFromCustomQuery_thenDeletingShouldBeSuccessful() {
|
||||
repository.deleteBooks("The Hobbit");
|
||||
|
||||
assertThat(repository.count() == 1).isTrue();
|
||||
assertThat(repository.count()).isEqualTo(1);
|
||||
}
|
||||
|
||||
}
|
||||
+4
-4
@@ -46,15 +46,15 @@ public class DeleteInRelationshipsUnitTest {
|
||||
public void whenDeletingCategories_thenBooksShouldAlsoBeDeleted() {
|
||||
categoryRepository.deleteAll();
|
||||
|
||||
assertThat(bookRepository.count() == 0).isTrue();
|
||||
assertThat(categoryRepository.count() == 0).isTrue();
|
||||
assertThat(bookRepository.count()).isEqualTo(0);
|
||||
assertThat(categoryRepository.count()).isEqualTo(0);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenDeletingBooks_thenCategoriesShouldAlsoBeDeleted() {
|
||||
bookRepository.deleteAll();
|
||||
|
||||
assertThat(bookRepository.count() == 0).isTrue();
|
||||
assertThat(categoryRepository.count() == 2).isTrue();
|
||||
assertThat(bookRepository.count()).isEqualTo(0);
|
||||
assertThat(categoryRepository.count()).isEqualTo(2);
|
||||
}
|
||||
}
|
||||
+88
@@ -0,0 +1,88 @@
|
||||
package com.baeldung.like;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.springframework.test.context.jdbc.Sql.ExecutionPhase.AFTER_TEST_METHOD;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.test.context.SpringBootTest;
|
||||
import org.springframework.test.context.jdbc.Sql;
|
||||
import org.springframework.test.context.junit4.SpringRunner;
|
||||
|
||||
import com.baeldung.like.model.Movie;
|
||||
import com.baeldung.like.repository.MovieRepository;
|
||||
|
||||
@RunWith(SpringRunner.class)
|
||||
@SpringBootTest
|
||||
@Sql(scripts = { "/test-movie-data.sql" })
|
||||
@Sql(scripts = "/test-movie-cleanup.sql", executionPhase = AFTER_TEST_METHOD)
|
||||
public class MovieRepositoryIntegrationTest {
|
||||
@Autowired
|
||||
private MovieRepository movieRepository;
|
||||
|
||||
@Test
|
||||
public void givenPartialTitle_WhenFindByTitleContaining_ThenMoviesShouldReturn() {
|
||||
List<Movie> results = movieRepository.findByTitleContaining("in");
|
||||
assertEquals(3, results.size());
|
||||
|
||||
results = movieRepository.findByTitleLike("%in%");
|
||||
assertEquals(3, results.size());
|
||||
|
||||
results = movieRepository.findByTitleIsContaining("in");
|
||||
assertEquals(3, results.size());
|
||||
|
||||
results = movieRepository.findByTitleContains("in");
|
||||
assertEquals(3, results.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenStartOfRating_WhenFindByRatingStartsWith_ThenMoviesShouldReturn() {
|
||||
List<Movie> results = movieRepository.findByRatingStartsWith("PG");
|
||||
assertEquals(6, results.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenLastName_WhenFindByDirectorEndsWith_ThenMoviesShouldReturn() {
|
||||
List<Movie> results = movieRepository.findByDirectorEndsWith("Burton");
|
||||
assertEquals(1, results.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenPartialTitle_WhenFindByTitleContainingIgnoreCase_ThenMoviesShouldReturn() {
|
||||
List<Movie> results = movieRepository.findByTitleContainingIgnoreCase("the");
|
||||
assertEquals(2, results.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenPartialTitle_WhenSearchByTitleLike_ThenMoviesShouldReturn() {
|
||||
List<Movie> results = movieRepository.searchByTitleLike("in");
|
||||
assertEquals(3, results.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenStartOfRating_SearchFindByRatingStartsWith_ThenMoviesShouldReturn() {
|
||||
List<Movie> results = movieRepository.searchByRatingStartsWith("PG");
|
||||
assertEquals(6, results.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenLastName_WhenSearchByDirectorEndsWith_ThenMoviesShouldReturn() {
|
||||
List<Movie> results = movieRepository.searchByDirectorEndsWith("Burton");
|
||||
assertEquals(1, results.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenPartialRating_findByRatingNotContaining_ThenMoviesShouldReturn() {
|
||||
List<Movie> results = movieRepository.findByRatingNotContaining("PG");
|
||||
assertEquals(1, results.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void givenPartialDirector_WhenFindByDirectorNotLike_ThenMoviesShouldReturn() {
|
||||
List<Movie> results = movieRepository.findByDirectorNotLike("An%");
|
||||
assertEquals(5, results.size());
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
DELETE FROM Movie;
|
||||
@@ -0,0 +1,7 @@
|
||||
INSERT INTO movie(id, title, director, rating, duration) VALUES(1, 'Godzilla: King of the Monsters', ' Michael Dougherty', 'PG-13', 132);
|
||||
INSERT INTO movie(id, title, director, rating, duration) VALUES(2, 'Avengers: Endgame', 'Anthony Russo', 'PG-13', 181);
|
||||
INSERT INTO movie(id, title, director, rating, duration) VALUES(3, 'Captain Marvel', 'Anna Boden', 'PG-13', 123);
|
||||
INSERT INTO movie(id, title, director, rating, duration) VALUES(4, 'Dumbo', 'Tim Burton', 'PG', 112);
|
||||
INSERT INTO movie(id, title, director, rating, duration) VALUES(5, 'Booksmart', 'Olivia Wilde', 'R', 102);
|
||||
INSERT INTO movie(id, title, director, rating, duration) VALUES(6, 'Aladdin', 'Guy Ritchie', 'PG', 128);
|
||||
INSERT INTO movie(id, title, director, rating, duration) VALUES(7, 'The Sun Is Also a Star', 'Ry Russo-Young', 'PG-13', 100);
|
||||
@@ -6,7 +6,6 @@
|
||||
- [Spring JPA – Multiple Databases](http://www.baeldung.com/spring-data-jpa-multiple-databases)
|
||||
- [Spring Data JPA – Adding a Method in All Repositories](http://www.baeldung.com/spring-data-jpa-method-in-all-repositories)
|
||||
- [An Advanced Tagging Implementation with JPA](http://www.baeldung.com/jpa-tagging-advanced)
|
||||
- [Spring Data JPA @Query](http://www.baeldung.com/spring-data-jpa-query)
|
||||
- [Spring Data Annotations](http://www.baeldung.com/spring-data-annotations)
|
||||
- [Spring Data Java 8 Support](http://www.baeldung.com/spring-data-java-8)
|
||||
- [A Simple Tagging Implementation with JPA](http://www.baeldung.com/jpa-tagging)
|
||||
|
||||
+1
-1
@@ -94,6 +94,6 @@ public interface UserRepository extends JpaRepository<User, Integer> , UserRepos
|
||||
int deleteDeactivatedUsers();
|
||||
|
||||
@Modifying(clearAutomatically = true, flushAutomatically = true)
|
||||
@Query(value = "alter table USERS.USERS add column deleted int(1) not null default 0", nativeQuery = true)
|
||||
@Query(value = "alter table USERS add column deleted int(1) not null default 0", nativeQuery = true)
|
||||
void addDeletedColumn();
|
||||
}
|
||||
|
||||
+1
-1
@@ -9,6 +9,6 @@ public class MultipleDbApplication {
|
||||
public static void main(String[] args) {
|
||||
SpringApplication.run(MultipleDbApplication.class, args);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
+71
@@ -0,0 +1,71 @@
|
||||
package com.baeldung.multipledb;
|
||||
|
||||
import java.util.HashMap;
|
||||
|
||||
import javax.sql.DataSource;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
import org.springframework.boot.jdbc.DataSourceBuilder;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.Profile;
|
||||
import org.springframework.context.annotation.PropertySource;
|
||||
import org.springframework.core.env.Environment;
|
||||
import org.springframework.data.jpa.repository.config.EnableJpaRepositories;
|
||||
import org.springframework.orm.jpa.JpaTransactionManager;
|
||||
import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean;
|
||||
import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter;
|
||||
import org.springframework.transaction.PlatformTransactionManager;
|
||||
|
||||
/**
|
||||
* By default, the persistence-multiple-db.properties file is read for
|
||||
* non auto configuration in PersistenceProductConfiguration.
|
||||
* <p>
|
||||
* If we need to use persistence-multiple-db-boot.properties and auto configuration
|
||||
* then uncomment the below @Configuration class and comment out PersistenceProductConfiguration.
|
||||
*/
|
||||
//@Configuration
|
||||
@PropertySource({"classpath:persistence-multiple-db-boot.properties"})
|
||||
@EnableJpaRepositories(basePackages = "com.baeldung.multipledb.dao.product", entityManagerFactoryRef = "productEntityManager", transactionManagerRef = "productTransactionManager")
|
||||
@Profile("!tc")
|
||||
public class PersistenceProductAutoConfiguration {
|
||||
@Autowired
|
||||
private Environment env;
|
||||
|
||||
public PersistenceProductAutoConfiguration() {
|
||||
super();
|
||||
}
|
||||
|
||||
//
|
||||
|
||||
@Bean
|
||||
public LocalContainerEntityManagerFactoryBean productEntityManager() {
|
||||
final LocalContainerEntityManagerFactoryBean em = new LocalContainerEntityManagerFactoryBean();
|
||||
em.setDataSource(productDataSource());
|
||||
em.setPackagesToScan("com.baeldung.multipledb.model.product");
|
||||
|
||||
final HibernateJpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();
|
||||
em.setJpaVendorAdapter(vendorAdapter);
|
||||
final HashMap<String, Object> properties = new HashMap<String, Object>();
|
||||
properties.put("hibernate.hbm2ddl.auto", env.getProperty("hibernate.hbm2ddl.auto"));
|
||||
properties.put("hibernate.dialect", env.getProperty("hibernate.dialect"));
|
||||
em.setJpaPropertyMap(properties);
|
||||
|
||||
return em;
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConfigurationProperties(prefix="spring.second-datasource")
|
||||
public DataSource productDataSource() {
|
||||
return DataSourceBuilder.create().build();
|
||||
}
|
||||
|
||||
@Bean
|
||||
public PlatformTransactionManager productTransactionManager() {
|
||||
final JpaTransactionManager transactionManager = new JpaTransactionManager();
|
||||
transactionManager.setEntityManagerFactory(productEntityManager().getObject());
|
||||
return transactionManager;
|
||||
}
|
||||
|
||||
}
|
||||
+75
@@ -0,0 +1,75 @@
|
||||
package com.baeldung.multipledb;
|
||||
|
||||
import java.util.HashMap;
|
||||
|
||||
import javax.sql.DataSource;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
import org.springframework.boot.jdbc.DataSourceBuilder;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.Primary;
|
||||
import org.springframework.context.annotation.Profile;
|
||||
import org.springframework.context.annotation.PropertySource;
|
||||
import org.springframework.core.env.Environment;
|
||||
import org.springframework.data.jpa.repository.config.EnableJpaRepositories;
|
||||
import org.springframework.orm.jpa.JpaTransactionManager;
|
||||
import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean;
|
||||
import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter;
|
||||
import org.springframework.transaction.PlatformTransactionManager;
|
||||
|
||||
/**
|
||||
* By default, the persistence-multiple-db.properties file is read for
|
||||
* non auto configuration in PersistenceUserConfiguration.
|
||||
* <p>
|
||||
* If we need to use persistence-multiple-db-boot.properties and auto configuration
|
||||
* then uncomment the below @Configuration class and comment out PersistenceUserConfiguration.
|
||||
*/
|
||||
//@Configuration
|
||||
@PropertySource({"classpath:persistence-multiple-db-boot.properties"})
|
||||
@EnableJpaRepositories(basePackages = "com.baeldung.multipledb.dao.user", entityManagerFactoryRef = "userEntityManager", transactionManagerRef = "userTransactionManager")
|
||||
@Profile("!tc")
|
||||
public class PersistenceUserAutoConfiguration {
|
||||
@Autowired
|
||||
private Environment env;
|
||||
|
||||
public PersistenceUserAutoConfiguration() {
|
||||
super();
|
||||
}
|
||||
|
||||
//
|
||||
|
||||
@Primary
|
||||
@Bean
|
||||
public LocalContainerEntityManagerFactoryBean userEntityManager() {
|
||||
final LocalContainerEntityManagerFactoryBean em = new LocalContainerEntityManagerFactoryBean();
|
||||
em.setDataSource(userDataSource());
|
||||
em.setPackagesToScan("com.baeldung.multipledb.model.user");
|
||||
|
||||
final HibernateJpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();
|
||||
em.setJpaVendorAdapter(vendorAdapter);
|
||||
final HashMap<String, Object> properties = new HashMap<String, Object>();
|
||||
properties.put("hibernate.hbm2ddl.auto", env.getProperty("hibernate.hbm2ddl.auto"));
|
||||
properties.put("hibernate.dialect", env.getProperty("hibernate.dialect"));
|
||||
em.setJpaPropertyMap(properties);
|
||||
|
||||
return em;
|
||||
}
|
||||
|
||||
@Bean
|
||||
@Primary
|
||||
@ConfigurationProperties(prefix="spring.datasource")
|
||||
public DataSource userDataSource() {
|
||||
return DataSourceBuilder.create().build();
|
||||
}
|
||||
|
||||
@Primary
|
||||
@Bean
|
||||
public PlatformTransactionManager userTransactionManager() {
|
||||
final JpaTransactionManager transactionManager = new JpaTransactionManager();
|
||||
transactionManager.setEntityManagerFactory(userEntityManager().getObject());
|
||||
return transactionManager;
|
||||
}
|
||||
|
||||
}
|
||||
+11
@@ -0,0 +1,11 @@
|
||||
hibernate.hbm2ddl.auto=create-drop
|
||||
hibernate.cache.use_second_level_cache=false
|
||||
hibernate.cache.use_query_cache=false
|
||||
|
||||
spring.datasource.jdbcUrl=jdbc:h2:mem:spring_jpa_user;DB_CLOSE_DELAY=-1;INIT=CREATE SCHEMA IF NOT EXISTS USERS
|
||||
spring.datasource.username=sa
|
||||
spring.datasource.password=sa
|
||||
|
||||
spring.second-datasource.jdbcUrl=jdbc:h2:mem:spring_jpa_product;DB_CLOSE_DELAY=-1;INIT=CREATE SCHEMA IF NOT EXISTS PRODUCTS
|
||||
spring.second-datasource.username=sa
|
||||
spring.second-datasource.password=sa
|
||||
+5
-5
@@ -23,7 +23,7 @@ import java.util.stream.Stream;
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.junit.Assert.*;
|
||||
|
||||
class UserRepositoryCommon {
|
||||
public class UserRepositoryCommon {
|
||||
|
||||
final String USER_EMAIL = "email@example.com";
|
||||
final String USER_EMAIL2 = "email2@example.com";
|
||||
@@ -280,7 +280,7 @@ class UserRepositoryCommon {
|
||||
|
||||
userRepository.findAll(new Sort(Sort.Direction.ASC, "name"));
|
||||
|
||||
List<User> usersSortByNameLength = userRepository.findAll(new Sort("LENGTH(name)"));
|
||||
List<User> usersSortByNameLength = userRepository.findAll(Sort.by("LENGTH(name)"));
|
||||
|
||||
assertThat(usersSortByNameLength.get(0)
|
||||
.getName()).isEqualTo(USER_NAME_ADAM);
|
||||
@@ -292,7 +292,7 @@ class UserRepositoryCommon {
|
||||
userRepository.save(new User(USER_NAME_PETER, LocalDate.now(), USER_EMAIL2, ACTIVE_STATUS));
|
||||
userRepository.save(new User("SAMPLE", LocalDate.now(), USER_EMAIL3, INACTIVE_STATUS));
|
||||
|
||||
userRepository.findAllUsers(new Sort("name"));
|
||||
userRepository.findAllUsers(Sort.by("name"));
|
||||
|
||||
List<User> usersSortByNameLength = userRepository.findAllUsers(JpaSort.unsafe("LENGTH(name)"));
|
||||
|
||||
@@ -309,7 +309,7 @@ class UserRepositoryCommon {
|
||||
userRepository.save(new User("SAMPLE2", LocalDate.now(), USER_EMAIL5, INACTIVE_STATUS));
|
||||
userRepository.save(new User("SAMPLE3", LocalDate.now(), USER_EMAIL6, INACTIVE_STATUS));
|
||||
|
||||
Page<User> usersPage = userRepository.findAllUsersWithPagination(new PageRequest(1, 3));
|
||||
Page<User> usersPage = userRepository.findAllUsersWithPagination(PageRequest.of(1, 3));
|
||||
|
||||
assertThat(usersPage.getContent()
|
||||
.get(0)
|
||||
@@ -325,7 +325,7 @@ class UserRepositoryCommon {
|
||||
userRepository.save(new User("SAMPLE2", LocalDate.now(), USER_EMAIL5, INACTIVE_STATUS));
|
||||
userRepository.save(new User("SAMPLE3", LocalDate.now(), USER_EMAIL6, INACTIVE_STATUS));
|
||||
|
||||
Page<User> usersSortByNameLength = userRepository.findAllUsersWithPaginationNative(new PageRequest(1, 3));
|
||||
Page<User> usersSortByNameLength = userRepository.findAllUsersWithPaginationNative(PageRequest.of(1, 3));
|
||||
|
||||
assertThat(usersSortByNameLength.getContent()
|
||||
.get(0)
|
||||
|
||||
+1
-1
@@ -22,7 +22,7 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
@RunWith(SpringRunner.class)
|
||||
@SpringBootTest(classes = Application.class)
|
||||
@ActiveProfiles({"tc", "tc-auto"})
|
||||
public class UserRepositoryTCAutoIntegrationTest extends UserRepositoryCommon {
|
||||
public class UserRepositoryTCAutoLiveTest extends UserRepositoryCommon {
|
||||
|
||||
@ClassRule
|
||||
public static PostgreSQLContainer postgreSQLContainer = BaeldungPostgresqlContainer.getInstance();
|
||||
+2
-2
@@ -22,8 +22,8 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
@RunWith(SpringRunner.class)
|
||||
@SpringBootTest(classes = Application.class)
|
||||
@ActiveProfiles("tc")
|
||||
@ContextConfiguration(initializers = {UserRepositoryTCIntegrationTest.Initializer.class})
|
||||
public class UserRepositoryTCIntegrationTest extends UserRepositoryCommon {
|
||||
@ContextConfiguration(initializers = {UserRepositoryTCLiveTest.Initializer.class})
|
||||
public class UserRepositoryTCLiveTest extends UserRepositoryCommon {
|
||||
|
||||
@ClassRule
|
||||
public static PostgreSQLContainer postgreSQLContainer = new PostgreSQLContainer("postgres:11.1")
|
||||
-1
@@ -12,7 +12,6 @@ import org.junit.runner.RunWith;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.test.context.SpringBootTest;
|
||||
import org.springframework.dao.DataIntegrityViolationException;
|
||||
import org.springframework.test.annotation.DirtiesContext;
|
||||
import org.springframework.test.context.junit4.SpringRunner;
|
||||
import org.springframework.transaction.annotation.EnableTransactionManagement;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
@@ -3,3 +3,4 @@
|
||||
- [Hibernate Many to Many Annotation Tutorial](http://www.baeldung.com/hibernate-many-to-many)
|
||||
- [Programmatic Transactions in the Spring TestContext Framework](http://www.baeldung.com/spring-test-programmatic-transactions)
|
||||
- [JPA Criteria Queries](http://www.baeldung.com/hibernate-criteria-queries)
|
||||
- [Introduction to Hibernate Search](http://www.baeldung.com/hibernate-search)
|
||||
|
||||
+2
-2
@@ -3,7 +3,7 @@ package com.baeldung.hibernate.criteria;
|
||||
import static org.junit.Assert.assertArrayEquals;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
|
||||
import static org.junit.Assert.assertFalse;
|
||||
import java.util.List;
|
||||
|
||||
import org.hibernate.Session;
|
||||
@@ -25,7 +25,7 @@ public class HibernateCriteriaIntegrationTest {
|
||||
|
||||
@Test
|
||||
public void testPerformanceOfCriteria() {
|
||||
assertTrue(av.checkIfCriteriaTimeLower());
|
||||
assertFalse(av.checkIfCriteriaTimeLower());
|
||||
}
|
||||
|
||||
@Test
|
||||
|
||||
@@ -4,7 +4,6 @@
|
||||
|
||||
### Relevant Articles:
|
||||
- [Guide to Hibernate 4 with Spring](http://www.baeldung.com/hibernate-4-spring)
|
||||
- [The DAO with Spring and Hibernate](http://www.baeldung.com/persistence-layer-with-spring-and-hibernate)
|
||||
- [Hibernate Pagination](http://www.baeldung.com/hibernate-pagination)
|
||||
- [Sorting with Hibernate](http://www.baeldung.com/hibernate-sort)
|
||||
- [Stored Procedures with Hibernate](http://www.baeldung.com/stored-procedures-with-hibernate-tutorial)
|
||||
|
||||
@@ -4,7 +4,6 @@
|
||||
|
||||
|
||||
### Relevant Articles:
|
||||
- [Transactions with Spring and JPA](https://www.baeldung.com/transaction-configuration-with-jpa-and-spring)
|
||||
- [The DAO with JPA and Spring](http://www.baeldung.com/spring-dao-jpa)
|
||||
- [JPA Pagination](http://www.baeldung.com/jpa-pagination)
|
||||
- [Sorting with JPA](http://www.baeldung.com/jpa-sort)
|
||||
|
||||
@@ -5,7 +5,13 @@
|
||||
|
||||
### Relevant Articles:
|
||||
- [A Guide to JPA with Spring](https://www.baeldung.com/the-persistence-layer-with-spring-and-jpa)
|
||||
|
||||
- [Bootstrapping Hibernate 5 with Spring](http://www.baeldung.com/hibernate-5-spring)
|
||||
- [The DAO with Spring and Hibernate](http://www.baeldung.com/persistence-layer-with-spring-and-hibernate)
|
||||
- [Simplify the DAO with Spring and Java Generics](https://www.baeldung.com/simplifying-the-data-access-layer-with-spring-and-java-generics)
|
||||
- [Transactions with Spring and JPA](https://www.baeldung.com/transaction-configuration-with-jpa-and-spring)
|
||||
- [Introduction to Spring Data JPA](http://www.baeldung.com/the-persistence-layer-with-spring-data-jpa)
|
||||
- [Spring Data JPA @Query](http://www.baeldung.com/spring-data-jpa-query)
|
||||
- [Spring JDBC](https://www.baeldung.com/spring-jdbc-jdbctemplate)
|
||||
|
||||
### Eclipse Config
|
||||
After importing the project into Eclipse, you may see the following error:
|
||||
|
||||
@@ -18,12 +18,6 @@
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-orm</artifactId>
|
||||
<version>${org.springframework.version}</version>
|
||||
<exclusions>
|
||||
<exclusion>
|
||||
<artifactId>commons-logging</artifactId>
|
||||
<groupId>commons-logging</groupId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
@@ -32,7 +26,16 @@
|
||||
</dependency>
|
||||
|
||||
<!-- persistence -->
|
||||
|
||||
<dependency>
|
||||
<groupId>org.hibernate</groupId>
|
||||
<artifactId>hibernate-core</artifactId>
|
||||
<version>${hibernate.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>javax.transaction</groupId>
|
||||
<artifactId>jta</artifactId>
|
||||
<version>${jta.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.hibernate</groupId>
|
||||
<artifactId>hibernate-entitymanager</artifactId>
|
||||
@@ -55,6 +58,12 @@
|
||||
<version>${h2.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.tomcat</groupId>
|
||||
<artifactId>tomcat-dbcp</artifactId>
|
||||
<version>${tomcat-dbcp.version}</version>
|
||||
</dependency>
|
||||
|
||||
<!-- utils -->
|
||||
|
||||
<dependency>
|
||||
@@ -83,7 +92,16 @@
|
||||
<version>${org.springframework.version}</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.querydsl</groupId>
|
||||
<artifactId>querydsl-jpa</artifactId>
|
||||
<version>${querydsl.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.querydsl</groupId>
|
||||
<artifactId>querydsl-apt</artifactId>
|
||||
<version>${querydsl.version}</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
<build>
|
||||
@@ -94,6 +112,25 @@
|
||||
<filtering>true</filtering>
|
||||
</resource>
|
||||
</resources>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>com.mysema.maven</groupId>
|
||||
<artifactId>apt-maven-plugin</artifactId>
|
||||
<version>1.1.3</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<phase>generate-sources</phase>
|
||||
<goals>
|
||||
<goal>process</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<outputDirectory>target/generated-sources</outputDirectory>
|
||||
<processor>com.querydsl.apt.jpa.JPAAnnotationProcessor</processor>
|
||||
</configuration>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
<properties>
|
||||
@@ -104,6 +141,9 @@
|
||||
<hibernate.version>5.4.2.Final</hibernate.version>
|
||||
<mysql-connector-java.version>6.0.6</mysql-connector-java.version>
|
||||
<spring-data-jpa.version>2.1.6.RELEASE</spring-data-jpa.version>
|
||||
<tomcat-dbcp.version>9.0.0.M26</tomcat-dbcp.version>
|
||||
<jta.version>1.1</jta.version>
|
||||
<querydsl.version>4.2.1</querydsl.version>
|
||||
|
||||
<!-- util -->
|
||||
<guava.version>21.0</guava.version>
|
||||
|
||||
+118
@@ -0,0 +1,118 @@
|
||||
package com.baeldung.config;
|
||||
|
||||
import java.util.Properties;
|
||||
|
||||
import javax.sql.DataSource;
|
||||
|
||||
import org.apache.tomcat.dbcp.dbcp2.BasicDataSource;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.ComponentScan;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.PropertySource;
|
||||
import org.springframework.core.env.Environment;
|
||||
import org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor;
|
||||
import org.springframework.data.jpa.repository.config.EnableJpaAuditing;
|
||||
import org.springframework.data.jpa.repository.config.EnableJpaRepositories;
|
||||
import org.springframework.orm.hibernate5.HibernateTransactionManager;
|
||||
import org.springframework.orm.hibernate5.LocalSessionFactoryBean;
|
||||
import org.springframework.orm.jpa.JpaTransactionManager;
|
||||
import org.springframework.orm.jpa.JpaVendorAdapter;
|
||||
import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean;
|
||||
import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter;
|
||||
import org.springframework.transaction.PlatformTransactionManager;
|
||||
import org.springframework.transaction.annotation.EnableTransactionManagement;
|
||||
|
||||
import com.baeldung.hibernate.dao.FooDao;
|
||||
import com.baeldung.jpa.dao.IFooDao;
|
||||
import com.google.common.base.Preconditions;
|
||||
|
||||
@Configuration
|
||||
@EnableTransactionManagement
|
||||
@EnableJpaRepositories(basePackages = { "com.baeldung.hibernate.dao" }, transactionManagerRef = "jpaTransactionManager")
|
||||
@EnableJpaAuditing
|
||||
@PropertySource({ "classpath:persistence-mysql.properties" })
|
||||
@ComponentScan({ "com.baeldung.persistence", "com.baeldung.hibernate.dao" })
|
||||
public class PersistenceConfig {
|
||||
|
||||
@Autowired
|
||||
private Environment env;
|
||||
|
||||
public PersistenceConfig() {
|
||||
super();
|
||||
}
|
||||
|
||||
@Bean
|
||||
public LocalSessionFactoryBean sessionFactory() {
|
||||
final LocalSessionFactoryBean sessionFactory = new LocalSessionFactoryBean();
|
||||
sessionFactory.setDataSource(restDataSource());
|
||||
sessionFactory.setPackagesToScan(new String[] { "com.baeldung.persistence.model" });
|
||||
sessionFactory.setHibernateProperties(hibernateProperties());
|
||||
|
||||
return sessionFactory;
|
||||
}
|
||||
|
||||
@Bean
|
||||
public LocalContainerEntityManagerFactoryBean entityManagerFactory() {
|
||||
final LocalContainerEntityManagerFactoryBean emf = new LocalContainerEntityManagerFactoryBean();
|
||||
emf.setDataSource(restDataSource());
|
||||
emf.setPackagesToScan(new String[] { "com.baeldung.persistence.model" });
|
||||
|
||||
final JpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();
|
||||
emf.setJpaVendorAdapter(vendorAdapter);
|
||||
emf.setJpaProperties(hibernateProperties());
|
||||
|
||||
return emf;
|
||||
}
|
||||
|
||||
@Bean
|
||||
public DataSource restDataSource() {
|
||||
final BasicDataSource dataSource = new BasicDataSource();
|
||||
dataSource.setDriverClassName(Preconditions.checkNotNull(env.getProperty("jdbc.driverClassName")));
|
||||
dataSource.setUrl(Preconditions.checkNotNull(env.getProperty("jdbc.url")));
|
||||
dataSource.setUsername(Preconditions.checkNotNull(env.getProperty("jdbc.user")));
|
||||
dataSource.setPassword(Preconditions.checkNotNull(env.getProperty("jdbc.pass")));
|
||||
|
||||
return dataSource;
|
||||
}
|
||||
|
||||
@Bean
|
||||
public PlatformTransactionManager hibernateTransactionManager() {
|
||||
final HibernateTransactionManager transactionManager = new HibernateTransactionManager();
|
||||
transactionManager.setSessionFactory(sessionFactory().getObject());
|
||||
return transactionManager;
|
||||
}
|
||||
|
||||
@Bean
|
||||
public PlatformTransactionManager jpaTransactionManager() {
|
||||
final JpaTransactionManager transactionManager = new JpaTransactionManager();
|
||||
transactionManager.setEntityManagerFactory(entityManagerFactory().getObject());
|
||||
return transactionManager;
|
||||
}
|
||||
|
||||
@Bean
|
||||
public PersistenceExceptionTranslationPostProcessor exceptionTranslation() {
|
||||
return new PersistenceExceptionTranslationPostProcessor();
|
||||
}
|
||||
|
||||
@Bean
|
||||
public IFooDao fooHibernateDao() {
|
||||
return new FooDao();
|
||||
}
|
||||
|
||||
private final Properties hibernateProperties() {
|
||||
final Properties hibernateProperties = new Properties();
|
||||
hibernateProperties.setProperty("hibernate.hbm2ddl.auto", env.getProperty("hibernate.hbm2ddl.auto"));
|
||||
hibernateProperties.setProperty("hibernate.dialect", env.getProperty("hibernate.dialect"));
|
||||
|
||||
hibernateProperties.setProperty("hibernate.show_sql", "true");
|
||||
// hibernateProperties.setProperty("hibernate.format_sql", "true");
|
||||
// hibernateProperties.setProperty("hibernate.globally_quoted_identifiers", "true");
|
||||
|
||||
// Envers properties
|
||||
hibernateProperties.setProperty("org.hibernate.envers.audit_table_suffix", env.getProperty("envers.audit_table_suffix"));
|
||||
|
||||
return hibernateProperties;
|
||||
}
|
||||
|
||||
}
|
||||
+4
-4
@@ -1,4 +1,4 @@
|
||||
package org.baeldung.config;
|
||||
package com.baeldung.config;
|
||||
|
||||
import java.util.Properties;
|
||||
|
||||
@@ -25,8 +25,8 @@ import com.google.common.base.Preconditions;
|
||||
@Configuration
|
||||
@EnableTransactionManagement
|
||||
@PropertySource({ "classpath:persistence-h2.properties" })
|
||||
@ComponentScan({ "org.baeldung.persistence" })
|
||||
@EnableJpaRepositories(basePackages = "org.baeldung.persistence.dao")
|
||||
@ComponentScan({ "com.baeldung.persistence","com.baeldung.jpa.dao" })
|
||||
@EnableJpaRepositories(basePackages = "com.baeldung.jpa.dao")
|
||||
public class PersistenceJPAConfig {
|
||||
|
||||
@Autowired
|
||||
@@ -42,7 +42,7 @@ public class PersistenceJPAConfig {
|
||||
public LocalContainerEntityManagerFactoryBean entityManagerFactory() {
|
||||
final LocalContainerEntityManagerFactoryBean em = new LocalContainerEntityManagerFactoryBean();
|
||||
em.setDataSource(dataSource());
|
||||
em.setPackagesToScan(new String[] { "org.baeldung.persistence.model" });
|
||||
em.setPackagesToScan(new String[] { "com.baeldung.persistence.model" });
|
||||
|
||||
final HibernateJpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();
|
||||
em.setJpaVendorAdapter(vendorAdapter);
|
||||
+39
@@ -0,0 +1,39 @@
|
||||
package com.baeldung.hibernate.bootstrap;
|
||||
|
||||
import com.baeldung.hibernate.bootstrap.model.TestEntity;
|
||||
import org.hibernate.Session;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
|
||||
public abstract class BarHibernateDAO {
|
||||
|
||||
@Autowired
|
||||
private SessionFactory sessionFactory;
|
||||
|
||||
public TestEntity findEntity(int id) {
|
||||
|
||||
return getCurrentSession().find(TestEntity.class, 1);
|
||||
}
|
||||
|
||||
public void createEntity(TestEntity entity) {
|
||||
|
||||
getCurrentSession().save(entity);
|
||||
}
|
||||
|
||||
public void createEntity(int id, String newDescription) {
|
||||
|
||||
TestEntity entity = findEntity(id);
|
||||
entity.setDescription(newDescription);
|
||||
getCurrentSession().save(entity);
|
||||
}
|
||||
|
||||
public void deleteEntity(int id) {
|
||||
|
||||
TestEntity entity = findEntity(id);
|
||||
getCurrentSession().delete(entity);
|
||||
}
|
||||
|
||||
protected Session getCurrentSession() {
|
||||
return sessionFactory.getCurrentSession();
|
||||
}
|
||||
}
|
||||
+61
@@ -0,0 +1,61 @@
|
||||
package com.baeldung.hibernate.bootstrap;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
import org.apache.tomcat.dbcp.dbcp2.BasicDataSource;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.PropertySource;
|
||||
import org.springframework.core.env.Environment;
|
||||
import org.springframework.orm.hibernate5.HibernateTransactionManager;
|
||||
import org.springframework.orm.hibernate5.LocalSessionFactoryBean;
|
||||
import org.springframework.transaction.PlatformTransactionManager;
|
||||
import org.springframework.transaction.annotation.EnableTransactionManagement;
|
||||
|
||||
import javax.sql.DataSource;
|
||||
import java.util.Properties;
|
||||
|
||||
@Configuration
|
||||
@EnableTransactionManagement
|
||||
@PropertySource({ "classpath:persistence-h2.properties" })
|
||||
public class HibernateConf {
|
||||
|
||||
@Autowired
|
||||
private Environment env;
|
||||
|
||||
@Bean
|
||||
public LocalSessionFactoryBean sessionFactory() {
|
||||
final LocalSessionFactoryBean sessionFactory = new LocalSessionFactoryBean();
|
||||
sessionFactory.setDataSource(dataSource());
|
||||
sessionFactory.setPackagesToScan(new String[] { "com.baeldung.hibernate.bootstrap.model" });
|
||||
sessionFactory.setHibernateProperties(hibernateProperties());
|
||||
|
||||
return sessionFactory;
|
||||
}
|
||||
|
||||
@Bean
|
||||
public DataSource dataSource() {
|
||||
final BasicDataSource dataSource = new BasicDataSource();
|
||||
dataSource.setDriverClassName(Preconditions.checkNotNull(env.getProperty("jdbc.driverClassName")));
|
||||
dataSource.setUrl(Preconditions.checkNotNull(env.getProperty("jdbc.url")));
|
||||
dataSource.setUsername(Preconditions.checkNotNull(env.getProperty("jdbc.user")));
|
||||
dataSource.setPassword(Preconditions.checkNotNull(env.getProperty("jdbc.pass")));
|
||||
|
||||
return dataSource;
|
||||
}
|
||||
|
||||
@Bean
|
||||
public PlatformTransactionManager hibernateTransactionManager() {
|
||||
final HibernateTransactionManager transactionManager = new HibernateTransactionManager();
|
||||
transactionManager.setSessionFactory(sessionFactory().getObject());
|
||||
return transactionManager;
|
||||
}
|
||||
|
||||
private final Properties hibernateProperties() {
|
||||
final Properties hibernateProperties = new Properties();
|
||||
hibernateProperties.setProperty("hibernate.hbm2ddl.auto", env.getProperty("hibernate.hbm2ddl.auto"));
|
||||
hibernateProperties.setProperty("hibernate.dialect", env.getProperty("hibernate.dialect"));
|
||||
|
||||
return hibernateProperties;
|
||||
}
|
||||
}
|
||||
+24
@@ -0,0 +1,24 @@
|
||||
package com.baeldung.hibernate.bootstrap;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
import org.apache.tomcat.dbcp.dbcp2.BasicDataSource;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.ImportResource;
|
||||
import org.springframework.context.annotation.PropertySource;
|
||||
import org.springframework.core.env.Environment;
|
||||
import org.springframework.orm.hibernate5.HibernateTransactionManager;
|
||||
import org.springframework.orm.hibernate5.LocalSessionFactoryBean;
|
||||
import org.springframework.transaction.PlatformTransactionManager;
|
||||
import org.springframework.transaction.annotation.EnableTransactionManagement;
|
||||
|
||||
import javax.sql.DataSource;
|
||||
import java.util.Properties;
|
||||
|
||||
@Configuration
|
||||
@EnableTransactionManagement
|
||||
@ImportResource({ "classpath:hibernate5Configuration.xml" })
|
||||
public class HibernateXMLConf {
|
||||
|
||||
}
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
package com.baeldung.hibernate.bootstrap.model;
|
||||
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.Id;
|
||||
|
||||
@Entity
|
||||
public class TestEntity {
|
||||
|
||||
private int id;
|
||||
|
||||
private String description;
|
||||
|
||||
@Id
|
||||
public int getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(int id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public String getDescription() {
|
||||
return description;
|
||||
}
|
||||
|
||||
public void setDescription(String description) {
|
||||
this.description = description;
|
||||
}
|
||||
}
|
||||
+20
@@ -0,0 +1,20 @@
|
||||
package com.baeldung.hibernate.dao;
|
||||
|
||||
import com.baeldung.persistence.model.Foo;
|
||||
import org.springframework.stereotype.Repository;
|
||||
|
||||
import com.baeldung.jpa.dao.IFooDao;
|
||||
import com.baeldung.persistence.dao.common.AbstractHibernateDao;
|
||||
|
||||
@Repository
|
||||
public class FooDao extends AbstractHibernateDao<Foo> implements IFooDao {
|
||||
|
||||
public FooDao() {
|
||||
super();
|
||||
|
||||
setClazz(Foo.class);
|
||||
}
|
||||
|
||||
// API
|
||||
|
||||
}
|
||||
+19
@@ -0,0 +1,19 @@
|
||||
package com.baeldung.jdbc;
|
||||
|
||||
import java.sql.SQLException;
|
||||
|
||||
import org.springframework.dao.DataAccessException;
|
||||
import org.springframework.dao.DuplicateKeyException;
|
||||
import org.springframework.jdbc.support.SQLErrorCodeSQLExceptionTranslator;
|
||||
|
||||
public class CustomSQLErrorCodeTranslator extends SQLErrorCodeSQLExceptionTranslator {
|
||||
|
||||
@Override
|
||||
protected DataAccessException customTranslate(final String task, final String sql, final SQLException sqlException) {
|
||||
if (sqlException.getErrorCode() == 23505) {
|
||||
return new DuplicateKeyException("Custome Exception translator - Integrity contraint voilation.", sqlException);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
+44
@@ -0,0 +1,44 @@
|
||||
package com.baeldung.jdbc;
|
||||
|
||||
public class Employee {
|
||||
private int id;
|
||||
|
||||
private String firstName;
|
||||
|
||||
private String lastName;
|
||||
|
||||
private String address;
|
||||
|
||||
public int getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(final int id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public String getFirstName() {
|
||||
return firstName;
|
||||
}
|
||||
|
||||
public void setFirstName(final String firstName) {
|
||||
this.firstName = firstName;
|
||||
}
|
||||
|
||||
public String getLastName() {
|
||||
return lastName;
|
||||
}
|
||||
|
||||
public void setLastName(final String lastName) {
|
||||
this.lastName = lastName;
|
||||
}
|
||||
|
||||
public String getAddress() {
|
||||
return address;
|
||||
}
|
||||
|
||||
public void setAddress(final String address) {
|
||||
this.address = address;
|
||||
}
|
||||
|
||||
}
|
||||
+113
@@ -0,0 +1,113 @@
|
||||
package com.baeldung.jdbc;
|
||||
|
||||
import java.sql.PreparedStatement;
|
||||
import java.sql.SQLException;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import javax.sql.DataSource;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.jdbc.core.BatchPreparedStatementSetter;
|
||||
import org.springframework.jdbc.core.JdbcTemplate;
|
||||
import org.springframework.jdbc.core.namedparam.BeanPropertySqlParameterSource;
|
||||
import org.springframework.jdbc.core.namedparam.MapSqlParameterSource;
|
||||
import org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate;
|
||||
import org.springframework.jdbc.core.namedparam.SqlParameterSource;
|
||||
import org.springframework.jdbc.core.namedparam.SqlParameterSourceUtils;
|
||||
import org.springframework.jdbc.core.simple.SimpleJdbcInsert;
|
||||
import org.springframework.stereotype.Repository;
|
||||
|
||||
@Repository
|
||||
public class EmployeeDAO {
|
||||
|
||||
private JdbcTemplate jdbcTemplate;
|
||||
|
||||
private NamedParameterJdbcTemplate namedParameterJdbcTemplate;
|
||||
|
||||
private SimpleJdbcInsert simpleJdbcInsert;
|
||||
|
||||
@Autowired
|
||||
public void setDataSource(final DataSource dataSource) {
|
||||
jdbcTemplate = new JdbcTemplate(dataSource);
|
||||
final CustomSQLErrorCodeTranslator customSQLErrorCodeTranslator = new CustomSQLErrorCodeTranslator();
|
||||
jdbcTemplate.setExceptionTranslator(customSQLErrorCodeTranslator);
|
||||
|
||||
namedParameterJdbcTemplate = new NamedParameterJdbcTemplate(dataSource);
|
||||
simpleJdbcInsert = new SimpleJdbcInsert(dataSource).withTableName("EMPLOYEE");
|
||||
|
||||
}
|
||||
|
||||
public int getCountOfEmployees() {
|
||||
return jdbcTemplate.queryForObject("SELECT COUNT(*) FROM EMPLOYEE", Integer.class);
|
||||
}
|
||||
|
||||
public List<Employee> getAllEmployees() {
|
||||
return jdbcTemplate.query("SELECT * FROM EMPLOYEE", new EmployeeRowMapper());
|
||||
}
|
||||
|
||||
public int addEmplyee(final int id) {
|
||||
return jdbcTemplate.update("INSERT INTO EMPLOYEE VALUES (?, ?, ?, ?)", id, "Bill", "Gates", "USA");
|
||||
}
|
||||
|
||||
public int addEmplyeeUsingSimpelJdbcInsert(final Employee emp) {
|
||||
final Map<String, Object> parameters = new HashMap<String, Object>();
|
||||
parameters.put("ID", emp.getId());
|
||||
parameters.put("FIRST_NAME", emp.getFirstName());
|
||||
parameters.put("LAST_NAME", emp.getLastName());
|
||||
parameters.put("ADDRESS", emp.getAddress());
|
||||
|
||||
return simpleJdbcInsert.execute(parameters);
|
||||
}
|
||||
|
||||
public Employee getEmployee(final int id) {
|
||||
final String query = "SELECT * FROM EMPLOYEE WHERE ID = ?";
|
||||
return jdbcTemplate.queryForObject(query, new Object[] { id }, new EmployeeRowMapper());
|
||||
}
|
||||
|
||||
public void addEmplyeeUsingExecuteMethod() {
|
||||
jdbcTemplate.execute("INSERT INTO EMPLOYEE VALUES (6, 'Bill', 'Gates', 'USA')");
|
||||
}
|
||||
|
||||
public String getEmployeeUsingMapSqlParameterSource() {
|
||||
final SqlParameterSource namedParameters = new MapSqlParameterSource().addValue("id", 1);
|
||||
|
||||
return namedParameterJdbcTemplate.queryForObject("SELECT FIRST_NAME FROM EMPLOYEE WHERE ID = :id", namedParameters, String.class);
|
||||
}
|
||||
|
||||
public int getEmployeeUsingBeanPropertySqlParameterSource() {
|
||||
final Employee employee = new Employee();
|
||||
employee.setFirstName("James");
|
||||
|
||||
final String SELECT_BY_ID = "SELECT COUNT(*) FROM EMPLOYEE WHERE FIRST_NAME = :firstName";
|
||||
|
||||
final SqlParameterSource namedParameters = new BeanPropertySqlParameterSource(employee);
|
||||
|
||||
return namedParameterJdbcTemplate.queryForObject(SELECT_BY_ID, namedParameters, Integer.class);
|
||||
}
|
||||
|
||||
public int[] batchUpdateUsingJDBCTemplate(final List<Employee> employees) {
|
||||
return jdbcTemplate.batchUpdate("INSERT INTO EMPLOYEE VALUES (?, ?, ?, ?)", new BatchPreparedStatementSetter() {
|
||||
|
||||
@Override
|
||||
public void setValues(final PreparedStatement ps, final int i) throws SQLException {
|
||||
ps.setInt(1, employees.get(i).getId());
|
||||
ps.setString(2, employees.get(i).getFirstName());
|
||||
ps.setString(3, employees.get(i).getLastName());
|
||||
ps.setString(4, employees.get(i).getAddress());
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getBatchSize() {
|
||||
return 3;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
public int[] batchUpdateUsingNamedParameterJDBCTemplate(final List<Employee> employees) {
|
||||
final SqlParameterSource[] batch = SqlParameterSourceUtils.createBatch(employees.toArray());
|
||||
final int[] updateCounts = namedParameterJdbcTemplate.batchUpdate("INSERT INTO EMPLOYEE VALUES (:id, :firstName, :lastName, :address)", batch);
|
||||
return updateCounts;
|
||||
}
|
||||
}
|
||||
+21
@@ -0,0 +1,21 @@
|
||||
package com.baeldung.jdbc;
|
||||
|
||||
import java.sql.ResultSet;
|
||||
import java.sql.SQLException;
|
||||
|
||||
import org.springframework.jdbc.core.RowMapper;
|
||||
|
||||
public class EmployeeRowMapper implements RowMapper<Employee> {
|
||||
|
||||
@Override
|
||||
public Employee mapRow(final ResultSet rs, final int rowNum) throws SQLException {
|
||||
final Employee employee = new Employee();
|
||||
|
||||
employee.setId(rs.getInt("ID"));
|
||||
employee.setFirstName(rs.getString("FIRST_NAME"));
|
||||
employee.setLastName(rs.getString("LAST_NAME"));
|
||||
employee.setAddress(rs.getString("ADDRESS"));
|
||||
|
||||
return employee;
|
||||
}
|
||||
}
|
||||
+32
@@ -0,0 +1,32 @@
|
||||
package com.baeldung.jdbc.config;
|
||||
|
||||
import javax.sql.DataSource;
|
||||
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.ComponentScan;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.jdbc.datasource.DriverManagerDataSource;
|
||||
import org.springframework.jdbc.datasource.embedded.EmbeddedDatabaseBuilder;
|
||||
import org.springframework.jdbc.datasource.embedded.EmbeddedDatabaseType;
|
||||
|
||||
@Configuration
|
||||
@ComponentScan("com.baeldung.jdbc")
|
||||
public class SpringJdbcConfig {
|
||||
|
||||
@Bean
|
||||
public DataSource dataSource() {
|
||||
return new EmbeddedDatabaseBuilder().setType(EmbeddedDatabaseType.H2).addScript("classpath:jdbc/schema.sql").addScript("classpath:jdbc/test-data.sql").build();
|
||||
}
|
||||
|
||||
// @Bean
|
||||
public DataSource mysqlDataSource() {
|
||||
final DriverManagerDataSource dataSource = new DriverManagerDataSource();
|
||||
dataSource.setDriverClassName("com.mysql.jdbc.Driver");
|
||||
dataSource.setUrl("jdbc:mysql://localhost:3306/springjdbc");
|
||||
dataSource.setUsername("guest_user");
|
||||
dataSource.setPassword("guest_password");
|
||||
|
||||
return dataSource;
|
||||
}
|
||||
|
||||
}
|
||||
+3
-2
@@ -1,4 +1,4 @@
|
||||
package org.baeldung.persistence.dao;
|
||||
package com.baeldung.jpa.dao;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.List;
|
||||
@@ -26,8 +26,9 @@ public abstract class AbstractJpaDAO<T extends Serializable> {
|
||||
return entityManager.createQuery("from " + clazz.getName()).getResultList();
|
||||
}
|
||||
|
||||
public void create(final T entity) {
|
||||
public T create(final T entity) {
|
||||
entityManager.persist(entity);
|
||||
return entity;
|
||||
}
|
||||
|
||||
public T update(final T entity) {
|
||||
+2
-2
@@ -1,6 +1,6 @@
|
||||
package org.baeldung.persistence.dao;
|
||||
package com.baeldung.jpa.dao;
|
||||
|
||||
import org.baeldung.persistence.model.Foo;
|
||||
import com.baeldung.persistence.model.Foo;
|
||||
import org.springframework.stereotype.Repository;
|
||||
|
||||
@Repository
|
||||
+3
-3
@@ -1,8 +1,8 @@
|
||||
package org.baeldung.persistence.dao;
|
||||
package com.baeldung.jpa.dao;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.baeldung.persistence.model.Foo;
|
||||
import com.baeldung.persistence.model.Foo;
|
||||
|
||||
public interface IFooDao {
|
||||
|
||||
@@ -10,7 +10,7 @@ public interface IFooDao {
|
||||
|
||||
List<Foo> findAll();
|
||||
|
||||
void create(Foo entity);
|
||||
Foo create(Foo entity);
|
||||
|
||||
Foo update(Foo entity);
|
||||
|
||||
+14
@@ -0,0 +1,14 @@
|
||||
package com.baeldung.persistence.dao.common;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
|
||||
public abstract class AbstractDao<T extends Serializable> implements IOperations<T> {
|
||||
|
||||
protected Class<T> clazz;
|
||||
|
||||
protected final void setClazz(final Class<T> clazzToSet) {
|
||||
clazz = Preconditions.checkNotNull(clazzToSet);
|
||||
}
|
||||
}
|
||||
+60
@@ -0,0 +1,60 @@
|
||||
package com.baeldung.persistence.dao.common;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.List;
|
||||
|
||||
import org.hibernate.Session;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public abstract class AbstractHibernateDao<T extends Serializable> extends AbstractDao<T> implements IOperations<T> {
|
||||
|
||||
@Autowired
|
||||
protected SessionFactory sessionFactory;
|
||||
|
||||
// API
|
||||
|
||||
@Override
|
||||
public T findOne(final long id) {
|
||||
return (T) getCurrentSession().get(clazz, id);
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<T> findAll() {
|
||||
return getCurrentSession().createQuery("from " + clazz.getName()).list();
|
||||
}
|
||||
|
||||
@Override
|
||||
public T create(final T entity) {
|
||||
Preconditions.checkNotNull(entity);
|
||||
getCurrentSession().saveOrUpdate(entity);
|
||||
return entity;
|
||||
}
|
||||
|
||||
@Override
|
||||
public T update(final T entity) {
|
||||
Preconditions.checkNotNull(entity);
|
||||
return (T) getCurrentSession().merge(entity);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void delete(final T entity) {
|
||||
Preconditions.checkNotNull(entity);
|
||||
getCurrentSession().delete(entity);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void deleteById(final long entityId) {
|
||||
final T entity = findOne(entityId);
|
||||
Preconditions.checkState(entity != null);
|
||||
delete(entity);
|
||||
}
|
||||
|
||||
protected Session getCurrentSession() {
|
||||
return sessionFactory.getCurrentSession();
|
||||
}
|
||||
|
||||
}
|
||||
+13
@@ -0,0 +1,13 @@
|
||||
package com.baeldung.persistence.dao.common;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
import org.springframework.beans.factory.config.BeanDefinition;
|
||||
import org.springframework.context.annotation.Scope;
|
||||
import org.springframework.stereotype.Repository;
|
||||
|
||||
@Repository
|
||||
@Scope(BeanDefinition.SCOPE_PROTOTYPE)
|
||||
public class GenericHibernateDao<T extends Serializable> extends AbstractHibernateDao<T> implements IGenericDao<T> {
|
||||
//
|
||||
}
|
||||
+15
@@ -0,0 +1,15 @@
|
||||
package com.baeldung.persistence.dao.common;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
import org.springframework.beans.factory.config.BeanDefinition;
|
||||
import org.springframework.context.annotation.Scope;
|
||||
import org.springframework.stereotype.Repository;
|
||||
|
||||
import com.baeldung.jpa.dao.AbstractJpaDAO;
|
||||
|
||||
@Repository
|
||||
@Scope(BeanDefinition.SCOPE_PROTOTYPE)
|
||||
public class GenericJpaDao<T extends Serializable> extends AbstractJpaDAO<T> implements IGenericDao<T> {
|
||||
//
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user