BAEL-3091: The Prototype Pattern in Java (changed code based on valid comments from a reader)

This commit is contained in:
Vivek Balasubramaniam
2019-10-29 22:27:15 +05:30
parent db85c8f275
commit d3d5b060e7
20517 changed files with 1642290 additions and 0 deletions
+3
View File
@@ -0,0 +1,3 @@
## Persistence Modules
This module contains articles about persistence. Actual articles go into its submodules.
+2
View File
@@ -0,0 +1,2 @@
### Relevant Articles:
- [Introduction to ActiveJDBC](http://www.baeldung.com/active-jdbc)
+91
View File
@@ -0,0 +1,91 @@
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<artifactId>activejdbc</artifactId>
<version>1.0-SNAPSHOT</version>
<name>activejdbc</name>
<packaging>jar</packaging>
<url>http://maven.apache.org</url>
<parent>
<artifactId>parent-modules</artifactId>
<groupId>com.baeldung</groupId>
<version>1.0.0-SNAPSHOT</version>
<relativePath>../../</relativePath>
</parent>
<dependencies>
<dependency>
<groupId>org.javalite</groupId>
<artifactId>activejdbc</artifactId>
<version>${activejdbc.version}</version>
<exclusions>
<exclusion>
<groupId>opensymphony</groupId>
<artifactId>oscache</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>${mysql.connector.version}</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-simple</artifactId>
<version>${org.slf4j.version}</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>${maven-compiler-plugin.version}</version>
<configuration>
<source>${java.version}</source>
<target>${java.version}</target>
<encoding>UTF-8</encoding>
</configuration>
</plugin>
<plugin>
<groupId>org.javalite</groupId>
<artifactId>activejdbc-instrumentation</artifactId>
<version>${activejdbc.version}</version>
<executions>
<execution>
<phase>process-classes</phase>
<goals>
<goal>instrument</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.javalite</groupId>
<artifactId>db-migrator-maven-plugin</artifactId>
<version>${activejdbc.version}</version>
<configuration>
<configFile>${project.basedir}/src/main/resources/database.properties</configFile>
<environments>${environments}</environments>
</configuration>
<dependencies>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>${mysql.connector.version}</version>
</dependency>
</dependencies>
</plugin>
</plugins>
</build>
<properties>
<activejdbc.version>2.0</activejdbc.version>
<environments>development.test,development</environments>
<mysql.connector.version>5.1.34</mysql.connector.version>
</properties>
</project>
@@ -0,0 +1,61 @@
package com.baeldung;
import com.baeldung.model.Employee;
import com.baeldung.model.Role;
import org.javalite.activejdbc.Base;
import org.javalite.activejdbc.LazyList;
import org.javalite.activejdbc.Model;
public class ActiveJDBCApp
{
public static void main( String[] args )
{
try {
Base.open();
ActiveJDBCApp app = new ActiveJDBCApp();
app.create();
app.update();
app.delete();
app.deleteCascade();
} catch (Exception e) {
e.printStackTrace();
} finally {
Base.close();
}
}
protected void create() {
Employee employee = new Employee("Hugo","C","M","BN");
employee.saveIt();
employee.add(new Role("Java Developer","BN"));
LazyList<Model> all = Employee.findAll();
System.out.println(all.size());
}
protected void update() {
Employee employee = Employee.findFirst("first_name = ?","Hugo");
employee.set("last_namea","Choi").saveIt();
employee = Employee.findFirst("last_name = ?","Choi");
System.out.println(employee.getString("first_name") + " " + employee.getString("last_name"));
}
protected void delete() {
Employee employee = Employee.findFirst("first_name = ?","Hugo");
employee.delete();
employee = Employee.findFirst("last_name = ?","Choi");
if(null == employee){
System.out.println("No such Employee found!");
}
}
protected void deleteCascade() {
create();
Employee employee = Employee.findFirst("first_name = ?","Hugo");
employee.deleteCascade();
employee = Employee.findFirst("last_name = ?","C");
if(null == employee){
System.out.println("No such Employee found!");
}
}
}
@@ -0,0 +1,23 @@
package com.baeldung.model;
import org.javalite.activejdbc.Model;
public class Employee extends Model {
public Employee(){
}
public Employee(String firstName, String lastName, String gender, String createdBy) {
set("first_name1",firstName);
set("last_name",lastName);
set("gender",gender);
set("created_by",createdBy);
}
public String getLastName() {
return getString("last_name");
}
}
@@ -0,0 +1,22 @@
package com.baeldung.model;
import org.javalite.activejdbc.Model;
import org.javalite.activejdbc.annotations.Table;
@Table("EMP_ROLES")
public class Role extends Model {
public Role(){
}
public Role(String role,String createdBy){
set("role_name",role);
set("created_by",createdBy);
}
public String getRoleName() {
return getString("role_name");
}
}
@@ -0,0 +1,25 @@
# noinspection SqlNoDataSourceInspectionForFile
create table organisation.employees
(
id int not null auto_increment
primary key,
first_name varchar(100) not null,
last_name varchar(100) not null,
gender varchar(1) not null,
created_at datetime not null,
updated_at datetime null,
created_by varchar(100) not null,
updated_by varchar(100) null
)ENGINE = InnoDB DEFAULT CHARSET = utf8;
create table organisation.emp_roles
(
id int not null auto_increment primary key,
employee_id int not null,
role_name varchar(100) not null,
created_at datetime not null,
updated_at datetime null,
created_by varchar(100) not null,
updated_by varchar(100) null
)ENGINE = InnoDB DEFAULT CHARSET = utf8;
@@ -0,0 +1,10 @@
development.driver=com.mysql.jdbc.Driver
development.username=root
development.password=123456
development.url=jdbc:mysql://localhost/organisation
development.test.driver=com.mysql.jdbc.Driver
development.test.username=root
development.test.password=123456
development.test.url=jdbc:mysql://localhost/organisation_test
@@ -0,0 +1,13 @@
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
</pattern>
</encoder>
</appender>
<root level="INFO">
<appender-ref ref="STDOUT" />
</root>
</configuration>
@@ -0,0 +1,51 @@
package com.baeldung;
import com.baeldung.model.Employee;
import com.baeldung.model.Role;
import org.javalite.activejdbc.test.DBSpec;
import org.junit.Test;
import java.util.List;
public class ActiveJDBCAppManualTest extends DBSpec
{
@Test
public void ifEmployeeCreated_thenIsValid() {
Employee employee = new Employee("B", "N", "M", "BN");
the(employee).shouldBe("valid");
}
@Test
public void ifEmployeeCreatedWithRoles_thenShouldPersist() {
Employee employee = new Employee("B", "N", "M", "BN");
employee.saveIt();
employee.add(new Role("Java Developer","BN"));
employee.add(new Role("Lead Java Developer","BN"));
a(Role.count()).shouldBeEqual(2);
List<Role> roles = employee.getAll(Role.class).orderBy("created_at");
the(roles.get(0).getRoleName()).shouldBeEqual("Java Developer");
the(roles.get(1).getRoleName()).shouldBeEqual("Lead Java Developer");
}
@Test
public void ifEmployeeCreatedWithRoles_whenNameUpdated_thenShouldShowNewName() {
Employee employee = new Employee("Binesh", "N", "M", "BN");
employee.saveIt();
employee.add(new Role("Java Developer","BN"));
employee.add(new Role("Lead Java Developer","BN"));
employee = Employee.findFirst("first_name = ?", "Binesh");
employee.set("last_name","Narayanan").saveIt();
Employee updated = Employee.findFirst("first_name = ?", "Binesh");
the(updated.getLastName()).shouldBeEqual("Narayanan");
}
@Test
public void ifEmployeeCreatedWithRoles_whenDeleted_thenShouldNotBeFound() {
Employee employee = new Employee("Binesh", "N", "M", "BN");
employee.saveIt();
employee.add(new Role("Java Developer","BN"));
employee.delete();
employee = Employee.findFirst("first_name = ?", "Binesh");
the(employee).shouldBeNull();
}
}
@@ -0,0 +1,4 @@
## Relevant articles:
- [Advanced Querying in Apache Cayenne](http://www.baeldung.com/apache-cayenne-query)
- [Introduction to Apache Cayenne ORM](http://www.baeldung.com/apache-cayenne-orm)
@@ -0,0 +1,48 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<artifactId>apache-cayenne</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>apache-cayenne</name>
<packaging>jar</packaging>
<description>Introduction to Apache Cayenne</description>
<parent>
<groupId>com.baeldung</groupId>
<artifactId>parent-modules</artifactId>
<version>1.0.0-SNAPSHOT</version>
<relativePath>../../</relativePath>
</parent>
<dependencies>
<dependency>
<groupId>org.apache.cayenne</groupId>
<artifactId>cayenne-server</artifactId>
<version>${cayenne.version}</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>${mysql.connector.version}</version>
<scope>runtime</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.cayenne.plugins</groupId>
<artifactId>cayenne-modeler-maven-plugin</artifactId>
<version>${cayenne.version}</version>
</plugin>
</plugins>
</build>
<properties>
<mysql.connector.version>5.1.44</mysql.connector.version>
<cayenne.version>4.0.M5</cayenne.version>
</properties>
</project>
@@ -0,0 +1,9 @@
package com.baeldung.apachecayenne.persistent;
import com.baeldung.apachecayenne.persistent.auto._Article;
public class Article extends _Article {
private static final long serialVersionUID = 1L;
}
@@ -0,0 +1,9 @@
package com.baeldung.apachecayenne.persistent;
import com.baeldung.apachecayenne.persistent.auto._Author;
public class Author extends _Author {
private static final long serialVersionUID = 1L;
}
@@ -0,0 +1,47 @@
package com.baeldung.apachecayenne.persistent.auto;
import org.apache.cayenne.CayenneDataObject;
import org.apache.cayenne.exp.Property;
import com.baeldung.apachecayenne.persistent.Author;
/**
* Class _Article was generated by Cayenne.
* It is probably a good idea to avoid changing this class manually,
* since it may be overwritten next time code is regenerated.
* If you need to make any customizations, please use subclass.
*/
public abstract class _Article extends CayenneDataObject {
private static final long serialVersionUID = 1L;
public static final String ID_PK_COLUMN = "id";
public static final Property<String> CONTENT = Property.create("content", String.class);
public static final Property<String> TITLE = Property.create("title", String.class);
public static final Property<Author> AUTHOR = Property.create("author", Author.class);
public void setContent(String content) {
writeProperty("content", content);
}
public String getContent() {
return (String)readProperty("content");
}
public void setTitle(String title) {
writeProperty("title", title);
}
public String getTitle() {
return (String)readProperty("title");
}
public void setAuthor(Author author) {
setToOneTarget("author", author, true);
}
public Author getAuthor() {
return (Author)readProperty("author");
}
}
@@ -0,0 +1,44 @@
package com.baeldung.apachecayenne.persistent.auto;
import java.util.List;
import org.apache.cayenne.CayenneDataObject;
import org.apache.cayenne.exp.Property;
import com.baeldung.apachecayenne.persistent.Article;
/**
* Class _Author was generated by Cayenne.
* It is probably a good idea to avoid changing this class manually,
* since it may be overwritten next time code is regenerated.
* If you need to make any customizations, please use subclass.
*/
public abstract class _Author extends CayenneDataObject {
private static final long serialVersionUID = 1L;
public static final String ID_PK_COLUMN = "id";
public static final Property<String> NAME = Property.create("name", String.class);
public static final Property<List<Article>> ARTICLES = Property.create("articles", List.class);
public void setName(String name) {
writeProperty("name", name);
}
public String getName() {
return (String)readProperty("name");
}
public void addToArticles(Article obj) {
addToManyTarget("articles", obj, true);
}
public void removeFromArticles(Article obj) {
removeToManyTarget("articles", obj, true);
}
@SuppressWarnings("unchecked")
public List<Article> getArticles() {
return (List<Article>)readProperty("articles");
}
}
@@ -0,0 +1,17 @@
<?xml version="1.0" encoding="utf-8"?>
<domain project-version="9">
<map name="datamap"/>
<node name="datanode"
factory="org.apache.cayenne.configuration.server.XMLPoolingDataSourceFactory"
schema-update-strategy="org.apache.cayenne.access.dbsync.CreateIfNoSchemaStrategy"
>
<map-ref name="datamap"/>
<data-source>
<driver value="com.mysql.jdbc.Driver"/>
<url value="jdbc:mysql://localhost:3306/intro_cayenne"/>
<connectionPool min="1" max="1"/>
<login userName="root" password="root"/>
</data-source>
</node>
</domain>
@@ -0,0 +1,32 @@
<?xml version="1.0" encoding="utf-8"?>
<data-map xmlns="http://cayenne.apache.org/schema/9/modelMap"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://cayenne.apache.org/schema/9/modelMap http://cayenne.apache.org/schema/9/modelMap.xsd"
project-version="9">
<property name="defaultPackage" value="com.baeldung.apachecayenne.persistent"/>
<db-entity name="article" catalog="intro_cayenne">
<db-attribute name="author_id" type="INTEGER" isMandatory="true" length="10"/>
<db-attribute name="content" type="VARCHAR" isMandatory="true" length="254"/>
<db-attribute name="id" type="INTEGER" isPrimaryKey="true" isGenerated="true" isMandatory="true" length="10"/>
<db-attribute name="title" type="VARCHAR" isMandatory="true" length="254"/>
</db-entity>
<db-entity name="author" catalog="intro_cayenne">
<db-attribute name="id" type="INTEGER" isPrimaryKey="true" isGenerated="true" isMandatory="true" length="10"/>
<db-attribute name="name" type="VARCHAR" isMandatory="true" length="254"/>
</db-entity>
<obj-entity name="Article" className="com.baeldung.apachecayenne.persistent.Article" dbEntityName="article">
<obj-attribute name="content" type="java.lang.String" db-attribute-path="content"/>
<obj-attribute name="title" type="java.lang.String" db-attribute-path="title"/>
</obj-entity>
<obj-entity name="Author" className="com.baeldung.apachecayenne.persistent.Author" dbEntityName="author">
<obj-attribute name="name" type="java.lang.String" db-attribute-path="name"/>
</obj-entity>
<db-relationship name="author" source="article" target="author" toMany="false">
<db-attribute-pair source="author_id" target="id"/>
</db-relationship>
<db-relationship name="articles" source="author" target="article" toMany="true">
<db-attribute-pair source="id" target="author_id"/>
</db-relationship>
<obj-relationship name="author" source="Article" target="Author" deleteRule="Nullify" db-relationship-path="author"/>
<obj-relationship name="articles" source="Author" target="Article" deleteRule="Deny" db-relationship-path="articles"/>
</data-map>
@@ -0,0 +1,13 @@
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
</pattern>
</encoder>
</appender>
<root level="INFO">
<appender-ref ref="STDOUT" />
</root>
</configuration>
@@ -0,0 +1,256 @@
package com.baeldung.apachecayenne;
import com.baeldung.apachecayenne.persistent.Author;
import org.apache.cayenne.ObjectContext;
import org.apache.cayenne.QueryResponse;
import org.apache.cayenne.configuration.server.ServerRuntime;
import org.apache.cayenne.exp.Expression;
import org.apache.cayenne.exp.ExpressionFactory;
import org.apache.cayenne.query.*;
import org.junit.After;
import org.junit.Before;
import org.junit.BeforeClass;
import org.junit.Test;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import static junit.framework.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
public class CayenneAdvancedOperationLiveTest {
private static ObjectContext context = null;
@BeforeClass
public static void setupTheCayenneContext() {
ServerRuntime cayenneRuntime = ServerRuntime.builder()
.addConfig("cayenne-project.xml")
.build();
context = cayenneRuntime.newContext();
}
@Before
public void saveThreeAuthors() {
Author authorOne = context.newObject(Author.class);
authorOne.setName("Paul Xavier");
Author authorTwo = context.newObject(Author.class);
authorTwo.setName("pAuL Smith");
Author authorThree = context.newObject(Author.class);
authorThree.setName("Vicky Sarra");
context.commitChanges();
}
@After
public void deleteAllAuthors() {
SQLTemplate deleteAuthors = new SQLTemplate(Author.class, "delete from author");
context.performGenericQuery(deleteAuthors);
}
@Test
public void givenAuthors_whenFindAllSQLTmplt_thenWeGetThreeAuthors() {
SQLTemplate select = new SQLTemplate(Author.class, "select * from Author");
List<Author> authors = context.performQuery(select);
assertEquals(authors.size(), 3);
}
@Test
public void givenAuthors_whenFindByNameSQLTmplt_thenWeGetOneAuthor() {
SQLTemplate select = new SQLTemplate(Author.class, "select * from Author where name = 'Vicky Sarra'");
List<Author> authors = context.performQuery(select);
Author author = authors.get(0);
assertEquals(authors.size(), 1);
assertEquals(author.getName(), "Vicky Sarra");
}
@Test
public void givenAuthors_whenLikeSltQry_thenWeGetOneAuthor() {
Expression qualifier = ExpressionFactory.likeExp(Author.NAME.getName(), "Paul%");
SelectQuery query = new SelectQuery(Author.class, qualifier);
List<Author> authorsTwo = context.performQuery(query);
assertEquals(authorsTwo.size(), 1);
}
@Test
public void givenAuthors_whenCtnsIgnorCaseSltQry_thenWeGetTwoAuthors() {
Expression qualifier = ExpressionFactory.containsIgnoreCaseExp(Author.NAME.getName(), "Paul");
SelectQuery query = new SelectQuery(Author.class, qualifier);
List<Author> authors = context.performQuery(query);
assertEquals(authors.size(), 2);
}
@Test
public void givenAuthors_whenCtnsIgnorCaseEndsWSltQry_thenWeGetTwoAuthors() {
Expression qualifier = ExpressionFactory.containsIgnoreCaseExp(Author.NAME.getName(), "Paul")
.andExp(ExpressionFactory.endsWithExp(Author.NAME.getName(), "h"));
SelectQuery query = new SelectQuery(Author.class, qualifier);
List<Author> authors = context.performQuery(query);
Author author = authors.get(0);
assertEquals(authors.size(), 1);
assertEquals(author.getName(), "pAuL Smith");
}
@Test
public void givenAuthors_whenAscOrderingSltQry_thenWeGetOrderedAuthors() {
SelectQuery query = new SelectQuery(Author.class);
query.addOrdering(Author.NAME.asc());
List<Author> authors = query.select(context);
Author firstAuthor = authors.get(0);
assertEquals(authors.size(), 3);
assertEquals(firstAuthor.getName(), "Paul Xavier");
}
@Test
public void givenAuthors_whenDescOrderingSltQry_thenWeGetOrderedAuthors() {
SelectQuery query = new SelectQuery(Author.class);
query.addOrdering(Author.NAME.desc());
List<Author> authors = query.select(context);
Author firstAuthor = authors.get(0);
assertEquals(authors.size(), 3);
assertEquals(firstAuthor.getName(), "pAuL Smith");
}
@Test
public void givenAuthors_onContainsObjS_thenWeGetOneRecord() {
List<Author> authors = ObjectSelect.query(Author.class)
.where(Author.NAME.contains("Paul"))
.select(context);
assertEquals(authors.size(), 1);
}
@Test
public void givenAuthors_whenLikeObjS_thenWeGetTwoAuthors() {
List<Author> authors = ObjectSelect.query(Author.class)
.where(Author.NAME.likeIgnoreCase("Paul%"))
.select(context);
assertEquals(authors.size(), 2);
}
@Test
public void givenTwoAuthor_whenEndsWithObjS_thenWeGetOrderedAuthors() {
List<Author> authors = ObjectSelect.query(Author.class)
.where(Author.NAME.endsWith("Sarra"))
.select(context);
Author firstAuthor = authors.get(0);
assertEquals(authors.size(), 1);
assertEquals(firstAuthor.getName(), "Vicky Sarra");
}
@Test
public void givenTwoAuthor_whenInObjS_thenWeGetAuthors() {
List<String> names = Arrays.asList("Paul Xavier", "pAuL Smith", "Vicky Sarra");
List<Author> authors = ObjectSelect.query(Author.class)
.where(Author.NAME.in(names))
.select(context);
assertEquals(authors.size(), 3);
}
@Test
public void givenTwoAuthor_whenNinObjS_thenWeGetAuthors() {
List<String> names = Arrays.asList("Paul Xavier", "pAuL Smith");
List<Author> authors = ObjectSelect.query(Author.class)
.where(Author.NAME.nin(names))
.select(context);
Author author = authors.get(0);
assertEquals(authors.size(), 1);
assertEquals(author.getName(), "Vicky Sarra");
}
@Test
public void givenTwoAuthor_whenIsNotNullObjS_thenWeGetAuthors() {
List<Author> authors = ObjectSelect.query(Author.class)
.where(Author.NAME.isNotNull())
.select(context);
assertEquals(authors.size(), 3);
}
@Test
public void givenAuthors_whenFindAllEJBQL_thenWeGetThreeAuthors() {
EJBQLQuery query = new EJBQLQuery("select a FROM Author a");
List<Author> authors = context.performQuery(query);
assertEquals(authors.size(), 3);
}
@Test
public void givenAuthors_whenFindByNameEJBQL_thenWeGetOneAuthor() {
EJBQLQuery query = new EJBQLQuery("select a FROM Author a WHERE a.name = 'Vicky Sarra'");
List<Author> authors = context.performQuery(query);
Author author = authors.get(0);
assertEquals(authors.size(), 1);
assertEquals(author.getName(), "Vicky Sarra");
}
@Test
public void givenAuthors_whenUpdadingByNameEJBQL_thenWeGetTheUpdatedAuthor() {
EJBQLQuery query = new EJBQLQuery("UPDATE Author AS a SET a.name = 'Vicky Edison' WHERE a.name = 'Vicky Sarra'");
QueryResponse queryResponse = context.performGenericQuery(query);
EJBQLQuery queryUpdatedAuthor = new EJBQLQuery("select a FROM Author a WHERE a.name = 'Vicky Edison'");
List<Author> authors = context.performQuery(queryUpdatedAuthor);
Author author = authors.get(0);
assertNotNull(author);
}
@Test
public void givenAuthors_whenSeletingNamesEJBQL_thenWeGetListWithSizeThree() {
String [] args = {"Paul Xavier", "pAuL Smith", "Vicky Sarra"};
List<String> names = Arrays.asList(args);
EJBQLQuery query = new EJBQLQuery("select a.name FROM Author a");
List<String> nameList = context.performQuery(query);
Collections.sort(names);
Collections.sort(nameList);
assertEquals(names.size(), 3);
assertEquals(nameList.size(), 3);
assertEquals(names, nameList);
}
@Test
public void givenAuthors_whenDeletingAllWithEJB_thenWeGetNoAuthor() {
EJBQLQuery deleteQuery = new EJBQLQuery("delete FROM Author");
EJBQLQuery findAllQuery = new EJBQLQuery("select a FROM Author a");
context.performQuery(deleteQuery);
List<Author> objects = context.performQuery(findAllQuery);
assertEquals(objects.size(), 0);
}
@Test
public void givenAuthors_whenInsertingSQLExec_thenWeGetNewAuthor() {
int inserted = SQLExec
.query("INSERT INTO Author (name) VALUES ('Baeldung')")
.update(context);
assertEquals(inserted, 1);
}
@Test
public void givenAuthors_whenUpdatingSQLExec_thenItsUpdated() {
int updated = SQLExec
.query("UPDATE Author SET name = 'Baeldung' WHERE name = 'Vicky Sarra'")
.update(context);
assertEquals(updated, 1);
}
}
@@ -0,0 +1,131 @@
package com.baeldung.apachecayenne;
import com.baeldung.apachecayenne.persistent.Article;
import com.baeldung.apachecayenne.persistent.Author;
import org.apache.cayenne.ObjectContext;
import org.apache.cayenne.configuration.server.ServerRuntime;
import org.apache.cayenne.query.ObjectSelect;
import org.apache.cayenne.query.SQLTemplate;
import org.junit.After;
import org.junit.BeforeClass;
import org.junit.Test;
import java.util.List;
import static junit.framework.Assert.assertEquals;
import static org.junit.Assert.assertNull;
public class CayenneOperationLiveTest {
private static ObjectContext context = null;
@BeforeClass
public static void setupTheCayenneContext() {
ServerRuntime cayenneRuntime = ServerRuntime.builder()
.addConfig("cayenne-project.xml")
.build();
context = cayenneRuntime.newContext();
}
@After
public void deleteAllRecords() {
SQLTemplate deleteArticles = new SQLTemplate(Article.class, "delete from article");
SQLTemplate deleteAuthors = new SQLTemplate(Author.class, "delete from author");
context.performGenericQuery(deleteArticles);
context.performGenericQuery(deleteAuthors);
}
@Test
public void givenAuthor_whenInsert_thenWeGetOneRecordInTheDatabase() {
Author author = context.newObject(Author.class);
author.setName("Paul");
context.commitChanges();
long records = ObjectSelect.dataRowQuery(Author.class).selectCount(context);
assertEquals(1, records);
}
@Test
public void givenAuthor_whenInsert_andQueryByFirstName_thenWeGetTheAuthor() {
Author author = context.newObject(Author.class);
author.setName("Paul");
context.commitChanges();
Author expectedAuthor = ObjectSelect.query(Author.class)
.where(Author.NAME.eq("Paul"))
.selectOne(context);
assertEquals("Paul", expectedAuthor.getName());
}
@Test
public void givenTwoAuthor_whenInsert_andQueryAll_thenWeGetTwoAuthors() {
Author firstAuthor = context.newObject(Author.class);
firstAuthor.setName("Paul");
Author secondAuthor = context.newObject(Author.class);
secondAuthor.setName("Ludovic");
context.commitChanges();
List<Author> authors = ObjectSelect.query(Author.class).select(context);
assertEquals(2, authors.size());
}
@Test
public void givenAuthor_whenUpdating_thenWeGetAnUpatedeAuthor() {
Author author = context.newObject(Author.class);
author.setName("Paul");
context.commitChanges();
Author expectedAuthor = ObjectSelect.query(Author.class)
.where(Author.NAME.eq("Paul"))
.selectOne(context);
expectedAuthor.setName("Garcia");
context.commitChanges();
assertEquals(author.getName(), expectedAuthor.getName());
}
@Test
public void givenAuthor_whenDeleting_thenWeLostHisDetails() {
Author author = context.newObject(Author.class);
author.setName("Paul");
context.commitChanges();
Author savedAuthor = ObjectSelect.query(Author.class)
.where(Author.NAME.eq("Paul")).selectOne(context);
if(savedAuthor != null) {
context.deleteObjects(author);
context.commitChanges();
}
Author expectedAuthor = ObjectSelect.query(Author.class)
.where(Author.NAME.eq("Paul")).selectOne(context);
assertNull(expectedAuthor);
}
@Test
public void givenAuthor_whenAttachingToArticle_thenTheRelationIsMade() {
Author author = context.newObject(Author.class);
author.setName("Paul");
Article article = context.newObject(Article.class);
article.setTitle("My post title");
article.setContent("The content");
article.setAuthor(author);
context.commitChanges();
Author expectedAuthor = ObjectSelect.query(Author.class)
.where(Author.NAME.eq("Paul"))
.selectOne(context);
Article expectedArticle = (expectedAuthor.getArticles()).get(0);
assertEquals(article.getTitle(), expectedArticle.getTitle());
}
}
@@ -0,0 +1,11 @@
=========
## Core Java Persistence Examples
### Relevant Articles:
- [Introduction to JDBC](http://www.baeldung.com/java-jdbc)
- [Batch Processing in JDBC](http://www.baeldung.com/jdbc-batch-processing)
- [Introduction to the JDBC RowSet Interface in Java](http://www.baeldung.com/java-jdbc-rowset)
- [A Simple Guide to Connection Pooling in Java](https://www.baeldung.com/java-connection-pooling)
- [Guide to the JDBC ResultSet Interface](https://www.baeldung.com/jdbc-resultset)
- [Types of SQL Joins](https://www.baeldung.com/sql-joins)
@@ -0,0 +1,83 @@
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.baeldung.core-java-persistence</groupId>
<artifactId>core-java-persistence</artifactId>
<version>0.1.0-SNAPSHOT</version>
<name>core-java-persistence</name>
<packaging>jar</packaging>
<parent>
<groupId>com.baeldung</groupId>
<artifactId>parent-java</artifactId>
<version>0.0.1-SNAPSHOT</version>
<relativePath>../../parent-java</relativePath>
</parent>
<dependencies>
<dependency>
<groupId>org.postgresql</groupId>
<artifactId>postgresql</artifactId>
<version>${postgresql.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.assertj</groupId>
<artifactId>assertj-core</artifactId>
<version>${assertj-core.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>
<version>${h2.version}</version>
</dependency>
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-dbcp2</artifactId>
<version>${commons-dbcp2.version}</version>
</dependency>
<dependency>
<groupId>com.zaxxer</groupId>
<artifactId>HikariCP</artifactId>
<version>${HikariCP.version}</version>
</dependency>
<dependency>
<groupId>com.mchange</groupId>
<artifactId>c3p0</artifactId>
<version>${c3p0.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>${springframework.spring-web.version}</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
<version>${springframework.boot.spring-boot-starter.version}</version>
</dependency>
</dependencies>
<build>
<finalName>core-java-persistence</finalName>
<resources>
<resource>
<directory>src/main/resources</directory>
<filtering>true</filtering>
</resource>
</resources>
</build>
<properties>
<postgresql.version>42.2.5.jre7</postgresql.version>
<mysql-connector.version>8.0.15</mysql-connector.version>
<assertj-core.version>3.10.0</assertj-core.version>
<commons-dbcp2.version>2.4.0</commons-dbcp2.version>
<HikariCP.version>3.2.0</HikariCP.version>
<c3p0.version>0.9.5.2</c3p0.version>
<springframework.boot.spring-boot-starter.version>1.5.8.RELEASE</springframework.boot.spring-boot-starter.version>
<springframework.spring-web.version>4.3.4.RELEASE</springframework.spring-web.version>
</properties>
</project>
@@ -0,0 +1,92 @@
package com.baeldung.connectionpool;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
public class BasicConnectionPool implements ConnectionPool {
private final String url;
private final String user;
private final String password;
private final List<Connection> connectionPool;
private final List<Connection> usedConnections = new ArrayList<>();
private static final int INITIAL_POOL_SIZE = 10;
private final int MAX_POOL_SIZE = 20;
public static BasicConnectionPool create(String url, String user, String password) throws SQLException {
List<Connection> pool = new ArrayList<>(INITIAL_POOL_SIZE);
for (int i = 0; i < INITIAL_POOL_SIZE; i++) {
pool.add(createConnection(url, user, password));
}
return new BasicConnectionPool(url, user, password, pool);
}
private BasicConnectionPool(String url, String user, String password, List<Connection> connectionPool) {
this.url = url;
this.user = user;
this.password = password;
this.connectionPool = connectionPool;
}
@Override
public Connection getConnection() throws SQLException {
if (connectionPool.isEmpty()) {
if (usedConnections.size() < MAX_POOL_SIZE) {
connectionPool.add(createConnection(url, user, password));
} else {
throw new RuntimeException("Maximum pool size reached, no available connections!");
}
}
Connection connection = connectionPool.remove(connectionPool.size() - 1);
usedConnections.add(connection);
return connection;
}
@Override
public boolean releaseConnection(Connection connection) {
connectionPool.add(connection);
return usedConnections.remove(connection);
}
private static Connection createConnection(String url, String user, String password) throws SQLException {
return DriverManager.getConnection(url, user, password);
}
@Override
public int getSize() {
return connectionPool.size() + usedConnections.size();
}
@Override
public List<Connection> getConnectionPool() {
return connectionPool;
}
@Override
public String getUrl() {
return url;
}
@Override
public String getUser() {
return user;
}
@Override
public String getPassword() {
return password;
}
@Override
public void shutdown() throws SQLException {
usedConnections.forEach(this::releaseConnection);
for (Connection c : connectionPool) {
c.close();
}
connectionPool.clear();
}
}
@@ -0,0 +1,28 @@
package com.baeldung.connectionpool;
import com.mchange.v2.c3p0.ComboPooledDataSource;
import java.beans.PropertyVetoException;
import java.sql.Connection;
import java.sql.SQLException;
public class C3poDataSource {
private static final ComboPooledDataSource cpds = new ComboPooledDataSource();
static {
try {
cpds.setDriverClass("org.h2.Driver");
cpds.setJdbcUrl("jdbc:h2:mem:test");
cpds.setUser("user");
cpds.setPassword("password");
} catch (PropertyVetoException e) {
e.printStackTrace();
}
}
public static Connection getConnection() throws SQLException {
return cpds.getConnection();
}
private C3poDataSource(){}
}
@@ -0,0 +1,24 @@
package com.baeldung.connectionpool;
import java.sql.Connection;
import java.sql.SQLException;
import java.util.List;
public interface ConnectionPool {
Connection getConnection() throws SQLException;
boolean releaseConnection(Connection connection);
List<Connection> getConnectionPool();
int getSize();
String getUrl();
String getUser();
String getPassword();
void shutdown() throws SQLException;;
}
@@ -0,0 +1,25 @@
package com.baeldung.connectionpool;
import java.sql.Connection;
import java.sql.SQLException;
import org.apache.commons.dbcp2.BasicDataSource;
public class DBCPDataSource {
private static final BasicDataSource ds = new BasicDataSource();
static {
ds.setUrl("jdbc:h2:mem:test");
ds.setUsername("user");
ds.setPassword("password");
ds.setMinIdle(5);
ds.setMaxIdle(10);
ds.setMaxOpenPreparedStatements(100);
}
public static Connection getConnection() throws SQLException {
return ds.getConnection();
}
private DBCPDataSource(){}
}
@@ -0,0 +1,28 @@
package com.baeldung.connectionpool;
import com.zaxxer.hikari.HikariConfig;
import com.zaxxer.hikari.HikariDataSource;
import java.sql.Connection;
import java.sql.SQLException;
public class HikariCPDataSource {
private static final HikariConfig config = new HikariConfig();
private static final HikariDataSource ds;
static {
config.setJdbcUrl("jdbc:h2:mem:test");
config.setUsername("user");
config.setPassword("password");
config.addDataSourceProperty("cachePrepStmts", "true");
config.addDataSourceProperty("prepStmtCacheSize", "250");
config.addDataSourceProperty("prepStmtCacheSqlLimit", "2048");
ds = new HikariDataSource(config);
}
public static Connection getConnection() throws SQLException {
return ds.getConnection();
}
private HikariCPDataSource(){}
}
@@ -0,0 +1,96 @@
package com.baeldung.jdbc;
import java.sql.*;
import java.util.UUID;
public class BatchProcessing {
private final String[] EMPLOYEES = new String[]{"Zuck","Mike","Larry","Musk","Steve"};
private final String[] DESIGNATIONS = new String[]{"CFO","CSO","CTO","CEO","CMO"};
private final String[] ADDRESSES = new String[]{"China","York","Diego","Carolina","India"};
private Connection connection;
public void getConnection(){
try {
Class.forName("org.h2.Driver");
connection = DriverManager.getConnection("jdbc:h2:mem:db", "SA", "");
connection.setAutoCommit(false);
} catch (Exception e) {
e.printStackTrace(System.out);
}
}
public void createTables(){
try {
connection.createStatement().executeUpdate("create table EMPLOYEE (ID VARCHAR(36), NAME VARCHAR(45), DESIGNATION VARCHAR(15))");
connection.createStatement().executeUpdate("create table EMP_ADDRESS (ID VARCHAR(36), EMP_ID VARCHAR(36), ADDRESS VARCHAR(45))");
System.out.println("Tables Created!!!");
} catch (SQLException e) {
e.printStackTrace(System.out);
}
}
public void useStatement(){
try {
String insertEmployeeSQL = "INSERT INTO EMPLOYEE(ID, NAME, DESIGNATION) VALUES ('%s','%s','%s');";
String insertEmployeeAddrSQL = "INSERT INTO EMP_ADDRESS(ID, EMP_ID, ADDRESS) VALUES ('%s','%s','%s');";
Statement statement = connection.createStatement();
for(int i = 0; i < EMPLOYEES.length; i++){
String employeeId = UUID.randomUUID().toString();
statement.addBatch(String.format(insertEmployeeSQL, employeeId, EMPLOYEES[i],DESIGNATIONS[i]));
statement.addBatch(String.format(insertEmployeeAddrSQL, UUID.randomUUID().toString(),employeeId,ADDRESSES[i]));
}
statement.executeBatch();
connection.commit();
} catch (Exception e) {
try {
connection.rollback();
} catch (SQLException ex) {
System.out.println("Error during rollback");
System.out.println(ex.getMessage());
}
e.printStackTrace(System.out);
}
}
public void usePreparedStatement(){
try {
String insertEmployeeSQL = "INSERT INTO EMPLOYEE(ID, NAME, DESIGNATION) VALUES (?,?,?);";
String insertEmployeeAddrSQL = "INSERT INTO EMP_ADDRESS(ID, EMP_ID, ADDRESS) VALUES (?,?,?);";
PreparedStatement employeeStmt = connection.prepareStatement(insertEmployeeSQL);
PreparedStatement empAddressStmt = connection.prepareStatement(insertEmployeeAddrSQL);
for(int i = 0; i < EMPLOYEES.length; i++){
String employeeId = UUID.randomUUID().toString();
employeeStmt.setString(1,employeeId);
employeeStmt.setString(2,EMPLOYEES[i]);
employeeStmt.setString(3,DESIGNATIONS[i]);
employeeStmt.addBatch();
empAddressStmt.setString(1,UUID.randomUUID().toString());
empAddressStmt.setString(2,employeeId);
empAddressStmt.setString(3,ADDRESSES[i]);
empAddressStmt.addBatch();
}
employeeStmt.executeBatch();
empAddressStmt.executeBatch();
connection.commit();
} catch (Exception e) {
try {
connection.rollback();
} catch (SQLException ex) {
System.out.println("Error during rollback");
System.out.println(ex.getMessage());
}
e.printStackTrace(System.out);
}
}
public static void main(String[] args) {
BatchProcessing batchProcessing = new BatchProcessing();
batchProcessing.getConnection();
batchProcessing.createTables();
batchProcessing.useStatement();
batchProcessing.usePreparedStatement();
}
}
@@ -0,0 +1,70 @@
package com.baeldung.jdbc;
import java.util.Objects;
public class Employee {
private int id;
private String name;
private String position;
private double salary;
public Employee() {
}
public Employee(int id, String name, double salary, String position) {
this.id = id;
this.name = name;
this.salary = salary;
this.position = position;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public double getSalary() {
return salary;
}
public void setSalary(double salary) {
this.salary = salary;
}
public String getPosition() {
return position;
}
public void setPosition(String position) {
this.position = position;
}
@Override
public int hashCode() {
return Objects.hash(id, name, position, salary);
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
Employee other = (Employee) obj;
return id == other.id && Objects.equals(name, other.name) && Objects.equals(position, other.position) && Double.doubleToLongBits(salary) == Double.doubleToLongBits(other.salary);
}
}
@@ -0,0 +1,41 @@
package com.baeldung.jdbc.joins;
class ArticleWithAuthor {
private String title;
private String authorFirstName;
private String authorLastName;
public ArticleWithAuthor(String title, String authorFirstName, String authorLastName) {
this.title = title;
this.authorFirstName = authorFirstName;
this.authorLastName = authorLastName;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getAuthorFirstName() {
return authorFirstName;
}
public void setAuthorFirstName(String authorFirstName) {
this.authorFirstName = authorFirstName;
}
public String getAuthorLastName() {
return authorLastName;
}
public void setAuthorLastName(String authorLastName) {
this.authorLastName = authorLastName;
}
}
@@ -0,0 +1,61 @@
package com.baeldung.jdbc.joins;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.ArrayList;
import java.util.List;
class ArticleWithAuthorDAO {
private static final String QUERY_TEMPLATE = "SELECT ARTICLE.TITLE, AUTHOR.LAST_NAME, AUTHOR.FIRST_NAME FROM ARTICLE %s AUTHOR ON AUTHOR.id=ARTICLE.AUTHOR_ID";
private final Connection connection;
ArticleWithAuthorDAO(Connection connection) {
this.connection = connection;
}
List<ArticleWithAuthor> articleInnerJoinAuthor() {
String query = String.format(QUERY_TEMPLATE, "INNER JOIN");
return executeQuery(query);
}
List<ArticleWithAuthor> articleLeftJoinAuthor() {
String query = String.format(QUERY_TEMPLATE, "LEFT JOIN");
return executeQuery(query);
}
List<ArticleWithAuthor> articleRightJoinAuthor() {
String query = String.format(QUERY_TEMPLATE, "RIGHT JOIN");
return executeQuery(query);
}
List<ArticleWithAuthor> articleFullJoinAuthor() {
String query = String.format(QUERY_TEMPLATE, "FULL JOIN");
return executeQuery(query);
}
private List<ArticleWithAuthor> executeQuery(String query) {
try (Statement statement = connection.createStatement()) {
ResultSet resultSet = statement.executeQuery(query);
return mapToList(resultSet);
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
private List<ArticleWithAuthor> mapToList(ResultSet resultSet) throws SQLException {
List<ArticleWithAuthor> list = new ArrayList<>();
while (resultSet.next()) {
ArticleWithAuthor articleWithAuthor = new ArticleWithAuthor(
resultSet.getString("TITLE"),
resultSet.getString("FIRST_NAME"),
resultSet.getString("LAST_NAME")
);
list.add(articleWithAuthor);
}
return list;
}
}
@@ -0,0 +1,51 @@
package com.baeldung.jdbcrowset;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;
import java.sql.Statement;
import javax.sql.rowset.JdbcRowSet;
import javax.sql.rowset.RowSetFactory;
import javax.sql.rowset.RowSetProvider;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.context.annotation.Configuration;
@Configuration
@EnableAutoConfiguration
public class DatabaseConfiguration {
public static Connection geth2Connection() throws Exception {
Class.forName("org.h2.Driver");
System.out.println("Driver Loaded.");
String url = "jdbc:h2:mem:testdb";
return DriverManager.getConnection(url, "sa", "");
}
public static void initDatabase(Statement stmt) throws SQLException{
int iter = 1;
while(iter<=5){
String customer = "Customer"+iter;
String sql ="INSERT INTO customers(id, name) VALUES ("+iter+ ",'"+customer+"');";
System.out.println("here is sql statmeent for execution: " + sql);
stmt.executeUpdate(sql);
iter++;
}
int iterb = 1;
while(iterb<=5){
String associate = "Associate"+iter;
String sql = "INSERT INTO associates(id, name) VALUES("+iterb+",'"+associate+"');";
System.out.println("here is sql statement for associate:"+ sql);
stmt.executeUpdate(sql);
iterb++;
}
}
}
@@ -0,0 +1,24 @@
package com.baeldung.jdbcrowset;
import javax.sql.RowSetEvent;
import javax.sql.RowSetListener;
public class ExampleListener implements RowSetListener {
public void cursorMoved(RowSetEvent event) {
System.out.println("ExampleListener alerted of cursorMoved event");
System.out.println(event.toString());
}
public void rowChanged(RowSetEvent event) {
System.out.println("ExampleListener alerted of rowChanged event");
System.out.println(event.toString());
}
public void rowSetChanged(RowSetEvent event) {
System.out.println("ExampleListener alerted of rowSetChanged event");
System.out.println(event.toString());
}
}
@@ -0,0 +1,46 @@
package com.baeldung.jdbcrowset;
import java.sql.SQLException;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.sql.RowSet;
import javax.sql.rowset.Predicate;
public class FilterExample implements Predicate {
private Pattern pattern;
public FilterExample(String regexQuery) {
if (regexQuery != null && !regexQuery.isEmpty()) {
pattern = Pattern.compile(regexQuery);
}
}
public boolean evaluate(RowSet rs) {
try {
if (!rs.isAfterLast()) {
String name = rs.getString("name");
System.out.println(String.format(
"Searching for pattern '%s' in %s", pattern.toString(),
name));
Matcher matcher = pattern.matcher(name);
return matcher.matches();
} else
return false;
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
public boolean evaluate(Object value, int column) throws SQLException {
throw new UnsupportedOperationException("This operation is unsupported.");
}
public boolean evaluate(Object value, String columnName)
throws SQLException {
throw new UnsupportedOperationException("This operation is unsupported.");
}
}
@@ -0,0 +1,139 @@
package com.baeldung.jdbcrowset;
import java.io.FileOutputStream;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;
import java.sql.Statement;
import com.sun.rowset.*;
import javax.sql.rowset.CachedRowSet;
import javax.sql.rowset.FilteredRowSet;
import javax.sql.rowset.JdbcRowSet;
import javax.sql.rowset.JoinRowSet;
import javax.sql.rowset.RowSetFactory;
import javax.sql.rowset.RowSetProvider;
import javax.sql.rowset.WebRowSet;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
@SpringBootApplication
public class JdbcRowsetApplication {
public static void main(String[] args) throws Exception {
SpringApplication.run(JdbcRowsetApplication.class, args);
Statement stmt = null;
try {
Connection conn = DatabaseConfiguration.geth2Connection();
String drop = "DROP TABLE IF EXISTS customers, associates;";
String schema = "CREATE TABLE customers (id INT NOT NULL, name VARCHAR(50) NOT NULL, PRIMARY KEY (id)); ";
String schemapartb = "CREATE TABLE associates (id INT NOT NULL, name VARCHAR(50) NOT NULL, PRIMARY KEY (id));";
stmt = conn.createStatement();
stmt.executeUpdate(drop);
stmt.executeUpdate(schema);
stmt.executeUpdate(schemapartb);
// insert data
DatabaseConfiguration.initDatabase(stmt);
// JdbcRowSet Example
String sql = "SELECT * FROM customers";
JdbcRowSet jdbcRS;
jdbcRS = new JdbcRowSetImpl(conn);
jdbcRS.setType(ResultSet.TYPE_SCROLL_INSENSITIVE);
jdbcRS.setCommand(sql);
jdbcRS.execute();
jdbcRS.addRowSetListener(new ExampleListener());
while (jdbcRS.next()) {
// each call to next, generates a cursorMoved event
System.out.println("id=" + jdbcRS.getString(1));
System.out.println("name=" + jdbcRS.getString(2));
}
// CachedRowSet Example
String username = "sa";
String password = "";
String url = "jdbc:h2:mem:testdb";
CachedRowSet crs = new CachedRowSetImpl();
crs.setUsername(username);
crs.setPassword(password);
crs.setUrl(url);
crs.setCommand(sql);
crs.execute();
crs.addRowSetListener(new ExampleListener());
while (crs.next()) {
if (crs.getInt("id") == 1) {
System.out.println("CRS found customer1 and will remove the record.");
crs.deleteRow();
break;
}
}
// WebRowSet example
WebRowSet wrs = new WebRowSetImpl();
wrs.setUsername(username);
wrs.setPassword(password);
wrs.setUrl(url);
wrs.setCommand(sql);
wrs.execute();
FileOutputStream ostream = new FileOutputStream("customers.xml");
wrs.writeXml(ostream);
// JoinRowSet example
CachedRowSetImpl customers = new CachedRowSetImpl();
customers.setUsername(username);
customers.setPassword(password);
customers.setUrl(url);
customers.setCommand(sql);
customers.execute();
CachedRowSetImpl associates = new CachedRowSetImpl();
associates.setUsername(username);
associates.setPassword(password);
associates.setUrl(url);
String associatesSQL = "SELECT * FROM associates";
associates.setCommand(associatesSQL);
associates.execute();
JoinRowSet jrs = new JoinRowSetImpl();
final String ID = "id";
final String NAME = "name";
jrs.addRowSet(customers, ID);
jrs.addRowSet(associates, ID);
jrs.last();
System.out.println("Total rows: " + jrs.getRow());
jrs.beforeFirst();
while (jrs.next()) {
String string1 = jrs.getString(ID);
String string2 = jrs.getString(NAME);
System.out.println("ID: " + string1 + ", NAME: " + string2);
}
// FilteredRowSet example
RowSetFactory rsf = RowSetProvider.newFactory();
FilteredRowSet frs = rsf.createFilteredRowSet();
frs.setCommand("select * from customers");
frs.execute(conn);
frs.setFilter(new FilterExample("^[A-C].*"));
ResultSetMetaData rsmd = frs.getMetaData();
int columncount = rsmd.getColumnCount();
while (frs.next()) {
for (int i = 1; i <= columncount; i++) {
System.out.println(rsmd.getColumnLabel(i) + " = " + frs.getObject(i) + " ");
}
}
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
@@ -0,0 +1,13 @@
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
</pattern>
</encoder>
</appender>
<root level="INFO">
<appender-ref ref="STDOUT" />
</root>
</configuration>
@@ -0,0 +1,67 @@
package com.baeldung.connectionpool;
import java.sql.Connection;
import java.sql.SQLException;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
import org.junit.BeforeClass;
import org.junit.Test;
public class BasicConnectionPoolUnitTest {
private static ConnectionPool connectionPool;
@BeforeClass
public static void setUpBasicConnectionPoolInstance() throws SQLException {
connectionPool = BasicConnectionPool.create("jdbc:h2:mem:test", "user", "password");
}
@Test
public void givenBasicConnectionPoolInstance_whenCalledgetConnection_thenCorrect() throws Exception {
assertTrue(connectionPool.getConnection().isValid(1));
}
@Test
public void givenBasicConnectionPoolInstance_whenCalledreleaseConnection_thenCorrect() throws Exception {
Connection connection = connectionPool.getConnection();
assertThat(connectionPool.releaseConnection(connection)).isTrue();
}
@Test
public void givenBasicConnectionPoolInstance_whenCalledgetUrl_thenCorrect() {
assertThat(connectionPool.getUrl()).isEqualTo("jdbc:h2:mem:test");
}
@Test
public void givenBasicConnectionPoolInstance_whenCalledgetUser_thenCorrect() {
assertThat(connectionPool.getUser()).isEqualTo("user");
}
@Test
public void givenBasicConnectionPoolInstance_whenCalledgetPassword_thenCorrect() {
assertThat(connectionPool.getPassword()).isEqualTo("password");
}
@Test(expected = RuntimeException.class)
public void givenBasicConnectionPoolInstance_whenAskedForMoreThanMax_thenError() throws Exception {
// this test needs to be independent so it doesn't share the same connection pool as other tests
ConnectionPool cp = BasicConnectionPool.create("jdbc:h2:mem:test", "user", "password");
final int MAX_POOL_SIZE = 20;
for (int i = 0; i < MAX_POOL_SIZE + 1; i++) {
cp.getConnection();
}
fail();
}
@Test
public void givenBasicConnectionPoolInstance_whenSutdown_thenEmpty() throws Exception {
ConnectionPool cp = BasicConnectionPool.create("jdbc:h2:mem:test", "user", "password");
assertThat(((BasicConnectionPool)cp).getSize()).isEqualTo(10);
((BasicConnectionPool) cp).shutdown();
assertThat(((BasicConnectionPool)cp).getSize()).isEqualTo(0);
}
}
@@ -0,0 +1,13 @@
package com.baeldung.connectionpool;
import java.sql.SQLException;
import static org.junit.Assert.assertTrue;
import org.junit.Test;
public class C3poDataSourceUnitTest {
@Test
public void givenC3poDataSourceClass_whenCalledgetConnection_thenCorrect() throws SQLException {
assertTrue(C3poDataSource.getConnection().isValid(1));
}
}
@@ -0,0 +1,13 @@
package com.baeldung.connectionpool;
import java.sql.SQLException;
import static org.junit.Assert.assertTrue;
import org.junit.Test;
public class DBCPDataSourceUnitTest {
@Test
public void givenDBCPDataSourceClass_whenCalledgetConnection_thenCorrect() throws SQLException {
assertTrue(DBCPDataSource.getConnection().isValid(1));
}
}
@@ -0,0 +1,13 @@
package com.baeldung.connectionpool;
import java.sql.SQLException;
import static org.junit.Assert.assertTrue;
import org.junit.Test;
public class HikariCPDataSourceUnitTest {
@Test
public void givenHikariDataSourceClass_whenCalledgetConnection_thenCorrect() throws SQLException {
assertTrue(HikariCPDataSource.getConnection().isValid(1));
}
}
@@ -0,0 +1,71 @@
package com.baeldung.jdbc;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.mockito.MockitoAnnotations;
import org.mockito.junit.MockitoJUnitRunner;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.Statement;
@RunWith(MockitoJUnitRunner.class)
public class BatchProcessingLiveTest {
@InjectMocks
private BatchProcessing target = new BatchProcessing();
@Mock
private Connection connection;
@Mock
private Statement statement;
@Mock
private PreparedStatement employeeStatement;
@Mock
private PreparedStatement employeeAddressStatement;
@Before
public void before(){
MockitoAnnotations.initMocks(this);
}
@Test
public void when_useStatement_thenInsertData_success() throws Exception {
Mockito.when(connection.createStatement()).thenReturn(statement);
target.useStatement();
}
@Test
public void when_useStatement_ifThrowException_thenCatchException() throws Exception {
Mockito.when(connection.createStatement()).thenThrow(new RuntimeException());
target.useStatement();
}
@Test
public void when_usePreparedStatement_thenInsertData_success() throws Exception {
String insertEmployeeSQL = "INSERT INTO EMPLOYEE(ID, NAME, DESIGNATION) VALUES (?,?,?);";
String insertEmployeeAddrSQL = "INSERT INTO EMP_ADDRESS(ID, EMP_ID, ADDRESS) VALUES (?,?,?);";
Mockito.when(connection.prepareStatement(insertEmployeeSQL)).thenReturn(employeeStatement);
Mockito.when(connection.prepareStatement(insertEmployeeAddrSQL)).thenReturn(employeeAddressStatement);
target.usePreparedStatement();
}
@Test
public void when_usePreparedStatement_ifThrowException_thenCatchException() throws Exception {
String insertEmployeeSQL = "INSERT INTO EMPLOYEE(ID, NAME, DESIGNATION) VALUES (?,?,?);";
String insertEmployeeAddrSQL = "INSERT INTO EMP_ADDRESS(ID, EMP_ID, ADDRESS) VALUES (?,?,?);";
Mockito.when(connection.prepareStatement(insertEmployeeSQL)).thenReturn(employeeStatement);
Mockito.when(connection.prepareStatement(insertEmployeeAddrSQL)).thenThrow(new RuntimeException());
target.usePreparedStatement();
}
}
@@ -0,0 +1,158 @@
package com.baeldung.jdbc;
import static org.junit.Assert.*;
import java.sql.CallableStatement;
import java.sql.Connection;
import java.sql.DatabaseMetaData;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;
import java.sql.Statement;
import java.sql.Types;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.IntStream;
import org.apache.log4j.Logger;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
public class JdbcLiveTest {
private static final Logger LOG = Logger.getLogger(JdbcLiveTest.class);
private Connection con;
@Before
public void setup() throws ClassNotFoundException, SQLException {
Class.forName("com.mysql.cj.jdbc.Driver");
con = DriverManager.getConnection("jdbc:mysql://localhost:3306/myDb?noAccessToProcedureBodies=true", "user1", "pass");
Statement stmt = con.createStatement();
String tableSql = "CREATE TABLE IF NOT EXISTS employees (emp_id int PRIMARY KEY AUTO_INCREMENT, name varchar(30), position varchar(30), salary double)";
stmt.execute(tableSql);
}
@Test
public void whenInsertUpdateRecord_thenCorrect() throws SQLException {
Statement stmt = con.createStatement();
String insertSql = "INSERT INTO employees(name, position, salary) values ('john', 'developer', 2000)";
stmt.executeUpdate(insertSql);
String selectSql = "SELECT * FROM employees";
ResultSet resultSet = stmt.executeQuery(selectSql);
List<Employee> employees = new ArrayList<>();
while (resultSet.next()) {
Employee emp = new Employee();
emp.setId(resultSet.getInt("emp_id"));
emp.setName(resultSet.getString("name"));
emp.setSalary(resultSet.getDouble("salary"));
emp.setPosition(resultSet.getString("position"));
employees.add(emp);
}
assertEquals("employees list size incorrect", 1, employees.size());
assertEquals("name incorrect", "john", employees.iterator().next().getName());
assertEquals("position incorrect", "developer", employees.iterator().next().getPosition());
assertEquals("salary incorrect", 2000, employees.iterator().next().getSalary(), 0.1);
Statement updatableStmt = con.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_UPDATABLE);
ResultSet updatableResultSet = updatableStmt.executeQuery(selectSql);
updatableResultSet.moveToInsertRow();
updatableResultSet.updateString("name", "mark");
updatableResultSet.updateString("position", "analyst");
updatableResultSet.updateDouble("salary", 2000);
updatableResultSet.insertRow();
String updatePositionSql = "UPDATE employees SET position=? WHERE emp_id=?";
PreparedStatement pstmt = con.prepareStatement(updatePositionSql);
pstmt.setString(1, "lead developer");
pstmt.setInt(2, 1);
String updateSalarySql = "UPDATE employees SET salary=? WHERE emp_id=?";
PreparedStatement pstmt2 = con.prepareStatement(updateSalarySql);
pstmt.setDouble(1, 3000);
pstmt.setInt(2, 1);
boolean autoCommit = con.getAutoCommit();
try {
con.setAutoCommit(false);
pstmt.executeUpdate();
pstmt2.executeUpdate();
con.commit();
} catch (SQLException exc) {
con.rollback();
} finally {
con.setAutoCommit(autoCommit);
}
}
@Test
public void whenCallProcedure_thenCorrect() {
try {
String preparedSql = "{call insertEmployee(?,?,?,?)}";
CallableStatement cstmt = con.prepareCall(preparedSql);
cstmt.setString(2, "ana");
cstmt.setString(3, "tester");
cstmt.setDouble(4, 2000);
cstmt.registerOutParameter(1, Types.INTEGER);
cstmt.execute();
int new_id = cstmt.getInt(1);
assertTrue(new_id > 0);
} catch (SQLException exc) {
LOG.error("Procedure incorrect or does not exist!");
}
}
@Test
public void whenReadMetadata_thenCorrect() throws SQLException {
DatabaseMetaData dbmd = con.getMetaData();
ResultSet tablesResultSet = dbmd.getTables(null, null, "%", null);
while (tablesResultSet.next()) {
LOG.info(tablesResultSet.getString("TABLE_NAME"));
}
String selectSql = "SELECT * FROM employees";
Statement stmt = con.createStatement();
ResultSet resultSet = stmt.executeQuery(selectSql);
ResultSetMetaData rsmd = resultSet.getMetaData();
int nrColumns = rsmd.getColumnCount();
assertEquals(nrColumns, 4);
IntStream.range(1, nrColumns).forEach(i -> {
try {
LOG.info(rsmd.getColumnName(i));
} catch (SQLException e) {
e.printStackTrace();
}
});
}
@After
public void closeConnection() throws SQLException {
Statement updatableStmt = con.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_UPDATABLE);
ResultSet updatableResultSet = updatableStmt.executeQuery("SELECT * FROM employees");
while (updatableResultSet.next()) {
updatableResultSet.deleteRow();
}
con.close();
}
}
@@ -0,0 +1,359 @@
package com.baeldung.jdbc;
import static org.junit.Assert.assertEquals;
import java.sql.Connection;
import java.sql.DatabaseMetaData;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.ArrayList;
import java.util.List;
import org.apache.log4j.Logger;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.FixMethodOrder;
import org.junit.Test;
import org.junit.runners.MethodSorters;
import junit.framework.Assert;
@FixMethodOrder(MethodSorters.NAME_ASCENDING)
public class ResultSetLiveTest {
private static final Logger logger = Logger.getLogger(ResultSetLiveTest.class);
private final Employee expectedEmployee1 = new Employee(1, "John", 1000.0, "Developer");
private final Employee updatedEmployee1 = new Employee(1, "John", 1100.0, "Developer");
private final Employee expectedEmployee2 = new Employee(2, "Chris", 925.0, "DBA");
private final int rowCount = 2;
private static Connection dbConnection;
@BeforeClass
public static void setup() throws ClassNotFoundException, SQLException {
Class.forName("com.mysql.cj.jdbc.Driver");
dbConnection = DriverManager.getConnection("jdbc:mysql://localhost:3306/myDB?noAccessToProcedureBodies=true", "user1", "pass");
String tableSql = "CREATE TABLE IF NOT EXISTS employees (emp_id int PRIMARY KEY AUTO_INCREMENT, name varchar(30), position varchar(30), salary double)";
try (Statement stmt = dbConnection.createStatement()) {
stmt.execute(tableSql);
try (PreparedStatement pstmt = dbConnection.prepareStatement("INSERT INTO employees(name, position, salary) values ('John', 'Developer', 1000.0)")) {
pstmt.executeUpdate();
}
}
}
@Test
public void givenDbConnectionA_whenRetreiveByColumnNames_thenCorrect() throws SQLException {
Employee employee = null;
try (PreparedStatement pstmt = dbConnection.prepareStatement("select * from employees"); ResultSet rs = pstmt.executeQuery()) {
while (rs.next()) {
String name = rs.getString("name");
Integer empId = rs.getInt("emp_id");
Double salary = rs.getDouble("salary");
String position = rs.getString("position");
employee = new Employee(empId, name, salary, position);
}
}
assertEquals("Employee information retreived by column names.", expectedEmployee1, employee);
}
@Test
public void givenDbConnectionB_whenRetreiveByColumnIds_thenCorrect() throws SQLException {
Employee employee = null;
try (PreparedStatement pstmt = dbConnection.prepareStatement("select * from employees"); ResultSet rs = pstmt.executeQuery()) {
while (rs.next()) {
Integer empId = rs.getInt(1);
String name = rs.getString(2);
String position = rs.getString(3);
Double salary = rs.getDouble(4);
employee = new Employee(empId, name, salary, position);
}
}
assertEquals("Employee information retreived by column ids.", expectedEmployee1, employee);
}
@Test
public void givenDbConnectionD_whenInsertRow_thenCorrect() throws SQLException {
int rowCount = 0;
try (PreparedStatement pstmt = dbConnection.prepareStatement("select * from employees", ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE); ResultSet rs = pstmt.executeQuery()) {
rs.moveToInsertRow();
rs.updateString("name", "Chris");
rs.updateString("position", "DBA");
rs.updateDouble("salary", 925.0);
rs.insertRow();
rs.moveToCurrentRow();
rs.last();
rowCount = rs.getRow();
}
assertEquals("Row Count after inserting a row", 2, rowCount);
}
private Employee populateResultSet(ResultSet rs) throws SQLException {
Employee employee;
String name = rs.getString("name");
Integer empId = rs.getInt("emp_id");
Double salary = rs.getDouble("salary");
String position = rs.getString("position");
employee = new Employee(empId, name, salary, position);
return employee;
}
@Test
public void givenDbConnectionE_whenRowCount_thenCorrect() throws SQLException {
int numOfRows = 0;
try (PreparedStatement pstmt = dbConnection.prepareStatement("select * from employees", ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE); ResultSet rs = pstmt.executeQuery()) {
rs.last();
numOfRows = rs.getRow();
}
assertEquals("Num of rows", rowCount, numOfRows);
}
@Test
public void givenDbConnectionG_whenAbsoluteNavigation_thenCorrect() throws SQLException {
Employee secondEmployee = null;
try (PreparedStatement pstmt = dbConnection.prepareStatement("select * from employees", ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE); ResultSet rs = pstmt.executeQuery()) {
rs.absolute(2);
secondEmployee = populateResultSet(rs);
}
assertEquals("Absolute navigation", expectedEmployee2, secondEmployee);
}
@Test
public void givenDbConnectionH_whenLastNavigation_thenCorrect() throws SQLException {
Employee secondEmployee = null;
try (PreparedStatement pstmt = dbConnection.prepareStatement("select * from employees", ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE); ResultSet rs = pstmt.executeQuery()) {
rs.last();
secondEmployee = populateResultSet(rs);
}
assertEquals("Using Last", expectedEmployee2, secondEmployee);
}
@Test
public void givenDbConnectionI_whenNavigation_thenCorrect() throws SQLException {
Employee firstEmployee = null;
try (PreparedStatement pstmt = dbConnection.prepareStatement("select * from employees", ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE); ResultSet rs = pstmt.executeQuery()) {
while (rs.next()) {
Employee employee = populateResultSet(rs);
}
rs.beforeFirst();
while (rs.next()) {
Employee employee = populateResultSet(rs);
}
rs.first();
while (rs.next()) {
Employee employee = populateResultSet(rs);
}
while (rs.previous()) {
Employee employee = populateResultSet(rs);
}
rs.afterLast();
while (rs.previous()) {
Employee employee = populateResultSet(rs);
}
rs.last();
while (rs.previous()) {
firstEmployee = populateResultSet(rs);
}
}
assertEquals("Several Navigation Options", updatedEmployee1, firstEmployee);
}
@Test
public void givenDbConnectionJ_whenClosedCursor_thenCorrect() throws SQLException {
Employee employee = null;
dbConnection.setHoldability(ResultSet.CLOSE_CURSORS_AT_COMMIT);
try (Statement pstmt = dbConnection.createStatement(ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE, ResultSet.CLOSE_CURSORS_AT_COMMIT)) {
dbConnection.setAutoCommit(false);
ResultSet rs = pstmt.executeQuery("select * from employees");
while (rs.next()) {
if (rs.getString("name")
.equalsIgnoreCase("john")) {
rs.updateString("position", "Senior Engineer");
rs.updateRow();
dbConnection.commit();
employee = populateResultSet(rs);
}
}
rs.last();
}
assertEquals("Update using closed cursor", "Senior Engineer", employee.getPosition());
}
@Test
public void givenDbConnectionK_whenUpdate_thenCorrect() throws SQLException {
Employee employee = null;
dbConnection.setHoldability(ResultSet.HOLD_CURSORS_OVER_COMMIT);
try (Statement pstmt = dbConnection.createStatement(ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE, ResultSet.HOLD_CURSORS_OVER_COMMIT)) {
dbConnection.setAutoCommit(false);
ResultSet rs = pstmt.executeQuery("select * from employees");
while (rs.next()) {
if (rs.getString("name")
.equalsIgnoreCase("john")) {
rs.updateString("name", "John Doe");
rs.updateRow();
dbConnection.commit();
employee = populateResultSet(rs);
}
}
rs.last();
}
assertEquals("Update using open cursor", "John Doe", employee.getName());
}
@Test
public void givenDbConnectionM_whenDelete_thenCorrect() throws SQLException {
int numOfRows = 0;
try (PreparedStatement pstmt = dbConnection.prepareStatement("select * from employees", ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE); ResultSet rs = pstmt.executeQuery()) {
rs.absolute(2);
rs.deleteRow();
}
try (PreparedStatement pstmt = dbConnection.prepareStatement("select * from employees", ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE); ResultSet rs = pstmt.executeQuery()) {
rs.last();
numOfRows = rs.getRow();
}
assertEquals("Deleted row", 1, numOfRows);
}
@Test
public void givenDbConnectionC_whenUpdate_thenCorrect() throws SQLException {
Employee employee = null;
try (PreparedStatement pstmt = dbConnection.prepareStatement("select * from employees", ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE); ResultSet rs = pstmt.executeQuery()) {
while (rs.next()) {
Assert.assertEquals(1100.0, rs.getDouble("salary"));
rs.updateDouble("salary", 1200.0);
rs.updateRow();
Assert.assertEquals(1200.0, rs.getDouble("salary"));
String name = rs.getString("name");
Integer empId = rs.getInt("emp_id");
Double salary = rs.getDouble("salary");
String position = rs.getString("position");
employee = new Employee(empId, name, salary, position);
}
}
}
@Test
public void givenDbConnectionC_whenUpdateByIndex_thenCorrect() throws SQLException {
Employee employee = null;
try (PreparedStatement pstmt = dbConnection.prepareStatement("select * from employees", ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE); ResultSet rs = pstmt.executeQuery()) {
while (rs.next()) {
Assert.assertEquals(1000.0, rs.getDouble(4));
rs.updateDouble(4, 1100.0);
rs.updateRow();
Assert.assertEquals(1100.0, rs.getDouble(4));
String name = rs.getString("name");
Integer empId = rs.getInt("emp_id");
Double salary = rs.getDouble("salary");
String position = rs.getString("position");
employee = new Employee(empId, name, salary, position);
}
}
}
@Test
public void givenDbConnectionE_whenDBMetaInfo_thenCorrect() throws SQLException {
DatabaseMetaData dbmd = dbConnection.getMetaData();
boolean supportsTypeForward = dbmd.supportsResultSetType(ResultSet.TYPE_FORWARD_ONLY);
boolean supportsTypeScrollSensitive = dbmd.supportsResultSetType(ResultSet.TYPE_SCROLL_SENSITIVE);
boolean supportsTypeScrollInSensitive = dbmd.supportsResultSetType(ResultSet.TYPE_SCROLL_INSENSITIVE);
boolean supportsCloseCursorsAtCommit = dbmd.supportsResultSetHoldability(ResultSet.CLOSE_CURSORS_AT_COMMIT);
boolean supportsHoldCursorsAtCommit = dbmd.supportsResultSetHoldability(ResultSet.HOLD_CURSORS_OVER_COMMIT);
boolean concurrency4TypeFwdNConcurReadOnly = dbmd.supportsResultSetConcurrency(ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY);
boolean concurrency4TypeFwdNConcurUpdatable = dbmd.supportsResultSetConcurrency(ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_UPDATABLE);
boolean concurrency4TypeScrollInSensitiveNConcurUpdatable = dbmd.supportsResultSetConcurrency(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_UPDATABLE);
boolean concurrency4TypeScrollInSensitiveNConcurReadOnly = dbmd.supportsResultSetConcurrency(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY);
boolean concurrency4TypeScrollSensitiveNConcurUpdatable = dbmd.supportsResultSetConcurrency(ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE);
boolean concurrency4TypeScrollSensitiveNConcurReadOnly = dbmd.supportsResultSetConcurrency(ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_READ_ONLY);
int rsHoldability = dbmd.getResultSetHoldability();
assertEquals("checking scroll sensitivity and concur updates : ", true, concurrency4TypeScrollInSensitiveNConcurUpdatable);
}
@Test
public void givenDbConnectionF_whenRSMetaInfo_thenCorrect() throws SQLException {
int columnCount = 0;
try (PreparedStatement pstmt = dbConnection.prepareStatement("select * from employees", ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE); ResultSet rs = pstmt.executeQuery()) {
ResultSetMetaData metaData = rs.getMetaData();
columnCount = metaData.getColumnCount();
for (int i = 1; i <= columnCount; i++) {
String catalogName = metaData.getCatalogName(i);
String className = metaData.getColumnClassName(i);
String label = metaData.getColumnLabel(i);
String name = metaData.getColumnName(i);
String typeName = metaData.getColumnTypeName(i);
Integer type = metaData.getColumnType(i);
String tableName = metaData.getTableName(i);
String schemaName = metaData.getSchemaName(i);
boolean isAutoIncrement = metaData.isAutoIncrement(i);
boolean isCaseSensitive = metaData.isCaseSensitive(i);
boolean isCurrency = metaData.isCurrency(i);
boolean isDefiniteWritable = metaData.isDefinitelyWritable(i);
boolean isReadOnly = metaData.isReadOnly(i);
boolean isSearchable = metaData.isSearchable(i);
boolean isReadable = metaData.isReadOnly(i);
boolean isSigned = metaData.isSigned(i);
boolean isWritable = metaData.isWritable(i);
int nullable = metaData.isNullable(i);
}
}
assertEquals("column count", 4, columnCount);
}
@Test
public void givenDbConnectionL_whenFetch_thenCorrect() throws SQLException {
PreparedStatement pstmt = null;
ResultSet rs = null;
List<Employee> listOfEmployees = new ArrayList<Employee>();
try {
pstmt = dbConnection.prepareStatement("select * from employees", ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE);
pstmt.setFetchSize(1);
rs = pstmt.executeQuery();
rs.setFetchSize(1);
while (rs.next()) {
Employee employee = populateResultSet(rs);
listOfEmployees.add(employee);
}
} catch (Exception e) {
throw e;
} finally {
if (rs != null)
rs.close();
if (pstmt != null)
pstmt.close();
}
assertEquals(2, listOfEmployees.size());
}
@AfterClass
public static void closeConnection() throws SQLException {
PreparedStatement deleteStmt = dbConnection.prepareStatement("drop table employees", ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_UPDATABLE);
deleteStmt.execute();
dbConnection.close();
}
}
@@ -0,0 +1,89 @@
package com.baeldung.jdbc.joins;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class ArticleWithAuthorDAOLiveTest {
private Connection connection;
private ArticleWithAuthorDAO articleWithAuthorDAO;
@Before
public void setup() throws ClassNotFoundException, SQLException {
Class.forName("org.postgresql.Driver");
connection = DriverManager.getConnection("jdbc:postgresql://localhost:5432/myDb", "user", "pass");
articleWithAuthorDAO = new ArticleWithAuthorDAO(connection);
Statement statement = connection.createStatement();
String createAuthorSql = "CREATE TABLE IF NOT EXISTS AUTHOR (ID int NOT NULL PRIMARY KEY, FIRST_NAME varchar(255), LAST_NAME varchar(255));";
String createArticleSql = "CREATE TABLE IF NOT EXISTS ARTICLE (ID int NOT NULL PRIMARY KEY, TITLE varchar(255) NOT NULL, AUTHOR_ID int, FOREIGN KEY(AUTHOR_ID) REFERENCES AUTHOR(ID));";
statement.execute(createAuthorSql);
statement.execute(createArticleSql);
insertTestData(statement);
}
@Test
public void whenQueryWithInnerJoin_thenShouldReturnProperRows() {
List<ArticleWithAuthor> articleWithAuthorList = articleWithAuthorDAO.articleInnerJoinAuthor();
assertThat(articleWithAuthorList).hasSize(4);
assertThat(articleWithAuthorList).noneMatch(row -> row.getAuthorFirstName() == null || row.getTitle() == null);
}
@Test
public void whenQueryWithLeftJoin_thenShouldReturnProperRows() {
List<ArticleWithAuthor> articleWithAuthorList = articleWithAuthorDAO.articleLeftJoinAuthor();
assertThat(articleWithAuthorList).hasSize(5);
assertThat(articleWithAuthorList).anyMatch(row -> row.getAuthorFirstName() == null);
}
@Test
public void whenQueryWithRightJoin_thenShouldReturnProperRows() {
List<ArticleWithAuthor> articleWithAuthorList = articleWithAuthorDAO.articleRightJoinAuthor();
assertThat(articleWithAuthorList).hasSize(5);
assertThat(articleWithAuthorList).anyMatch(row -> row.getTitle() == null);
}
@Test
public void whenQueryWithFullJoin_thenShouldReturnProperRows() {
List<ArticleWithAuthor> articleWithAuthorList = articleWithAuthorDAO.articleFullJoinAuthor();
assertThat(articleWithAuthorList).hasSize(6);
assertThat(articleWithAuthorList).anyMatch(row -> row.getTitle() == null);
assertThat(articleWithAuthorList).anyMatch(row -> row.getAuthorFirstName() == null);
}
@After
public void cleanup() throws SQLException {
connection.createStatement().execute("DROP TABLE ARTICLE");
connection.createStatement().execute("DROP TABLE AUTHOR");
connection.close();
}
public void insertTestData(Statement statement) throws SQLException {
String insertAuthors = "INSERT INTO AUTHOR VALUES "
+ "(1, 'Siena', 'Kerr'),"
+ "(2, 'Daniele', 'Ferguson'),"
+ "(3, 'Luciano', 'Wise'),"
+ "(4, 'Jonas', 'Lugo');";
String insertArticles = "INSERT INTO ARTICLE VALUES "
+ "(1, 'First steps in Java', 1),"
+ "(2, 'SpringBoot tutorial', 1),"
+ "(3, 'Java 12 insights', null),"
+ "(4, 'SQL JOINS', 2),"
+ "(5, 'Introduction to Spring Security', 3);";
statement.execute(insertAuthors);
statement.execute(insertArticles);
}
}
@@ -0,0 +1,157 @@
package com.baeldung.jdbcrowset;
import java.io.FileOutputStream;
import java.io.IOException;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;
import java.sql.Statement;
import javax.sql.rowset.CachedRowSet;
import javax.sql.rowset.FilteredRowSet;
import javax.sql.rowset.JdbcRowSet;
import javax.sql.rowset.JoinRowSet;
import javax.sql.rowset.RowSetFactory;
import javax.sql.rowset.RowSetProvider;
import javax.sql.rowset.WebRowSet;
import org.junit.Before;
import org.junit.Test;
import com.sun.rowset.CachedRowSetImpl;
import com.sun.rowset.JdbcRowSetImpl;
import com.sun.rowset.JoinRowSetImpl;
import com.sun.rowset.WebRowSetImpl;
public class JdbcRowSetLiveTest {
Statement stmt = null;
String username = "sa";
String password = "";
String url = "jdbc:h2:mem:testdb";
String sql = "SELECT * FROM customers";
@Before
public void setup() throws Exception {
Connection conn = DatabaseConfiguration.geth2Connection();
String drop = "DROP TABLE IF EXISTS customers, associates;";
String schema = "CREATE TABLE customers (id INT NOT NULL, name VARCHAR(50) NOT NULL, PRIMARY KEY (id)); ";
String schemapartb = "CREATE TABLE associates (id INT NOT NULL, name VARCHAR(50) NOT NULL, PRIMARY KEY (id));";
stmt = conn.createStatement();
stmt.executeUpdate(drop);
stmt.executeUpdate(schema);
stmt.executeUpdate(schemapartb);
DatabaseConfiguration.initDatabase(stmt);
}
// JdbcRowSet Example
@Test
public void createJdbcRowSet_SelectCustomers_ThenCorrect() throws Exception {
String sql = "SELECT * FROM customers";
JdbcRowSet jdbcRS;
Connection conn = DatabaseConfiguration.geth2Connection();
jdbcRS = new JdbcRowSetImpl(conn);
jdbcRS.setType(ResultSet.TYPE_SCROLL_INSENSITIVE);
jdbcRS.setCommand(sql);
jdbcRS.execute();
jdbcRS.addRowSetListener(new ExampleListener());
while (jdbcRS.next()) {
// each call to next, generates a cursorMoved event
System.out.println("id=" + jdbcRS.getString(1));
System.out.println("name=" + jdbcRS.getString(2));
}
}
// CachedRowSet Example
@Test
public void createCachedRowSet_DeleteRecord_ThenCorrect() throws Exception {
CachedRowSet crs = new CachedRowSetImpl();
crs.setUsername(username);
crs.setPassword(password);
crs.setUrl(url);
crs.setCommand(sql);
crs.execute();
crs.addRowSetListener(new ExampleListener());
while (crs.next()) {
if (crs.getInt("id") == 1) {
System.out.println("CRS found customer1 and will remove the record.");
crs.deleteRow();
break;
}
}
}
// WebRowSet example
@Test
public void createWebRowSet_SelectCustomers_WritetoXML_ThenCorrect() throws SQLException, IOException {
WebRowSet wrs = new WebRowSetImpl();
wrs.setUsername(username);
wrs.setPassword(password);
wrs.setUrl(url);
wrs.setCommand(sql);
wrs.execute();
FileOutputStream ostream = new FileOutputStream("customers.xml");
wrs.writeXml(ostream);
}
// JoinRowSet example
@Test
public void createCachedRowSets_DoJoinRowSet_ThenCorrect() throws Exception {
CachedRowSetImpl customers = new CachedRowSetImpl();
customers.setUsername(username);
customers.setPassword(password);
customers.setUrl(url);
customers.setCommand(sql);
customers.execute();
CachedRowSetImpl associates = new CachedRowSetImpl();
associates.setUsername(username);
associates.setPassword(password);
associates.setUrl(url);
String associatesSQL = "SELECT * FROM associates";
associates.setCommand(associatesSQL);
associates.execute();
JoinRowSet jrs = new JoinRowSetImpl();
final String ID = "id";
final String NAME = "name";
jrs.addRowSet(customers, ID);
jrs.addRowSet(associates, ID);
jrs.last();
System.out.println("Total rows: " + jrs.getRow());
jrs.beforeFirst();
while (jrs.next()) {
String string1 = jrs.getString(ID);
String string2 = jrs.getString(NAME);
System.out.println("ID: " + string1 + ", NAME: " + string2);
}
}
// FilteredRowSet example
@Test
public void createFilteredRowSet_filterByRegexExpression_thenCorrect() throws Exception {
RowSetFactory rsf = RowSetProvider.newFactory();
FilteredRowSet frs = rsf.createFilteredRowSet();
frs.setCommand("select * from customers");
Connection conn = DatabaseConfiguration.geth2Connection();
frs.execute(conn);
frs.setFilter(new FilterExample("^[A-C].*"));
ResultSetMetaData rsmd = frs.getMetaData();
int columncount = rsmd.getColumnCount();
while (frs.next()) {
for (int i = 1; i <= columncount; i++) {
System.out.println(rsmd.getColumnLabel(i) + " = " + frs.getObject(i) + " ");
}
}
}
}
@@ -0,0 +1,3 @@
/.idea
baeldung-jee7-seed.iml
/target
+3
View File
@@ -0,0 +1,3 @@
## Relevant articles:
- [A Guide to DeltaSpike Data Module](http://www.baeldung.com/deltaspike-data-module)
+322
View File
@@ -0,0 +1,322 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.baeldung</groupId>
<artifactId>deltaspike</artifactId>
<version>1.0</version>
<name>deltaspike</name>
<packaging>war</packaging>
<description>A starter Java EE 7 webapp which uses DeltaSpike</description>
<url>http://wildfly.org</url>
<parent>
<groupId>com.baeldung</groupId>
<artifactId>parent-modules</artifactId>
<version>1.0.0-SNAPSHOT</version>
<relativePath>../../</relativePath>
</parent>
<dependencies>
<!-- First declare the APIs we depend on and need for compilation. All of them are provided by JBoss WildFly -->
<!-- Import the CDI API, we use provided scope as the API is included in JBoss WildFly -->
<dependency>
<groupId>javax.enterprise</groupId>
<artifactId>cdi-api</artifactId>
<scope>provided</scope>
</dependency>
<!-- Import the Common Annotations API (JSR-250), we use provided scope as the API is included in JBoss WildFly -->
<dependency>
<groupId>org.jboss.spec.javax.annotation</groupId>
<artifactId>jboss-annotations-api_1.2_spec</artifactId>
<scope>provided</scope>
</dependency>
<!-- Import the JAX-RS API, we use provided scope as the API is included in JBoss WildFly -->
<dependency>
<groupId>org.jboss.resteasy</groupId>
<artifactId>jaxrs-api</artifactId>
<scope>provided</scope>
</dependency>
<!-- Import the JPA API, we use provided scope as the API is included in JBoss WildFly -->
<dependency>
<groupId>org.hibernate.javax.persistence</groupId>
<artifactId>hibernate-jpa-2.1-api</artifactId>
<scope>provided</scope>
</dependency>
<!-- Import the EJB API, we use provided scope as the API is included in JBoss WildFly -->
<dependency>
<groupId>org.jboss.spec.javax.ejb</groupId>
<artifactId>jboss-ejb-api_3.2_spec</artifactId>
<scope>provided</scope>
</dependency>
<!-- JSR-303 (Bean Validation) Implementation -->
<!-- Provides portable constraints such as @Email -->
<!-- Hibernate Validator is shipped in JBoss WildFly -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-validator</artifactId>
<scope>provided</scope>
<exclusions>
<exclusion>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
</exclusion>
</exclusions>
</dependency>
<!-- Import the JSF API, we use provided scope as the API is included in JBoss WildFly -->
<dependency>
<groupId>org.jboss.spec.javax.faces</groupId>
<artifactId>jboss-jsf-api_2.2_spec</artifactId>
<scope>provided</scope>
</dependency>
<!-- Now we declare any tools needed -->
<!-- Annotation processor to generate the JPA 2.0 metamodel classes for typesafe criteria queries -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-jpamodelgen</artifactId>
<scope>provided</scope>
</dependency>
<!-- Annotation processor that raising compilation errors whenever constraint annotations are incorrectly used. -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-validator-annotation-processor</artifactId>
<scope>provided</scope>
</dependency>
<!-- Optional, but highly recommended -->
<!-- Arquillian allows you to test enterprise code such as EJBs and Transactional(JTA) JPA from JUnit/TestNG -->
<dependency>
<groupId>org.jboss.arquillian.junit</groupId>
<artifactId>arquillian-junit-container</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.jboss.arquillian.protocol</groupId>
<artifactId>arquillian-protocol-servlet</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.jboss.shrinkwrap.resolver</groupId>
<artifactId>shrinkwrap-resolver-impl-maven</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.apache.deltaspike.modules</groupId>
<artifactId>deltaspike-data-module-api</artifactId>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.apache.deltaspike.modules</groupId>
<artifactId>deltaspike-data-module-impl</artifactId>
<scope>runtime</scope>
</dependency>
<!-- querydsl libraries -->
<dependency>
<groupId>com.mysema.querydsl</groupId>
<artifactId>querydsl-apt</artifactId>
<version>${querydsl.version}</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>com.mysema.querydsl</groupId>
<artifactId>querydsl-jpa</artifactId>
<version>${querydsl.version}</version>
</dependency>
<dependency>
<groupId>org.apache.deltaspike.modules</groupId>
<artifactId>deltaspike-test-control-module-api</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.apache.deltaspike.modules</groupId>
<artifactId>deltaspike-test-control-module-impl</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.apache.deltaspike.cdictrl</groupId>
<artifactId>deltaspike-cdictrl-weld</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.jboss.weld.se</groupId>
<artifactId>weld-se-core</artifactId>
<version>${weld.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.jboss</groupId>
<artifactId>jandex</artifactId>
<version>${jandex.version}</version>
</dependency>
<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>
<version>${h2.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<scope>provided</scope>
</dependency>
<!-- Needed for running tests (you may also use TestNG) -->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<scope>test</scope>
</dependency>
<!-- Others -->
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-lang3</artifactId>
<version>${commons-lang3.version}</version>
</dependency>
</dependencies>
<build>
<!-- Maven will append the version to the finalName (which is the name given to the generated war, and hence the context root) -->
<finalName>${project.artifactId}</finalName>
<plugins>
<plugin>
<artifactId>maven-war-plugin</artifactId>
<version>${war.plugin.version}</version>
<configuration>
<!-- Java EE 7 doesn't require web.xml, Maven needs to catch up! -->
<failOnMissingWebXml>false</failOnMissingWebXml>
</configuration>
</plugin>
<plugin>
<groupId>com.mysema.maven</groupId>
<artifactId>apt-maven-plugin</artifactId>
<version>${apt-maven-plugin.version}</version>
<executions>
<execution>
<goals>
<goal>process</goal>
</goals>
<configuration>
<outputDirectory>target/generated-sources/java</outputDirectory>
<processor>com.mysema.query.apt.jpa.JPAAnnotationProcessor</processor>
</configuration>
</execution>
</executions>
</plugin>
<!-- The WildFly plugin deploys your war to a local WildFly container -->
<!-- To use, run: mvn package wildfly:deploy -->
<plugin>
<groupId>org.wildfly.plugins</groupId>
<artifactId>wildfly-maven-plugin</artifactId>
<version>${wildfly.maven.plugin.version}</version>
</plugin>
</plugins>
</build>
<profiles>
<profile>
<!-- An optional Arquillian testing profile that executes tests in your WildFly instance -->
<!-- This profile will start a new WildFly instance, and execute the test, shutting it down when done -->
<!-- Run with: mvn clean test -Parq-wildfly-managed -->
<id>arq-wildfly-managed</id>
<dependencies>
<dependency>
<groupId>org.wildfly</groupId>
<artifactId>wildfly-arquillian-container-managed</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
</profile>
</profiles>
<licenses>
<license>
<name>Apache License, Version 2.0</name>
<distribution>repo</distribution>
<url>http://www.apache.org/licenses/LICENSE-2.0.html</url>
</license>
</licenses>
<repositories>
<repository>
<id>redhat-repository-techpreview</id>
<url>https://maven.repository.redhat.com/techpreview/all/</url>
</repository>
</repositories>
<dependencyManagement>
<dependencies>
<!-- JBoss distributes a complete set of Java EE 7 APIs including a Bill of Materials (BOM). A BOM specifies the versions of a "stack" (or a collection) of artifacts. We
use this here so that we always get the correct versions of artifacts. Here we use the jboss-javaee-7.0-with-tools stack (you can read this as the JBoss stack of the Java EE 7 APIs,
with some extras tools for your project, such as Arquillian for testing) and the jboss-javaee-7.0-with-hibernate stack you can read this as the JBoss stack of the Java EE 7 APIs, with
extras from the Hibernate family of projects) -->
<dependency>
<groupId>org.wildfly.bom</groupId>
<artifactId>jboss-javaee-7.0-with-tools</artifactId>
<version>${jboss.bom.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>org.wildfly.bom</groupId>
<artifactId>jboss-javaee-7.0-with-hibernate</artifactId>
<version>${jboss.bom.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>org.apache.deltaspike.distribution</groupId>
<artifactId>distributions-bom</artifactId>
<version>${deltaspike.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<properties>
<querydsl.version>3.7.4</querydsl.version>
<deltaspike.version>1.8.2</deltaspike.version>
<!-- JBoss dependency versions -->
<wildfly.maven.plugin.version>1.0.2.Final</wildfly.maven.plugin.version>
<!-- Define the version of the JBoss BOMs we want to import to specify tested stacks. -->
<jboss.bom.version>8.2.1.Final</jboss.bom.version>
<weld.version>2.1.2.Final</weld.version>
<!-- other plugin versions -->
<war.plugin.version>2.6</war.plugin.version>
<apt-maven-plugin.version>1.1.3</apt-maven-plugin.version>
<jandex.version>1.2.5.Final-redhat-1</jandex.version>
</properties>
</project>
@@ -0,0 +1,82 @@
/*
* JBoss, Home of Professional Open Source
* Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
* contributors by the @authors tag. See the copyright.txt in the
* distribution for a full listing of individual contributors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package baeldung.controller;
import baeldung.model.Member;
import baeldung.service.MemberRegistration;
import javax.annotation.PostConstruct;
import javax.enterprise.inject.Model;
import javax.enterprise.inject.Produces;
import javax.faces.application.FacesMessage;
import javax.faces.context.FacesContext;
import javax.inject.Inject;
import javax.inject.Named;
// The @Model stereotype is a convenience mechanism to make this a request-scoped bean that has an
// EL name
// Read more about the @Model stereotype in this FAQ:
// http://www.cdi-spec.org/faq/#accordion6
@Model
public class MemberController {
@Inject private FacesContext facesContext;
@Inject private MemberRegistration memberRegistration;
@Produces
@Named
private Member newMember;
@PostConstruct
public void initNewMember() {
newMember = new Member();
}
public void register() throws Exception {
try {
memberRegistration.register(newMember);
FacesMessage m = new FacesMessage(FacesMessage.SEVERITY_INFO, "Registered!", "Registration successful");
facesContext.addMessage(null, m);
initNewMember();
} catch (Exception e) {
String errorMessage = getRootErrorMessage(e);
FacesMessage m = new FacesMessage(FacesMessage.SEVERITY_ERROR, errorMessage, "Registration unsuccessful");
facesContext.addMessage(null, m);
}
}
private String getRootErrorMessage(Exception e) {
// Default to general error message that registration failed.
String errorMessage = "Registration failed. See server log for more information";
if (e == null) {
// This shouldn't happen, but return the default messages
return errorMessage;
}
// Start with the exception and recurse to find the root cause
Throwable t = e;
while (t != null) {
// Get the message from the Throwable class instance
errorMessage = t.getLocalizedMessage();
t = t.getCause();
}
// This is the root cause message
return errorMessage;
}
}
@@ -0,0 +1,18 @@
package baeldung.data;
import javax.enterprise.context.RequestScoped;
import javax.enterprise.inject.Produces;
import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
public class EntityManagerProducer {
@PersistenceContext(unitName = "primary") private EntityManager entityManager;
@RequestScoped
@Produces
public EntityManager create() {
return entityManager;
}
}
@@ -0,0 +1,53 @@
/*
* JBoss, Home of Professional Open Source
* Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
* contributors by the @authors tag. See the copyright.txt in the
* distribution for a full listing of individual contributors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package baeldung.data;
import baeldung.model.Member;
import javax.annotation.PostConstruct;
import javax.enterprise.context.RequestScoped;
import javax.enterprise.event.Observes;
import javax.enterprise.event.Reception;
import javax.enterprise.inject.Produces;
import javax.inject.Inject;
import javax.inject.Named;
import java.util.List;
@RequestScoped
public class MemberListProducer {
@Inject private MemberRepository memberRepository;
private List<Member> members;
// @Named provides access the return value via the EL variable name "members" in the UI (e.g.
// Facelets or JSP view)
@Produces
@Named
public List<Member> getMembers() {
return members;
}
public void onMemberListChanged(@Observes(notifyObserver = Reception.IF_EXISTS) final Member member) {
retrieveAllMembersOrderedByName();
}
@PostConstruct
public void retrieveAllMembersOrderedByName() {
members = memberRepository.findAllOrderedByNameWithQueryDSL();
}
}
@@ -0,0 +1,46 @@
/*
* JBoss, Home of Professional Open Source
* Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
* contributors by the @authors tag. See the copyright.txt in the
* distribution for a full listing of individual contributors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package baeldung.data;
import baeldung.model.Member;
import baeldung.model.QMember;
import org.apache.deltaspike.data.api.AbstractEntityRepository;
import org.apache.deltaspike.data.api.EntityManagerConfig;
import org.apache.deltaspike.data.api.Query;
import org.apache.deltaspike.data.api.Repository;
import java.util.List;
@Repository
@EntityManagerConfig(entityManagerResolver = SecondaryEntityManagerResolver.class)
public abstract class MemberRepository extends AbstractEntityRepository<Member, Long> implements QueryDslSupport {
public abstract Member findById(Long id);
public abstract Member findByEmail(String email);
@Query("from Member m order by m.name")
public abstract List<Member> findAllOrderedByName();
public List<Member> findAllOrderedByNameWithQueryDSL() {
final QMember member = QMember.member;
return jpaQuery()
.from(member)
.orderBy(member.email.asc())
.list(member);
}
}
@@ -0,0 +1,17 @@
package baeldung.data;
import com.mysema.query.jpa.impl.JPAQuery;
import org.apache.deltaspike.data.spi.DelegateQueryHandler;
import org.apache.deltaspike.data.spi.QueryInvocationContext;
import javax.inject.Inject;
public class QueryDslRepositoryExtension<E> implements QueryDslSupport, DelegateQueryHandler {
@Inject private QueryInvocationContext context;
@Override
public JPAQuery jpaQuery() {
return new JPAQuery(context.getEntityManager());
}
}
@@ -0,0 +1,7 @@
package baeldung.data;
import com.mysema.query.jpa.impl.JPAQuery;
public interface QueryDslSupport {
JPAQuery jpaQuery();
}
@@ -0,0 +1,21 @@
package baeldung.data;
import javax.enterprise.context.ApplicationScoped;
import javax.enterprise.context.RequestScoped;
import javax.enterprise.inject.Produces;
import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
@ApplicationScoped
public class SecondaryEntityManagerProducer {
@PersistenceContext(unitName = "secondary") private EntityManager entityManager;
@Produces
@RequestScoped
@SecondaryPersistenceUnit
public EntityManager create() {
return entityManager;
}
}
@@ -0,0 +1,18 @@
package baeldung.data;
import org.apache.deltaspike.data.api.EntityManagerResolver;
import javax.inject.Inject;
import javax.persistence.EntityManager;
public class SecondaryEntityManagerResolver implements EntityManagerResolver {
@Inject
@SecondaryPersistenceUnit
private EntityManager entityManager;
@Override
public EntityManager resolveEntityManager() {
return entityManager;
}
}
@@ -0,0 +1,12 @@
package baeldung.data;
import javax.inject.Qualifier;
import java.lang.annotation.Documented;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Qualifier
public @interface SecondaryPersistenceUnit {
}
@@ -0,0 +1,45 @@
package baeldung.data;
import baeldung.model.User;
import org.apache.deltaspike.data.api.FirstResult;
import org.apache.deltaspike.data.api.MaxResults;
import org.apache.deltaspike.data.api.Repository;
import java.util.Collection;
import java.util.List;
/**
* Created by adam.
*/
@Repository(forEntity = User.class)
public abstract class SimpleUserRepository {
public abstract Collection<User> findAll();
public abstract Collection<User> findAllOrderByFirstNameAsc(@FirstResult int start, @MaxResults int size);
public abstract Collection<User> findTop2OrderByFirstNameAsc();
public abstract Collection<User> findFirst2OrderByFirstNameAsc();
public abstract List<User> findAllOrderByFirstNameAsc();
public abstract List<User> findAllOrderByFirstNameAscLastNameDesc();
public abstract User findById(Long id);
public abstract Collection<User> findByFirstName(String firstName);
public abstract User findAnyByLastName(String lastName);
public abstract Collection<User> findAnyByFirstName(String firstName);
public abstract Collection<User> findByFirstNameAndLastName(String firstName, String lastName);
public abstract Collection<User> findByFirstNameOrLastName(String firstName, String lastName);
public abstract Collection<User> findByAddress_city(String city);
public abstract int count();
public abstract void remove(User user);
}
@@ -0,0 +1,31 @@
package baeldung.data;
import baeldung.model.User;
import org.apache.deltaspike.data.api.AbstractEntityRepository;
import org.apache.deltaspike.data.api.Query;
import org.apache.deltaspike.data.api.Repository;
import java.util.Collection;
import java.util.List;
/**
* Created by adam.
*/
@Repository
public abstract class UserRepository extends AbstractEntityRepository<User, Long> {
public List<User> findByFirstName(String firstName) {
return typedQuery("select u from User u where u.firstName = ?1")
.setParameter(1, firstName)
.getResultList();
}
public abstract List<User> findByLastName(String lastName);
@Query("select u from User u where u.firstName = ?1")
public abstract Collection<User> findUsersWithFirstName(String firstName);
@Query(value = "select * from User where firstName = ?1", isNative = true)
public abstract Collection<User> findUsersWithFirstNameNative(String firstName);
}
@@ -0,0 +1,51 @@
package baeldung.model;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
/**
* Created by adam.
*/
@Entity
public class Address {
@Id
@GeneratedValue
private Long id;
private String street;
private String city;
private String postCode;
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getStreet() {
return street;
}
public void setStreet(String street) {
this.street = street;
}
public String getCity() {
return city;
}
public void setCity(String city) {
this.city = city;
}
public String getPostCode() {
return postCode;
}
public void setPostCode(String postCode) {
this.postCode = postCode;
}
}
@@ -0,0 +1,87 @@
/*
* JBoss, Home of Professional Open Source
* Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
* contributors by the @authors tag. See the copyright.txt in the
* distribution for a full listing of individual contributors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package baeldung.model;
import org.hibernate.validator.constraints.Email;
import org.hibernate.validator.constraints.NotEmpty;
import javax.persistence.*;
import javax.validation.constraints.Digits;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Pattern;
import javax.validation.constraints.Size;
import javax.xml.bind.annotation.XmlRootElement;
import java.io.Serializable;
@SuppressWarnings("serial")
@Entity
@XmlRootElement
@Table(uniqueConstraints = @UniqueConstraint(columnNames = "email"))
public class Member implements Serializable {
@Id
@GeneratedValue
private Long id;
@NotNull
@Size(min = 1, max = 25)
@Pattern(regexp = "[^0-9]*", message = "Must not contain numbers")
private String name;
@NotNull
@NotEmpty
@Email
private String email;
@NotNull
@Size(min = 10, max = 12)
@Digits(fraction = 0, integer = 12)
@Column(name = "phone_number")
private String phoneNumber;
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 getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getPhoneNumber() {
return phoneNumber;
}
public void setPhoneNumber(String phoneNumber) {
this.phoneNumber = phoneNumber;
}
}
@@ -0,0 +1,52 @@
package baeldung.model;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.OneToOne;
/**
* Created by adam.
*/
@Entity
public class User {
@Id
@GeneratedValue
private Long id;
private String firstName;
private String lastName;
@OneToOne private Address address;
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public Address getAddress() {
return address;
}
public void setAddress(Address address) {
this.address = address;
}
}
@@ -0,0 +1,33 @@
/*
* JBoss, Home of Professional Open Source
* Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
* contributors by the @authors tag. See the copyright.txt in the
* distribution for a full listing of individual contributors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package baeldung.rest;
import javax.ws.rs.ApplicationPath;
import javax.ws.rs.core.Application;
/**
* A class extending {@link Application} and annotated with @ApplicationPath is the Java EE 7 "no XML" approach to activating
* JAX-RS.
* <p>
* <p>
* Resources are served relative to the servlet path specified in the {@link ApplicationPath} annotation.
* </p>
*/
@ApplicationPath("/rest")
public class JaxRsActivator extends Application {
/* class body intentionally left blank */
}
@@ -0,0 +1,185 @@
/*
* JBoss, Home of Professional Open Source
* Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
* contributors by the @authors tag. See the copyright.txt in the
* distribution for a full listing of individual contributors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package baeldung.rest;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.logging.Logger;
import javax.enterprise.context.RequestScoped;
import javax.inject.Inject;
import javax.persistence.NoResultException;
import javax.validation.ConstraintViolation;
import javax.validation.ConstraintViolationException;
import javax.validation.ValidationException;
import javax.validation.Validator;
import javax.ws.rs.Consumes;
import javax.ws.rs.GET;
import javax.ws.rs.POST;
import javax.ws.rs.Path;
import javax.ws.rs.PathParam;
import javax.ws.rs.Produces;
import javax.ws.rs.WebApplicationException;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import baeldung.data.MemberRepository;
import baeldung.model.Member;
import baeldung.service.MemberRegistration;
/**
* JAX-RS Example
* <p/>
* This class produces a RESTful service to read/write the contents of the members table.
*/
@Path("/members")
@RequestScoped
public class MemberResourceRESTService {
@Inject
private Logger log;
@Inject
private Validator validator;
@Inject
private MemberRepository repository;
@Inject
MemberRegistration registration;
@GET
@Produces(MediaType.APPLICATION_JSON)
public List<Member> listAllMembers() {
return repository.findAllOrderedByName();
}
@GET
@Path("/{id:[0-9][0-9]*}")
@Produces(MediaType.APPLICATION_JSON)
public Member lookupMemberById(@PathParam("id") long id) {
Member member = repository.findById(id);
if (member == null) {
throw new WebApplicationException(Response.Status.NOT_FOUND);
}
return member;
}
/**
* Creates a new member from the values provided. Performs validation, and will return a JAX-RS response with either 200 ok,
* or with a map of fields, and related errors.
*/
@POST
@Consumes(MediaType.APPLICATION_JSON)
@Produces(MediaType.APPLICATION_JSON)
public Response createMember(Member member) {
Response.ResponseBuilder builder = null;
try {
// Validates member using bean validation
validateMember(member);
registration.register(member);
// Create an "ok" response
builder = Response.ok();
} catch (ConstraintViolationException ce) {
// Handle bean validation issues
builder = createViolationResponse(ce.getConstraintViolations());
} catch (ValidationException e) {
// Handle the unique constrain violation
Map<String, String> responseObj = new HashMap<>();
responseObj.put("email", "Email taken");
builder = Response.status(Response.Status.CONFLICT).entity(responseObj);
} catch (Exception e) {
// Handle generic exceptions
Map<String, String> responseObj = new HashMap<>();
responseObj.put("error", e.getMessage());
builder = Response.status(Response.Status.BAD_REQUEST).entity(responseObj);
}
return builder.build();
}
/**
* <p>
* Validates the given Member variable and throws validation exceptions based on the type of error. If the error is standard
* bean validation errors then it will throw a ConstraintValidationException with the set of the constraints violated.
* </p>
* <p>
* If the error is caused because an existing member with the same email is registered it throws a regular validation
* exception so that it can be interpreted separately.
* </p>
*
* @param member Member to be validated
* @throws ConstraintViolationException If Bean Validation errors exist
* @throws ValidationException If member with the same email already exists
*/
private void validateMember(Member member) throws ConstraintViolationException, ValidationException {
// Create a bean validator and check for issues.
Set<ConstraintViolation<Member>> violations = validator.validate(member);
if (!violations.isEmpty()) {
throw new ConstraintViolationException(new HashSet<ConstraintViolation<?>>(violations));
}
// Check the uniqueness of the email address
if (emailAlreadyExists(member.getEmail())) {
throw new ValidationException("Unique Email Violation");
}
}
/**
* Creates a JAX-RS "Bad Request" response including a map of all violation fields, and their message. This can then be used
* by clients to show violations.
*
* @param violations A set of violations that needs to be reported
* @return JAX-RS response containing all violations
*/
private Response.ResponseBuilder createViolationResponse(Set<ConstraintViolation<?>> violations) {
log.fine("Validation completed. violations found: " + violations.size());
Map<String, String> responseObj = new HashMap<>();
for (ConstraintViolation<?> violation : violations) {
responseObj.put(violation.getPropertyPath().toString(), violation.getMessage());
}
return Response.status(Response.Status.BAD_REQUEST).entity(responseObj);
}
/**
* Checks if a member with the same email address is already registered. This is the only way to easily capture the
* "@UniqueConstraint(columnNames = "email")" constraint from the Member class.
*
* @param email The email to check
* @return True if the email already exists, and false otherwise
*/
public boolean emailAlreadyExists(String email) {
Member member = null;
try {
member = repository.findByEmail(email);
} catch (NoResultException e) {
// ignore
}
return member != null;
}
}
@@ -0,0 +1,84 @@
/*
* JBoss, Home of Professional Open Source
* Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
* contributors by the @authors tag. See the copyright.txt in the
* distribution for a full listing of individual contributors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package baeldung.service;
import baeldung.data.MemberRepository;
import baeldung.data.SecondaryPersistenceUnit;
import baeldung.model.Member;
import baeldung.model.QMember;
import javax.ejb.Stateless;
import javax.enterprise.event.Event;
import javax.enterprise.inject.Default;
import javax.inject.Inject;
import javax.persistence.EntityManager;
import javax.persistence.NoResultException;
import javax.validation.ConstraintViolation;
import javax.validation.ConstraintViolationException;
import javax.validation.ValidationException;
import javax.validation.Validator;
import java.util.HashSet;
import java.util.Set;
import java.util.logging.Logger;
@Stateless
public class MemberRegistration {
@Inject
private Logger log;
@Inject
private MemberRepository repository;
@Inject
private Event<Member> memberEventSrc;
@Inject
private Validator validator;
private void validateMember(Member member) throws ConstraintViolationException, ValidationException {
// Create a bean validator and check for issues.
Set<ConstraintViolation<Member>> violations = validator.validate(member);
if (!violations.isEmpty()) {
throw new ConstraintViolationException(new HashSet<ConstraintViolation<?>>(violations));
}
// Check the uniqueness of the email address
if (emailAlreadyExists(member.getEmail())) {
throw new ValidationException("Unique Email Violation");
}
}
public void register(Member member) throws Exception {
log.info("Registering " + member.getName());
validateMember(member);
repository.save(member);
memberEventSrc.fire(member);
}
public boolean emailAlreadyExists(String email) {
Member member = null;
try {
member = repository.findByEmail(email);
} catch (NoResultException e) {
// ignore
}
return member != null;
}
}
@@ -0,0 +1,53 @@
/*
* JBoss, Home of Professional Open Source
* Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
* contributors by the @authors tag. See the copyright.txt in the
* distribution for a full listing of individual contributors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package baeldung.util;
import java.util.logging.Logger;
import javax.enterprise.context.RequestScoped;
import javax.enterprise.inject.Produces;
import javax.enterprise.inject.spi.InjectionPoint;
import javax.faces.context.FacesContext;
import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
/**
* This class uses CDI to alias Java EE resources, such as the persistence context, to CDI beans
* <p>
* <p>
* Example injection on a managed bean field:
* </p>
* <p>
* <pre>
* &#064;Inject
* private EntityManager em;
* </pre>
*/
public class Resources {
@Produces
public Logger produceLog(InjectionPoint injectionPoint) {
return Logger.getLogger(injectionPoint.getMember().getDeclaringClass().getName());
}
@Produces
@RequestScoped
public FacesContext produceFacesContext() {
return FacesContext.getCurrentInstance();
}
}
@@ -0,0 +1 @@
globalAlternatives.org.apache.deltaspike.jpa.spi.transaction.TransactionStrategy=org.apache.deltaspike.jpa.impl.transaction.BeanManagedUserTransactionStrategy
@@ -0,0 +1,5 @@
<beans xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="
http://xmlns.jcp.org/xml/ns/javaee
http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd" bean-discovery-mode="all">
</beans>
@@ -0,0 +1,21 @@
<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.1"
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
http://xmlns.jcp.org/xml/ns/persistence/persistence_2_1.xsd">
<persistence-unit name="primary" transaction-type="JTA">
<jta-data-source>java:jboss/datasources/baeldung-jee7-seedDS</jta-data-source>
<properties>
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
<property name="hibernate.show_sql" value="false" />
</properties>
</persistence-unit>
<persistence-unit name="secondary" transaction-type="JTA">
<jta-data-source>java:jboss/datasources/baeldung-jee7-seed-secondaryDS</jta-data-source>
<properties>
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
<property name="hibernate.show_sql" value="false" />
</properties>
</persistence-unit>
</persistence>
@@ -0,0 +1,19 @@
--
-- JBoss, Home of Professional Open Source
-- Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
-- contributors by the @authors tag. See the copyright.txt in the
-- distribution for a full listing of individual contributors.
--
-- Licensed under the Apache License, Version 2.0 (the "License");
-- you may not use this file except in compliance with the License.
-- You may obtain a copy of the License at
-- http://www.apache.org/licenses/LICENSE-2.0
-- Unless required by applicable law or agreed to in writing, software
-- distributed under the License is distributed on an "AS IS" BASIS,
-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-- See the License for the specific language governing permissions and
-- limitations under the License.
--
-- You can use this file to load seed data into the database using SQL statements
insert into Member (id, name, email, phone_number) values (0, 'John Smith', 'john.smith@mailinator.com', '2125551212')
@@ -0,0 +1,13 @@
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
</pattern>
</encoder>
</appender>
<root level="INFO">
<appender-ref ref="STDOUT" />
</root>
</configuration>
@@ -0,0 +1,37 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
JBoss, Home of Professional Open Source
Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
contributors by the @authors tag. See the copyright.txt in the
distribution for a full listing of individual contributors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<!-- This is an unmanaged datasource. It should be used for proofs of concept
or testing only. It uses H2, an in memory database that ships with JBoss
AS. -->
<datasources xmlns="http://www.jboss.org/ironjacamar/schema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.jboss.org/ironjacamar/schema http://docs.jboss.org/ironjacamar/schema/datasources_1_0.xsd">
<!-- The datasource is bound into JNDI at this location. We reference
this in META-INF/persistence.xml -->
<datasource jndi-name="java:jboss/datasources/baeldung-jee7-seedDS"
pool-name="baeldung-jee7-seed" enabled="true"
use-java-context="true">
<connection-url>jdbc:h2:mem:baeldung-jee7-seed;DB_CLOSE_ON_EXIT=FALSE;DB_CLOSE_DELAY=-1</connection-url>
<driver>h2</driver>
<security>
<user-name>sa</user-name>
<password>sa</password>
</security>
</datasource>
</datasources>
@@ -0,0 +1,19 @@
<?xml version="1.0" encoding="UTF-8"?>
<datasources xmlns="http://www.jboss.org/ironjacamar/schema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.jboss.org/ironjacamar/schema http://docs.jboss.org/ironjacamar/schema/datasources_1_0.xsd">
<!-- The datasource is bound into JNDI at this location. We reference
this in META-INF/persistence.xml -->
<datasource jndi-name="java:jboss/datasources/baeldung-jee7-seed-secondaryDS"
pool-name="baeldung-jee7-seed" enabled="true"
use-java-context="true">
<connection-url>jdbc:h2:mem:baeldung-jee7-seed;DB_CLOSE_ON_EXIT=FALSE;DB_CLOSE_DELAY=-1</connection-url>
<driver>h2</driver>
<security>
<user-name>sa</user-name>
<password>sa</password>
</security>
</datasource>
</datasources>
@@ -0,0 +1,23 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
JBoss, Home of Professional Open Source
Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
contributors by the @authors tag. See the copyright.txt in the
distribution for a full listing of individual contributors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<!-- Marker file indicating CDI should be enabled -->
<beans xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="
http://xmlns.jcp.org/xml/ns/javaee
http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd" bean-discovery-mode="all">
</beans>
@@ -0,0 +1,25 @@
<?xml version="1.0"?>
<!--
JBoss, Home of Professional Open Source
Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
contributors by the @authors tag. See the copyright.txt in the
distribution for a full listing of individual contributors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<!-- Marker file indicating JSF 2.2 should be enabled in the application -->
<faces-config version="2.2"
xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="
http://xmlns.jcp.org/xml/ns/javaee
http://xmlns.jcp.org/xml/ns/javaee/web-facesconfig_2_2.xsd">
</faces-config>
@@ -0,0 +1,55 @@
<!--
JBoss, Home of Professional Open Source
Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
contributors by the @authors tag. See the copyright.txt in the
distribution for a full listing of individual contributors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:ui="http://java.sun.com/jsf/facelets">
<h:head>
<title>baeldung-jee7-seed</title>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<h:outputStylesheet name="css/screen.css" />
</h:head>
<h:body>
<div id="container">
<div class="dualbrand">
<img src="resources/gfx/dualbrand_logo.png" />
</div>
<div id="content">
<ui:insert name="content">
[Template content will be inserted here]
</ui:insert>
</div>
<div id="aside">
<p>Learn more about JBoss WildFly.</p>
<ul>
<li><a
href="https://github.com/wildfly/quickstart/blob/master/guide/Introduction.asciidoc">Getting
Started Developing Applications Guide</a></li>
<li><a href="http://www.wildfly.org/">Community
Project Information</a></li>
</ul>
</div>
<div id="footer">
<p>
This project was generated from a Maven archetype from
WildFly.<br />
</p>
</div>
</div>
</h:body>
</html>
@@ -0,0 +1,23 @@
<!--
JBoss, Home of Professional Open Source
Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
contributors by the @authors tag. See the copyright.txt in the
distribution for a full listing of individual contributors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<!-- Plain HTML page that kicks us into the app -->
<html>
<head>
<meta http-equiv="Refresh" content="0; URL=index.jsf">
</head>
</html>
@@ -0,0 +1,97 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
JBoss, Home of Professional Open Source
Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
contributors by the @authors tag. See the copyright.txt in the
distribution for a full listing of individual contributors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<ui:composition xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
template="/WEB-INF/templates/default.xhtml">
<ui:define name="content">
<h1>Welcome to WildFly!</h1>
<div>
<p>You have successfully deployed a Java EE 7 Enterprise
Application.</p>
<h3>Your application can run on:</h3>
<img src="resources/gfx/wildfly_400x130.jpg" />
</div>
<h:form id="reg">
<h2>Member Registration</h2>
<p>Enforces annotation-based constraints defined on the
model class.</p>
<h:panelGrid columns="3" columnClasses="titleCell">
<h:outputLabel for="name" value="Name:" />
<h:inputText id="name" value="#{newMember.name}" />
<h:message for="name" errorClass="invalid" />
<h:outputLabel for="email" value="Email:" />
<h:inputText id="email" value="#{newMember.email}" />
<h:message for="email" errorClass="invalid" />
<h:outputLabel for="phoneNumber" value="Phone #:" />
<h:inputText id="phoneNumber"
value="#{newMember.phoneNumber}" />
<h:message for="phoneNumber" errorClass="invalid" />
</h:panelGrid>
<p>
<h:panelGrid columns="2">
<h:commandButton id="register"
action="#{memberController.register}"
value="Register" styleClass="register" />
<h:messages styleClass="messages"
errorClass="invalid" infoClass="valid"
warnClass="warning" globalOnly="true" />
</h:panelGrid>
</p>
</h:form>
<h2>Members</h2>
<h:panelGroup rendered="#{empty members}">
<em>No registered members.</em>
</h:panelGroup>
<h:dataTable var="_member" value="#{members}"
rendered="#{not empty members}"
styleClass="simpletablestyle">
<h:column>
<f:facet name="header">Id</f:facet>
#{_member.id}
</h:column>
<h:column>
<f:facet name="header">Name</f:facet>
#{_member.name}
</h:column>
<h:column>
<f:facet name="header">Email</f:facet>
#{_member.email}
</h:column>
<h:column>
<f:facet name="header">Phone #</f:facet>
#{_member.phoneNumber}
</h:column>
<h:column>
<f:facet name="header">REST URL</f:facet>
<a
href="#{request.contextPath}/rest/members/#{_member.id}">/rest/members/#{_member.id}</a>
</h:column>
<f:facet name="footer">
REST URL for all members: <a
href="#{request.contextPath}/rest/members">/rest/members</a>
</f:facet>
</h:dataTable>
</ui:define>
</ui:composition>
@@ -0,0 +1,202 @@
/*
* JBoss, Home of Professional Open Source
* Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
* contributors by the @authors tag. See the copyright.txt in the
* distribution for a full listing of individual contributors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/* Core styles for the page */
body {
margin: 0;
padding: 0;
background-color: #F1F1F1;
font-family: "Lucida Sans Unicode", "Lucida Grande", sans-serif;
font-size: 0.8em;
color:#363636;
}
#container {
margin: 0 auto;
padding: 0 20px 10px 20px;
border-top: 5px solid #000000;
border-left: 5px solid #8c8f91;
border-right: 5px solid #8c8f91;
border-bottom: 25px solid #8c8f91;
width: 865px; /* subtract 40px from banner width for padding */
background: #FFFFFF;
background-image: url(#{request.contextPath}/resources/gfx/headerbkg.png);
background-repeat: repeat-x;
padding-top: 30px;
box-shadow: 3px 3px 15px #d5d5d5;
}
#content {
float: left;
width: 500px;
margin: 20px;
}
#aside {
font-size: 0.9em;
width: 275px;
float: left;
margin: 20px 0px;
border: 1px solid #D5D5D5;
background: #F1F1F1;
background-image: url(#{request.contextPath}/resources/gfx/asidebkg.png);
background-repeat: repeat-x;
padding: 20px;
}
#aside ul {
padding-left: 30px;
}
.dualbrand {
float: right;
padding-right: 10px;
}
#footer {
clear: both;
text-align: center;
color: #666666;
font-size: 0.85em;
}
code {
font-size: 1.1em;
}
a {
color: #4a5d75;
text-decoration: none;
}
a:hover {
color: #369;
text-decoration: underline;
}
h1 {
color:#243446;
font-size: 2.25em;
}
h2 {
font-size: 1em;
}
h3 {
color:#243446;
}
h4 {
}
h5 {
}
h6 {
}
/* Member registration styles */
span.invalid {
padding-left: 3px;
color: red;
}
form {
padding: 1em;
font: 80%/1 sans-serif;
width: 375px;
border: 1px solid #D5D5D5;
}
label {
float: left;
width: 15%;
margin-left: 20px;
margin-right: 0.5em;
padding-top: 0.2em;
text-align: right;
font-weight: bold;
color:#363636;
}
input {
margin-bottom: 8px;
}
.register {
float: left;
margin-left: 85px;
}
/* ----- table style ------- */
/* = Simple Table style (black header, grey/white stripes */
.simpletablestyle {
background-color:#E6E7E8;
clear:both;
width: 550px;
}
.simpletablestyle img {
border:0px;
}
.simpletablestyle td {
height:2em;
padding-left: 6px;
font-size:11px;
padding:5px 5px;
}
.simpletablestyle th {
background: url(#{request.contextPath}/resources/gfx/bkg-blkheader.png) black repeat-x top left;
font-size:12px;
font-weight:normal;
padding:0 10px 0 5px;
border-bottom:#999999 dotted 1px;
}
.simpletablestyle thead {
background: url(#{request.contextPath}/resources/gfx/bkg-blkheader.png) black repeat-x top left;
height:31px;
font-size:10px;
font-weight:bold;
color:#FFFFFF;
text-align:left;
}
.simpletablestyle .header a {
color:#94aebd;
}
.simpletablestype tfoot {
height: 20px;
font-size: 10px;
font-weight: bold;
background-color: #EAECEE;
text-align: center;
}
.simpletablestyle tr.header td {
padding: 0px 10px 0px 5px;
}
.simpletablestyle .subheader {
background-color: #e6e7e8;
font-size:10px;
font-weight:bold;
color:#000000;
text-align:left;
}
/* Using new CSS3 selectors for styling*/
.simpletablestyle tr:nth-child(odd) {
background: #f4f3f3;
}
.simpletablestyle tr:nth-child(even) {
background: #ffffff;
}
.simpletablestyle td a:hover {
color:#3883ce;
text-decoration:none;
}
Binary file not shown.

After

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 116 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 12 KiB

@@ -0,0 +1,21 @@
package baeldung;
import javax.enterprise.inject.Produces;
import javax.validation.Validation;
import javax.validation.Validator;
/**
* Created by adam.
*/
public class ValidatorProducer {
@Produces
public Validator createValidator() {
return Validation
.byDefaultProvider()
.configure()
.buildValidatorFactory()
.getValidator();
}
}
@@ -0,0 +1,23 @@
package baeldung.data;
import javax.enterprise.context.ApplicationScoped;
import javax.enterprise.inject.Produces;
import javax.enterprise.inject.Specializes;
import javax.persistence.EntityManager;
import javax.persistence.Persistence;
/**
* Created by adam.
*/
public class TestEntityManagerProducer extends EntityManagerProducer {
@ApplicationScoped
@Produces
@Specializes
public EntityManager create() {
return Persistence
.createEntityManagerFactory("pu-test")
.createEntityManager();
}
}
@@ -0,0 +1,78 @@
/*
* JBoss, Home of Professional Open Source
* Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
* contributors by the @authors tag. See the copyright.txt in the
* distribution for a full listing of individual contributors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package baeldung.test;
import baeldung.data.*;
import baeldung.model.Member;
import baeldung.service.MemberRegistration;
import baeldung.util.Resources;
import org.jboss.arquillian.container.test.api.Deployment;
import org.jboss.arquillian.junit.Arquillian;
import org.jboss.shrinkwrap.api.Archive;
import org.jboss.shrinkwrap.api.ShrinkWrap;
import org.jboss.shrinkwrap.api.asset.EmptyAsset;
import org.jboss.shrinkwrap.api.spec.WebArchive;
import org.jboss.shrinkwrap.resolver.api.maven.Maven;
import org.junit.Test;
import org.junit.runner.RunWith;
import javax.inject.Inject;
import java.io.File;
import java.util.logging.Logger;
import static org.junit.Assert.assertNotNull;
@RunWith(Arquillian.class)
public class MemberRegistrationLiveTest {
@Deployment
public static Archive<?> createTestArchive() {
File[] files = Maven
.resolver()
.loadPomFromFile("pom.xml")
.importRuntimeDependencies()
.resolve()
.withTransitivity()
.asFile();
return ShrinkWrap
.create(WebArchive.class, "test.war")
.addClasses(EntityManagerProducer.class, Member.class, MemberRegistration.class, MemberRepository.class, Resources.class, QueryDslRepositoryExtension.class, QueryDslSupport.class, SecondaryPersistenceUnit.class, SecondaryEntityManagerProducer.class,
SecondaryEntityManagerResolver.class)
.addAsResource("META-INF/persistence.xml", "META-INF/persistence.xml")
.addAsResource("META-INF/apache-deltaspike.properties")
.addAsWebInfResource(EmptyAsset.INSTANCE, "beans.xml")
.addAsWebInfResource("test-ds.xml")
.addAsWebInfResource("test-secondary-ds.xml")
.addAsLibraries(files);
}
@Inject MemberRegistration memberRegistration;
@Inject Logger log;
@Test
public void testRegister() throws Exception {
Member newMember = new Member();
newMember.setName("Jane Doe");
newMember.setEmail("jane@mailinator.com");
newMember.setPhoneNumber("2125551234");
memberRegistration.register(newMember);
assertNotNull(newMember.getId());
log.info(newMember.getName() + " was persisted with id " + newMember.getId());
}
}
@@ -0,0 +1,133 @@
package baeldung.test;
import baeldung.data.SimpleUserRepository;
import baeldung.model.User;
import org.apache.deltaspike.testcontrol.api.junit.CdiTestRunner;
import org.junit.Test;
import org.junit.runner.RunWith;
import javax.inject.Inject;
import javax.persistence.EntityManager;
import java.util.List;
import static org.hamcrest.CoreMatchers.*;
import static org.junit.Assert.assertThat;
/**
* Created by adam.
*/
@RunWith(CdiTestRunner.class)
public class SimpleUserRepositoryUnitTest {
@Inject private EntityManager entityManager;
@Inject private SimpleUserRepository simpleUserRepository;
@Test
public void givenFourUsersWhenFindAllShouldReturnFourUsers() {
assertThat(simpleUserRepository
.findAll()
.size(), equalTo(4));
}
@Test
public void givenTwoUsersWithSpecifiedNameWhenFindByFirstNameShouldReturnTwoUsers() {
assertThat(simpleUserRepository
.findByFirstName("Adam")
.size(), equalTo(2));
}
@Test
public void givenTwoUsersWithSpecifiedNameWhenFindAnyByFirstNameShouldReturnTwoUsers() {
assertThat(simpleUserRepository
.findAnyByFirstName("Adam")
.size(), equalTo(2));
}
@Test
public void givenTwoUsersWithSpecifiedNameWhenCountByFirstNameShouldReturnSizeTwo() {
assertThat(simpleUserRepository.count(), equalTo(4));
}
@Test
public void givenTwoUsersWithSpecifiedNameWhenRemoveByFirstNameShouldReturnSizeTwo() {
simpleUserRepository.remove(entityManager.merge(simpleUserRepository.findById(1L)));
assertThat(entityManager.find(User.class, 1L), nullValue());
}
@Test
public void givenOneUserWithSpecifiedFirstNameAndLastNameWhenFindByFirstNameAndLastNameShouldReturnOneUser() {
assertThat(simpleUserRepository
.findByFirstNameAndLastName("Adam", "LastName1")
.size(), equalTo(1));
assertThat(simpleUserRepository
.findByFirstNameAndLastName("David", "LastName2")
.size(), equalTo(1));
}
@Test
public void givenOneUserWithSpecifiedLastNameWhenFindAnyByLastNameShouldReturnOneUser() {
assertThat(simpleUserRepository.findAnyByLastName("LastName1"), notNullValue());
}
@Test
public void givenOneUserWithSpecifiedAddressCityWhenFindByCityShouldReturnOneUser() {
assertThat(simpleUserRepository
.findByAddress_city("London")
.size(), equalTo(1));
}
@Test
public void givenUsersWithSpecifiedFirstOrLastNameWhenFindByFirstNameOrLastNameShouldReturnTwoUsers() {
assertThat(simpleUserRepository
.findByFirstNameOrLastName("David", "LastName1")
.size(), equalTo(2));
}
@Test
public void givenUsersWhenFindAllOrderByFirstNameAscShouldReturnFirstAdamLastPeter() {
List<User> users = simpleUserRepository.findAllOrderByFirstNameAsc();
assertThat(users
.get(0)
.getFirstName(), equalTo("Adam"));
assertThat(users
.get(3)
.getFirstName(), equalTo("Peter"));
}
@Test
public void givenUsersWhenFindAllOrderByFirstNameAscLastNameDescShouldReturnFirstAdamLastPeter() {
List<User> users = simpleUserRepository.findAllOrderByFirstNameAscLastNameDesc();
assertThat(users
.get(0)
.getFirstName(), equalTo("Adam"));
assertThat(users
.get(3)
.getFirstName(), equalTo("Peter"));
}
@Test
public void givenUsersWhenFindTop2ShouldReturnTwoUsers() {
assertThat(simpleUserRepository
.findTop2OrderByFirstNameAsc()
.size(), equalTo(2));
}
@Test
public void givenUsersWhenFindFirst2ShouldReturnTwoUsers() {
assertThat(simpleUserRepository
.findFirst2OrderByFirstNameAsc()
.size(), equalTo(2));
}
@Test
public void givenPagesWithSizeTwoWhenFindAllOrderByFirstNameAscShouldReturnTwoPages() {
assertThat(simpleUserRepository
.findAllOrderByFirstNameAsc(0, 2)
.size(), equalTo(2));
assertThat(simpleUserRepository
.findAllOrderByFirstNameAsc(2, 4)
.size(), equalTo(2));
}
}
@@ -0,0 +1,55 @@
package baeldung.test;
import baeldung.data.UserRepository;
import org.apache.deltaspike.testcontrol.api.junit.CdiTestRunner;
import org.junit.Test;
import org.junit.runner.RunWith;
import javax.inject.Inject;
import static org.hamcrest.CoreMatchers.equalTo;
import static org.junit.Assert.assertThat;
/**
* Created by adam.
*/
@RunWith(CdiTestRunner.class)
public class UserRepositoryUnitTest {
@Inject private UserRepository userRepository;
@Test
public void givenFourUsersWhenFindAllShouldReturnFourUsers() {
assertThat(userRepository
.findAll()
.size(), equalTo(4));
}
@Test
public void givenTwoUsersWithSpecifiedNameWhenFindByFirstNameShouldReturnTwoUsers() {
assertThat(userRepository
.findByFirstName("Adam")
.size(), equalTo(2));
}
@Test
public void givenTwoUsersWithSpecifiedNameWhenFindUsersWithFirstNameShouldReturnTwoUsers() {
assertThat(userRepository
.findUsersWithFirstName("Adam")
.size(), equalTo(2));
}
@Test
public void givenTwoUsersWithSpecifiedNameWhenFindUsersWithFirstNameNativeShouldReturnTwoUsers() {
assertThat(userRepository
.findUsersWithFirstNameNative("Adam")
.size(), equalTo(2));
}
@Test
public void givenTwoUsersWithSpecifiedLastNameWhenFindByLastNameShouldReturnTwoUsers() {
assertThat(userRepository
.findByLastName("LastName3")
.size(), equalTo(2));
}
}
@@ -0,0 +1,3 @@
globalAlternatives.org.apache.deltaspike.jpa.spi.transaction.TransactionStrategy=org.apache.deltaspike.jpa.impl.transaction.BeanManagedUserTransactionStrategy
org.apache.deltaspike.ProjectStage=UnitTest
deltaspike.testcontrol.stop_container=false
@@ -0,0 +1,18 @@
<!--<?xml version="1.0" encoding="UTF-8"?>-->
<!--&lt;!&ndash; JBoss, Home of Professional Open Source Copyright 2013, Red Hat, Inc. -->
<!--and/or its affiliates, and individual contributors by the @authors tag. See -->
<!--the copyright.txt in the distribution for a full listing of individual contributors. -->
<!--Licensed under the Apache License, Version 2.0 (the "License"); you may not -->
<!--use this file except in compliance with the License. You may obtain a copy -->
<!--of the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required -->
<!--by applicable law or agreed to in writing, software distributed under the -->
<!--License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS -->
<!--OF ANY KIND, either express or implied. See the License for the specific -->
<!--language governing permissions and limitations under the License. &ndash;&gt;-->
<!--&lt;!&ndash; Marker file indicating CDI should be enabled &ndash;&gt;-->
<beans xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="
http://xmlns.jcp.org/xml/ns/javaee
http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd" bean-discovery-mode="all">
</beans>
@@ -0,0 +1,41 @@
<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.1"
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
http://xmlns.jcp.org/xml/ns/persistence/persistence_2_1.xsd">
<persistence-unit name="primary">
<jta-data-source>java:jboss/datasources/baeldung-jee7-seedTestDS</jta-data-source>
<properties>
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
<property name="hibernate.show_sql" value="false" />
</properties>
</persistence-unit>
<persistence-unit name="secondary">
<jta-data-source>java:jboss/datasources/baeldung-jee7-seedTestSecondaryDS</jta-data-source>
<properties>
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
<property name="hibernate.show_sql" value="false" />
</properties>
</persistence-unit>
<persistence-unit name="pu-test" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
<!-- add classes -->
<class>baeldung.model.User</class>
<class>baeldung.model.Address</class>
<properties>
<!-- Configuring JDBC properties -->
<property name="javax.persistence.jdbc.url" value="jdbc:h2:mem:test"/>
<property name="javax.persistence.jdbc.driver" value="org.h2.Driver"/>
<!-- Hibernate properties -->
<property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect"/>
<property name="hibernate.hbm2ddl.auto" value="create-drop"/>
<property name="hibernate.format_sql" value="false"/>
<property name="hibernate.show_sql" value="true"/>
</properties>
</persistence-unit>
</persistence>
@@ -0,0 +1,31 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
JBoss, Home of Professional Open Source
Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
contributors by the @authors tag. See the copyright.txt in the
distribution for a full listing of individual contributors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<arquillian xmlns="http://jboss.org/schema/arquillian"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://jboss.org/schema/arquillian
http://jboss.org/schema/arquillian/arquillian_1_0.xsd">
<!-- Uncomment to have test archives exported to the file system for inspection -->
<!-- <engine> -->
<!-- <property name="deploymentExportPath">target/</property> -->
<!-- </engine> -->
<!-- Force the use of the Servlet 3.0 protocol with all containers, as it is the most mature -->
<defaultProtocol type="Servlet 3.0" />
</arquillian>
@@ -0,0 +1,6 @@
INSERT INTO ADDRESS(ID, STREET, CITY, POSTCODE) VALUES (1, 'Oxford', 'London', 'N121');
INSERT INTO USER(ID, FIRSTNAME, LASTNAME, ADDRESS_ID) VALUES (1, 'Adam', 'LastName1', null);
INSERT INTO USER(ID, FIRSTNAME, LASTNAME, ADDRESS_ID) VALUES (2, 'David', 'LastName2', null);
INSERT INTO USER(ID, FIRSTNAME, LASTNAME, ADDRESS_ID) VALUES (3, 'Adam', 'LastName3', null);
INSERT INTO USER(ID, FIRSTNAME, LASTNAME, ADDRESS_ID) VALUES (4, 'Peter', 'LastName3', 1);
@@ -0,0 +1,16 @@
<?xml version="1.0" encoding="UTF-8"?>
<datasources xmlns="http://www.jboss.org/ironjacamar/schema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.jboss.org/ironjacamar/schema http://docs.jboss.org/ironjacamar/schema/datasources_1_0.xsd">
<datasource jndi-name="java:jboss/datasources/baeldung-jee7-seedTestDS"
pool-name="baeldung-jee7-seed-test" enabled="true"
use-java-context="true">
<connection-url>jdbc:h2:mem:baeldung-jee7-seed-test;DB_CLOSE_DELAY=-1</connection-url>
<driver>h2</driver>
<security>
<user-name>sa</user-name>
<password>sa</password>
</security>
</datasource>
</datasources>
@@ -0,0 +1,16 @@
<?xml version="1.0" encoding="UTF-8"?>
<datasources xmlns="http://www.jboss.org/ironjacamar/schema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.jboss.org/ironjacamar/schema http://docs.jboss.org/ironjacamar/schema/datasources_1_0.xsd">
<datasource jndi-name="java:jboss/datasources/baeldung-jee7-seedTestSecondaryDS"
pool-name="baeldung-jee7-seed-test" enabled="true"
use-java-context="true">
<connection-url>jdbc:h2:mem:baeldung-jee7-seed-test;DB_CLOSE_DELAY=-1</connection-url>
<driver>h2</driver>
<security>
<user-name>sa</user-name>
<password>sa</password>
</security>
</datasource>
</datasources>
@@ -0,0 +1,29 @@
HELP.md
/target/
!.mvn/wrapper/maven-wrapper.jar
### STS ###
.apt_generated
.classpath
.factorypath
.project
.settings
.springBeans
.sts4-cache
### IntelliJ IDEA ###
.idea
*.iws
*.iml
*.ipr
### NetBeans ###
/nbproject/private/
/nbbuild/
/dist/
/nbdist/
/.nb-gradle/
/build/
### VS Code ###
.vscode/
@@ -0,0 +1,3 @@
### Relevant Articles
- [Jest Elasticsearch Java Client](https://www.baeldung.com/elasticsearch-jest)
+34
View File
@@ -0,0 +1,34 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.baeldung</groupId>
<artifactId>elasticsearch</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>elasticsearch</name>
<description>Demo project for Java Elasticsearch libraries</description>
<parent>
<groupId>com.baeldung</groupId>
<artifactId>parent-modules</artifactId>
<version>1.0.0-SNAPSHOT</version>
<relativePath>../../</relativePath>
</parent>
<dependencies>
<dependency>
<groupId>io.searchbox</groupId>
<artifactId>jest</artifactId>
<version>${jest.version}</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>${jackson.version}</version>
</dependency>
</dependencies>
<properties>
<jest.version>6.3.1</jest.version>
</properties>
</project>

Some files were not shown because too many files have changed in this diff Show More