2011-10-24 18 views
13

我想在Java程序中定義一個方法攔截器,換句話說,我想要在每個方法調用時執行一個行爲。 此應用程序不在應用程序服務器中執行,因此我無法在調用攔截器周圍使用EJB。 我發現在標準的Java庫,但一個不錯的Proxy API有限的,因爲它需要在創建代理的接口:具體類的動態代理

Foo f = (Foo) Proxy.newProxyInstance(Foo.class.getClassLoader(), 
             new Class[] { Foo.class }, 
             handler); 

是否有類似的API,它不會強制讓Foo.class聲明爲一個界面?

回答

7

爲什麼不使用CGLIB?有關更多信息,請參閱this article

如果您想代理那些沒有接口的遺留類,該怎麼辦? 您可以使用CGLIB。 CGLIB是一個功能強大,高性能的代碼庫。在封面下,它使用ASM,一個小而快的字節碼處理框架,將現有的字節碼轉換爲 生成新的類。 CGLIB比JDK動態代理方法更快。本質上,它動態生成一個子類,以覆蓋代理類的非最終方法,並將 回調到用戶定義的攔截器。

+0

http://cglib.sourceforge.net/apidocs/net/sf/cglib/Enhancer.html – eliocs

+0

http://cglib.sourceforge.net/apidocs/net/sf/cglib/MethodInterceptor.html – eliocs

+0

我是新到CGLIB。我的理解是它在內存中生成類二進制文件,但現有的類加載器只是從文件系統加載類,所以它如何使用它自己的類加載器? – Chao

1

不幸的是,沒有類的API。許多框架正在使用像CGLIB這樣的字節碼生成庫來實現這一點。

1

你可以嘗試其中一個嘲笑類。最簡單的方法可能是分班,你的班級。或者你可以使用AOP來注入你想要的日誌代碼。

0

sun.misc.ProxyGenerator可用於生成代理類,並且不檢查其「接口」是否都是接口。它的generateClassFile方法將字節碼作爲字節數組提供給您,您可以保存該字節碼以鏈接到未來版本或使用第三方工具進行更改。

請注意,如果任何「接口」有最終方法,當您嘗試加載類時會出現錯誤。