2011-02-19 49 views
2

在以下Connector/J JDBC/MySQL參考中,它建議我們緩存InitialContext和Datasource的實例。只是使它成爲一個私有的靜態實例解決緩存?難道不應該擔心線程安全(如果有的話)?什麼是最好的'地方'來緩存這個Web應用程序(Restlet + glassfish/Java EE + mysql)?在Java EE web應用中緩存InitialContext和DataSource

有一個GenericDAO類是數據訪問類的,可以這麼說。那麼只是讓靜態實例解決問題呢?這會迫使一些方法成爲我們不想要的靜態方法。建議?

謝謝!

public void doSomething() throws Exception { 
/* 
* Create a JNDI Initial context to be able to 
* lookup the DataSource 
** 
In production-level code, this should be cached as 
* an instance or static variable, as it can 
* be quite expensive to create a JNDI context. 
** 
Note: This code only works when you are using servlets 
* or EJBs in a Java EE application server. If you are 
* using connection pooling in standalone Java code, you 
* will have to create/configure datasources using whatever 
* mechanisms your particular connection pooling library 
* provides. 
*/ 
InitialContext ctx = new InitialContext(); 
/* 
* Lookup the DataSource, which will be backed by a pool 
* that the application server provides. DataSource instances 
* are also a good candidate for caching as an instance 
* variable, as JNDI lookups can be expensive as well. 
*/ 
DataSource ds = 
(DataSource)ctx.lookup("java:comp/env/jdbc/MySQLDB"); 

/* 
*Remaining code here... 
*/ 
    } 
+0

我沒有關於的Restlet部分想法,但在正常的Servlet環境中,你會使用`ServletContextListener`這一點​​。 [Example here](http://stackoverflow.com/questions/4491596/get-database-connection-from-a-connection-pool/4492111#4492111)。如果你熟悉Servlets,那可能會給你新的見解。 – BalusC 2011-02-19 02:25:51

+0

@BalusC:看起來會工作......一旦我實施它,我會發布確認!自從我編寫Web應用程序以來,這已經有一段時間了 - 我完全忘了ServletContext!萬分感謝。 – PhD 2011-02-19 03:26:49

+0

由於InitialContexts不是線程安全的(http://docs.oracle.com/javase/7/docs/api/javax/naming/InitialContext.html),我想緩存必須小心。我不確定DataSources是否有同樣的問題(看起來他們沒有) – marcus 2013-02-20 00:51:03

回答

2

繼續BalusC的link,我可以證實我們可以在使用Restlet時做同樣的事情。但是,按照the example中的代碼獲取您在ServletContext中傳遞的配置實例作爲參數。 Restlet就像'另一個'框架,它使用Servlets作爲適配器來配置自己。因此,這將是棘手的從別的地方傳遞的ServletContext作爲參數代碼(的Restlet使用它自己的上下文對象,它在概念上類似於ServletContext中)

對於我來說,一個靜態方法返回緩存的數據源,似乎「足夠乾淨」,但可能有其他設計/組織方法。

4

如果您使用JAX-RS,那麼您可以使用@Context註釋。

E.g.

@Context 
private ServletContext context; 

@GET 
@Path("whatevers") 
public List<Whatever> getWhatevers() { 
    DataSource dataSource = Config.getInstance(context).getDataSource(); 
    // ... 
} 

但是,如果@Resource註釋也支持你的Restlet的環境中,你可以利用它爲好。

@Resource(mappedName="jdbc/MySQLDB") 
private DataSource dataSource 

這又在技術上更好地被放置在一個EJB,你又被@EJB在你的web服務注入。

@Stateless 
public class WhateverDAO { 

    @Resource(mappedName="jdbc/MySQLDB") 
    private DataSource dataSource 

    public List<Whatever> list() { 
     // ... 
    } 

} 

@EJB 
private WhateverDAO whateverDAO; 

@GET 
@Path("whatevers") 
public List<Whatever> getWhatevers() { 
    return whateverDAO.list(); 
} 
相關問題