Maven 版 JPA 最佳实践(转)
项目结构图
数据库环境
- 数据库:MySQL
- 版本:5.x
- 数据库名:jpa-demo
- 用户名密码:root/1234
代码清单 1:数据库脚本:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
|
/*
Navicat MySQL Data Transfer
Source Server : localhost
Source Server Version : 50525
Source Host : localhost:3306
Source Database : jpa-demo
Target Server Type : MYSQL
Target Server Version : 50525
File Encoding : 65001
Date: 2014-11-20 20:09:27
*/
SET FOREIGN_KEY_CHECKS=
0
;
-- ----------------------------
-- Table structure
for
`address`
-- ----------------------------
DROP TABLE IF EXISTS `address`;
CREATE TABLE `address` (
`addressID`
int
(
11
) NOT NULL,
`city` varchar(
55
) NOT NULL,
`street` varchar(
55
) NOT NULL,
`zip` varchar(
8
) NOT NULL,
PRIMARY KEY (`addressID`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
-- ----------------------------
-- Records of address
-- ----------------------------
INSERT INTO `address` VALUES (
'1'
,
'深圳'
,
'坂田市场'
,
'518001'
);
INSERT INTO `address` VALUES (
'2'
,
'深圳'
,
'坂田路口'
,
'518002'
);
INSERT INTO `address` VALUES (
'3'
,
'深圳'
,
'四季花城'
,
'518003'
);
-- ----------------------------
-- Table structure
for
`userinfo`
-- ----------------------------
DROP TABLE IF EXISTS `userinfo`;
CREATE TABLE `userinfo` (
`userID`
int
(
11
) NOT NULL,
`username` varchar(
20
) NOT NULL,
`birthday` datetime DEFAULT NULL,
`sex` varchar(
8
) NOT NULL,
`addressID`
int
(
11
) NOT NULL,
PRIMARY KEY (`userID`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
-- ----------------------------
-- Records of userinfo
-- ----------------------------
INSERT INTO `userinfo` VALUES (
'1'
,
'张金雄'
,
null
,
'male'
,
'1'
);
INSERT INTO `userinfo` VALUES (
'2'
,
'李某某'
,
null
,
'male'
,
'2'
);
INSERT INTO `userinfo` VALUES (
'3'
,
'王某某'
,
'2006-08-10 00:00:00'
,
'female'
,
'3'
);
INSERT INTO `userinfo` VALUES (
'4'
,
'陈某某'
,
'2006-08-12 00:00:00'
,
'male'
,
'3'
);
|
源代码
代码清单 2:pom.xml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
|
<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.coderdream</groupId>
<artifactId>jpa-demo</artifactId>
<packaging>war</packaging>
<version>
0.0
.
1
-SNAPSHOT</version>
<name>jpa-demo Maven Webapp</name>
<url>http:
//maven.apache.org</url>
<properties>
<project.build.sourceEncoding>UTF-
8
</project.build.sourceEncoding>
<junit.version>
4.11
</junit.version>
<mysql.version>
5.1
.
17
</mysql.version>
<slf.version>
1.7
.
5
</slf.version>
<toplink.essentials.version>
2.1
-60f</toplink.essentials.version>
</properties>
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>${junit.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>toplink.essentials</groupId>
<artifactId>toplink-essentials</artifactId>
<version>${toplink.essentials.version}</version>
</dependency>
<dependency>
<groupId>toplink.essentials</groupId>
<artifactId>toplink-essentials-agent</artifactId>
<version>${toplink.essentials.version}</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
<version>${slf.version}</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>${mysql.version}</version>
</dependency>
</dependencies>
<build>
<finalName>jpa-demo</finalName>
</build>
</project>
|
代码清单 3:persistence.xml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
|
<?xml version=
"1.0"
encoding=
"UTF-8"
?>
<persistence xmlns=
"http://java.sun.com/xml/ns/persistence"
xmlns:xsi=
"http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http:
//java.sun.com/xml/ns/persistence
http:
//java.sun.com/xml/ns/persistence/persistence_1_0.xsd"
version=
"1.0"
>
<persistence-unit name=
"piscesPU"
transaction-type=
"RESOURCE_LOCAL"
>
<provider>
oracle.toplink.essentials.PersistenceProvider
</provider>
<
class
>com.coderdream.model.UserInfo</
class
>
<
class
>com.coderdream.model.Address</
class
>
<properties>
<!-- 数据库连接配置, JDBC驱动 -->
<property name=
"toplink.jdbc.driver"
value=
"com.mysql.jdbc.Driver"
/>
<!-- 数据库连接配置,URL -->
<property name=
"toplink.jdbc.url"
value=
"jdbc:mysql://localhost:3306/jpa-demo"
/>
<!-- 数据库连接配置, 用户名 -->
<property name=
"toplink.jdbc.user"
value=
"root"
/>
<!-- 数据库连接配置, 密码 -->
<property name=
"toplink.jdbc.password"
value=
"1234"
/>
</properties>
</persistence-unit>
</persistence>
|
代码清单 4:Address.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
|
package
com.coderdream.model;
import
java.io.Serializable;
import
javax.persistence.Column;
import
javax.persistence.Entity;
import
javax.persistence.Id;
@Entity
public
class
Address
implements
Serializable {
// 地址id, 不能为空, 必须唯一
@Id
@Column
(name =
"addressid"
, unique =
true
, nullable =
false
)
private
int
addressid;
// 城市, 不能为空
@Column
(name =
"city"
, nullable =
false
)
private
String city;
// 街道, 不能为空
@Column
(name =
"street"
, nullable =
false
)
private
String street;
// 邮政编码, 不能为空
@Column
(name =
"zip"
, nullable =
false
)
private
String zip;
public
Address() {
}
public
Address(
int
addressid) {
this
.setAddressid(addressid);
}
public
int
getAddressid() {
return
this
.addressid;
}
public
void
setAddressid(
int
addressid) {
this
.addressid = addressid;
}
public
String getCity() {
return
this
.city;
}
public
void
setCity(String city) {
this
.city = city;
}
public
String getStreet() {
return
street;
}
public
void
setStreet(String street) {
this
.street = street;
}
public
String getZip() {
return
this
.zip;
}
public
void
setZip(String zip) {
this
.zip = zip;
}
@Override
public
int
hashCode() {
return
this
.addressid;
}
@Override
public
boolean
equals(Object object) {
if
(!(object
instanceof
Address))
return
false
;
final
Address other = (Address) object;
return
this
.addressid == other.addressid;
}
@Override
public
String toString() {
return
"Address[addressid="
+ getAddressid() +
", city='"
+ getCity() +
"', street='"
+ getStreet() +
"', zip='"
+ getZip() +
""
;
}
}
|
代码清单 5:UserInfo.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
|
package
com.coderdream.model;
import
java.io.Serializable;
import
java.sql.Timestamp;
import
javax.persistence.Column;
import
javax.persistence.Entity;
import
javax.persistence.Id;
import
javax.persistence.JoinColumn;
import
javax.persistence.OneToOne;
import
static
javax.persistence.CascadeType.*;
@Entity
public
class
UserInfo
implements
Serializable {
// 用户id, 不能为空, 必须唯一
@Id
@Column
(name =
"userid"
, unique =
true
, nullable =
false
)
private
int
userid;
// 用户名, 不能为空
@Column
(name =
"userName"
, nullable =
false
)
private
String userName;
// 性别, 不能为空
@Column
(name =
"sex"
, nullable =
false
)
private
String sex;
// 出生日期, 可以为空
@Column
(name =
"birthday"
)
private
Timestamp birthday;
// 地址, 不能为空
// PERSIST 表示更新、新增UserInfo数据时会同时更新、新增Address的数据
// REMOVE 表示从数据库删除UserInfo会同时删除Address表中对应的数据
@OneToOne
(cascade = { PERSIST, REMOVE })
@JoinColumn
(name =
"addressID"
, nullable =
false
)
private
Address address;
public
UserInfo() {
}
public
UserInfo(
int
userid) {
this
.setUserid(userid);
}
@Override
public
int
hashCode() {
return
this
.getUserid();
}
@Override
public
boolean
equals(Object object) {
if
(!(object
instanceof
UserInfo))
return
false
;
final
UserInfo other = (UserInfo) object;
return
this
.userid == other.userid;
}
@Override
public
String toString() {
return
"UserInfo[userid="
+
this
.userid +
", userName='"
+ userName +
"', sex='"
+ sex +
"', birthday="
+ birthday +
", address="
+ address +
""
;
}
public
int
getUserid() {
return
userid;
}
public
void
setUserid(
int
userid) {
this
.userid = userid;
}
public
String getUserName() {
return
userName;
}
public
void
setUserName(String userName) {
this
.userName = userName;
}
public
Timestamp getBirthday() {
return
birthday;
}
public
void
setBirthday(Timestamp birthday) {
this
.birthday = birthday;
}
public
String getSex() {
return
sex;
}
public
void
setSex(String sex) {
this
.sex = sex;
}
public
Address getAddress() {
return
address;
}
public
void
setAddress(Address address) {
this
.address = address;
}
}
|
代码清单 6:SimpleService.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
|
package
com.coderdream.service;
import
java.util.List;
import
javax.persistence.EntityManager;
import
javax.persistence.EntityManagerFactory;
import
javax.persistence.Persistence;
import
com.coderdream.model.Address;
import
com.coderdream.model.UserInfo;
public
class
SimpleService {
/**
* 删除用户id=6的数据
*/
public
static
void
delete() {
final
EntityManagerFactory emf = Persistence.createEntityManagerFactory(
"piscesPU"
);
final
EntityManager em = emf.createEntityManager();
// 找不到数据的话这里会抛异常
UserInfo info = em.find(UserInfo.
class
,
6
);
try
{
em.getTransaction().begin();
em.remove(info);
em.getTransaction().commit();
}
finally
{
em.close();
}
}
/**
* 修改用户id=6的数据
*/
public
static
void
update() {
final
EntityManagerFactory emf = Persistence.createEntityManagerFactory(
"piscesPU"
);
final
EntityManager em = emf.createEntityManager();
// 找不到数据的话这里会抛异常
UserInfo info = em.find(UserInfo.
class
,
6
);
info.setUserName(
"哈哈"
);
info.getAddress().setStreet(
"坂田2"
);
try
{
em.getTransaction().begin();
// 自动将info更新到数据库
em.getTransaction().commit();
}
finally
{
em.close();
}
}
/**
* 查询所有用户数据
*/
public
static
void
query() {
final
EntityManagerFactory emf = Persistence.createEntityManagerFactory(
"piscesPU"
);
long
s = System.currentTimeMillis();
// 数据库连接失败这里会抛出异常
final
EntityManager em = emf.createEntityManager();
long
e = System.currentTimeMillis();
System.out.println(
"连接数据库耗时: "
+ (e - s) +
"毫秒"
);
// 获取数据
@SuppressWarnings
(
"unchecked"
)
List<UserInfo> list = em.createQuery(
"SELECT a FROM UserInfo a"
).getResultList();
int
i =
0
;
for
(UserInfo info : list) {
System.out.println(
"第"
+ (++i) +
"个值为: "
+ info);
}
em.close();
}
/**
* 创建用户id=6的一条数据, 地址id=6
*/
public
static
void
create() {
final
EntityManagerFactory emf = Persistence.createEntityManagerFactory(
"piscesPU"
);
final
EntityManager em = emf.createEntityManager();
UserInfo info =
new
UserInfo(
6
);
info.setSex(
"male"
);
info.setUserName(
"张某某"
);
info.setBirthday(
new
java.sql.Timestamp(System.currentTimeMillis()));
Address naddr =
new
Address(
6
);
naddr.setCity(
"深圳"
);
naddr.setStreet(
"坂田"
);
naddr.setZip(
"518000"
);
info.setAddress(naddr);
try
{
em.getTransaction().begin();
em.persist(info);
em.getTransaction().commit();
}
finally
{
em.close();
}
}
/**
* 主函数
*/
public
static
void
main(String[] args)
throws
Throwable {
SimpleService.query();
SimpleService.create();
System.out.println(
"新增一条数据后进行查询"
);
SimpleService.query();
SimpleService.update();
System.out.println(
"修改一条数据后进行查询"
);
SimpleService.query();
SimpleService.delete();
System.out.println(
"删除一条数据后进行查询"
);
SimpleService.query();
}
}
|
运行结果
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
|
[TopLink Info]:
2014.11
.
20
08
:
24
:
08.134
--ServerSession(
1112823384
)--TopLink, version: Oracle TopLink Essentials -
2.1
(Build 60f (
01
/
07
/
2009
))
[TopLink Info]:
2014.11
.
20
08
:
24
:
08.822
--ServerSession(
1112823384
)--file:/E:/E_441_64/workspace/jpa-demo/target/classes/-piscesPU login successful
连接数据库耗时:
1264
毫秒
第
1
个值为: UserInfo[userid=
1
, userName=
'张金雄'
, sex=
'male'
, birthday=
null
, address=Address[addressid=
1
, city=
'深圳'
, street=
'坂田市场'
, zip='
518001
第
2
个值为: UserInfo[userid=
2
, userName=
'李某某'
, sex=
'male'
, birthday=
null
, address=Address[addressid=
2
, city=
'深圳'
, street=
'坂田路口'
, zip='
518002
第
3
个值为: UserInfo[userid=
3
, userName=
'王某某'
, sex=
'female'
, birthday=
2006
-
08
-
10
00
:
00
:
00.0
, address=Address[addressid=
3
, city=
'深圳'
, street=
'四季花城'
, zip='
518003
第
4
个值为: UserInfo[userid=
4
, userName=
'陈某某'
, sex=
'male'
, birthday=
2006
-
08
-
12
00
:
00
:
00.0
, address=Address[addressid=
3
, city=
'深圳'
, street=
'四季花城'
, zip='
518003
新增一条数据后进行查询
连接数据库耗时:
0
毫秒
第
1
个值为: UserInfo[userid=
1
, userName=
'张金雄'
, sex=
'male'
, birthday=
null
, address=Address[addressid=
1
, city=
'深圳'
, street=
'坂田市场'
, zip='
518001
第
2
个值为: UserInfo[userid=
2
, userName=
'李某某'
, sex=
'male'
, birthday=
null
, address=Address[addressid=
2
, city=
'深圳'
, street=
'坂田路口'
, zip='
518002
第
3
个值为: UserInfo[userid=
3
, userName=
'王某某'
, sex=
'female'
, birthday=
2006
-
08
-
10
00
:
00
:
00.0
, address=Address[addressid=
3
, city=
'深圳'
, street=
'四季花城'
, zip='
518003
第
4
个值为: UserInfo[userid=
4
, userName=
'陈某某'
, sex=
'male'
, birthday=
2006
-
08
-
12
00
:
00
:
00.0
, address=Address[addressid=
3
, city=
'深圳'
, street=
'四季花城'
, zip='
518003
第
5
个值为: UserInfo[userid=
6
, userName=
'张某某'
, sex=
'male'
, birthday=
2014
-
11
-
20
20
:
24
:
09.102
, address=Address[addressid=
6
, city=
'深圳'
, street=
'坂田'
, zip='
518000
修改一条数据后进行查询
连接数据库耗时:
0
毫秒
第
1
个值为: UserInfo[userid=
1
, userName=
'张金雄'
, sex=
'male'
, birthday=
null
, address=Address[addressid=
1
, city=
'深圳'
, street=
'坂田市场'
, zip='
518001
第
2
个值为: UserInfo[userid=
2
, userName=
'李某某'
, sex=
'male'
, birthday=
null
, address=Address[addressid=
2
, city=
'深圳'
, street=
'坂田路口'
, zip='
518002
第
3
个值为: UserInfo[userid=
3
, userName=
'王某某'
, sex=
'female'
, birthday=
2006
-
08
-
10
00
:
00
:
00.0
, address=Address[addressid=
3
, city=
'深圳'
, street=
'四季花城'
, zip='
518003
第
4
个值为: UserInfo[userid=
4
, userName=
'陈某某'
, sex=
'male'
, birthday=
2006
-
08
-
12
00
:
00
:
00.0
, address=Address[addressid=
3
, city=
'深圳'
, street=
'四季花城'
, zip='
518003
第
5
个值为: UserInfo[userid=
6
, userName=
'哈哈'
, sex=
'male'
, birthday=
2014
-
11
-
20
20
:
24
:
09.102
, address=Address[addressid=
6
, city=
'深圳'
, street=
'坂田2'
, zip='
518000
删除一条数据后进行查询
连接数据库耗时:
0
毫秒
第
1
个值为: UserInfo[userid=
1
, userName=
'张金雄'
, sex=
'male'
, birthday=
null
, address=Address[addressid=
1
, city=
'深圳'
, street=
'坂田市场'
, zip='
518001
第
2
个值为: UserInfo[userid=
2
, userName=
'李某某'
, sex=
'male'
, birthday=
null
, address=Address[addressid=
2
, city=
'深圳'
, street=
'坂田路口'
, zip='
518002
第
3
个值为: UserInfo[userid=
3
, userName=
'王某某'
, sex=
'female'
, birthday=
2006
-
08
-
10
00
:
00
:
00.0
, address=Address[addressid=
3
, city=
'深圳'
, street=
'四季花城'
, zip='
518003
第
4
个值为: UserInfo[userid=
4
, userName=
'陈某某'
, sex=
'male'
, birthday=
2006
-
08
-
12
00
:
00
:
00.0
, address=Address[addressid=
3
, city=
'深圳'
, street=
'四季花城'
, zip='
518003
|
完整工程源代码
下载地址:http://download.csdn.net/detail/xuxiheng/8181849
参考文档
-
在Java SE环境下使用JPA1.0(1)
-
Toplink JPA简介
http://www.cnblogs.com/ctoroad/p/4111447.html