過完五一長假,花了四天的時間來學習Hibernate框架的使用,作為門外漢,先是從sourceforg.net下載 Hibernate3.2,先看官方文檔,只有一個提綱,了解了一下各個包的結構,便開始根據Toturial實踐,基本掌握了它的使用方法之后,盟生了 實現自己的SessionFactory和ConnectionProvider的想法。
閑話少說,要實現我的SessionFactory和ConnectionProvider,不深入了解該體系結構是不行的,先從源代碼分析開始: 首先從org.hibernate.cfg.Configuration.java開始,使用Hibernate框架實現應用程序,首先就要與org.hibernate.cfg.Configuration打交道,要使用
Configuration.buildSessionFactory()方法獲得一個SessionFactory,截取代碼片段如下:
上面的代碼片斷省略了讀取Hibernate配置的代碼,從這個我們可以知道,Configuration類buildSessionFactory()方法實際上返回了SessionFactory接口的實現SessionFactoryImpl。
當我們得到了一個SessionFactory接口的實現SessionFactoryImpl,就要調用它的getCurrentSession()方 法來獲得一個Session,接下來轉到org.hibernate.impl.SessionFactoryImpl.java,來看看 getCurrentSession()方法的實現,代碼片段如下:
在該方法中,SessionFactoryImpl將獲得Session的工作委托給了currentSessionContext.currentSession(),currentSessionContext為何物?其定義為:
org.hibernate.context.CurrentSessionContext;在SessionFactoryImpl的構造函數中,可以看到:
currentSessionContext
=
buildCurrentSessionContext();
馬上追溯到buildCurrentSessionContext()方法,代碼片段如下:
從這里可以發現,SessionFactoryImpl用反射實現了CurrentSessionContext接口的動態裝配。
接下來,暫時將視線從SessionFactoryImpl移開,以org.hibernate.context.JTASessionContext為代表,看CurrentSessionContext接口是如何實現
的currentSession()方法的,打開org.hibernate.context.JTASessionContext.java,找到currentSession(),代碼片段如下:
轉移到buildOrObtainSession()方法,
閑話少說,要實現我的SessionFactory和ConnectionProvider,不深入了解該體系結構是不行的,先從源代碼分析開始: 首先從org.hibernate.cfg.Configuration.java開始,使用Hibernate框架實現應用程序,首先就要與org.hibernate.cfg.Configuration打交道,要使用
Configuration.buildSessionFactory()方法獲得一個SessionFactory,截取代碼片段如下:
1
public
SessionFactorybuildSessionFactory()
throws
HibernateException
{
2
3
return
new
SessionFactoryImpl(
4
this
,
5
mapping,
6
settings,
7
getInitializedEventListeners()
8
);
9
}

2



3

4

5

6

7

8

9

上面的代碼片斷省略了讀取Hibernate配置的代碼,從這個我們可以知道,Configuration類buildSessionFactory()方法實際上返回了SessionFactory接口的實現SessionFactoryImpl。
當我們得到了一個SessionFactory接口的實現SessionFactoryImpl,就要調用它的getCurrentSession()方 法來獲得一個Session,接下來轉到org.hibernate.impl.SessionFactoryImpl.java,來看看 getCurrentSession()方法的實現,代碼片段如下:
1
public
org.hibernate.classic.SessiongetCurrentSession()
throws
HibernateException
{
2
if
(currentSessionContext
==
null
)
{
3
throw
new
HibernateException(
"
NoCurrentSessionContextconfigured!
"
);
4
}
5
return
currentSessionContext.currentSession();
6
}

2

3

4

5

6

在該方法中,SessionFactoryImpl將獲得Session的工作委托給了currentSessionContext.currentSession(),currentSessionContext為何物?其定義為:
org.hibernate.context.CurrentSessionContext;在SessionFactoryImpl的構造函數中,可以看到:


馬上追溯到buildCurrentSessionContext()方法,代碼片段如下:
1
private
CurrentSessionContextbuildCurrentSessionContext()
{
2
Stringimpl
=
properties.getProperty(Environment.CURRENT_SESSION_CONTEXT_CLASS);
3
//
forbackward-compatability
4
if
(impl
==
null
&&
transactionManager
!=
null
)
{
5
impl
=
"
jta
"
;
6
}
7
8
if
(impl
==
null
)
{
9
return
null
;
10
}
11
else
if
(
"
jta
"
.equals(impl))
{
12
if
(settings.getTransactionFactory().areCallbacksLocalToHibernateTransactions())
{
13
log.warn(
"
JTASessionContextbeingusedwithJDBCTransactionFactory;auto-flushwillnotoperatecorrectlywithgetCurrentSession()
"
);
14
}
15
return
new
JTASessionContext(
this
);
16
}
17
else
if
(
"
thread
"
.equals(impl))
{
18
return
new
ThreadLocalSessionContext(
this
);
19
}
20
else
if
(
"
managed
"
.equals(impl))
{
21
return
new
ManagedSessionContext(
this
);
22
}
23
else
{
24
try
{
25
ClassimplClass
=
ReflectHelper.classForName(impl);
26
return
(CurrentSessionContext)implClass
27
.getConstructor(
new
Class[]
{SessionFactoryImplementor.
class
}
)
28
.newInstance(
new
Object[]
{
this
}
);
29
}
30
catch
(Throwablet)
{
31
log.error(
"
Unabletoconstructcurrentsessioncontext[
"
+
impl
+
"
]
"
,t);
32
return
null
;
33
}
34
}
35
}
36

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

從這里可以發現,SessionFactoryImpl用反射實現了CurrentSessionContext接口的動態裝配。
接下來,暫時將視線從SessionFactoryImpl移開,以org.hibernate.context.JTASessionContext為代表,看CurrentSessionContext接口是如何實現
的currentSession()方法的,打開org.hibernate.context.JTASessionContext.java,找到currentSession(),代碼片段如下:
1
public
SessioncurrentSession()
throws
HibernateException
{
2
3
if
(currentSession
==
null
)
{
4
currentSession
=
buildOrObtainSession();
5
6
}
7
8
return
currentSession;
9
}

2



3

4

5



6

7



8

9

轉移到buildOrObtainSession()方法,
1
protected
SessionbuildOrObtainSession()
{
2
return
factory.openSession(
3
null
,
4
isAutoFlushEnabled(),
5
isAutoCloseEnabled(),
6
getConnectionReleaseMode()
7
);
8
}

2

3

4

5

6

7

8

前面SessionFactoryImpl.buildCurrentSessionContext()方法有new JTASessionContext( this ),而此時的factory.openSessio()就是SessionFactoryImpl.openSessio()了。
將目光焦點回到org.hibernate.impl.SessionFactoryImpl.java,SessionFactoryImpl.openSessio()的實現如下:
1
private
SessionImplopenSession(
2
Connectionconnection,
3
boolean
autoClose,
4
long
timestamp,
5
InterceptorsessionLocalInterceptor
6
)
{
7
return
new
SessionImpl(
8
connection,
9
this
,
10
autoClose,
11
timestamp,
12
sessionLocalInterceptor
==
null
?
interceptor:sessionLocalInterceptor,
13
settings.getDefaultEntityMode(),
14
settings.isFlushBeforeCompletionEnabled(),
15
settings.isAutoCloseSessionEnabled(),
16
settings.getConnectionReleaseMode()
17
);
18
}

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

更多文章、技術交流、商務合作、聯系博主
微信掃碼或搜索:z360901061

微信掃一掃加我為好友
QQ號聯系: 360901061
您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點擊下面給點支持吧,站長非常感激您!手機微信長按不能支付解決辦法:請將微信支付二維碼保存到相冊,切換到微信,然后點擊微信右上角掃一掃功能,選擇支付二維碼完成支付。
【本文對您有幫助就好】元
