2012-03-26 25 views
3

我已經從How to gain access to a ServletContext instance from any method?的問題中讀到,如果我想從我的Java Web項目中的任何類訪問Servlet上下文,我可以聲明一個靜態字段,指向ServletContextListenerServletContext,但靜態字段是在Java Web應用程序中是一種不好的做法,因爲直到JVM關閉時GC才能收集它(如果我在這方面錯了,請糾正我)。是否有另一種方式來訪問ServletContext而不使用偵聽器或將其作爲參數接收?還有另一種解決方法來解決這個問題?我正在爲Web應用程序使用JSF 1.2和JBoss 5.1 GA。靜態Servlet上下文變量

注:我知道我可以使用

(ServletContext)FacesContext.getCurrentInstance().getExternalContext().getContext(); 

訪問ServletContext的,但運行在啓動時需要訪問的ServletContext和FacesContext.getCurrentInstance()尚未初始化的方法。

UPDATE:

我們需要當web應用程序啓動時,從web.xml中加載一些IP的成String常量。爲此,我們創建了一個Singleton類,它在變量中加載上下文參數,然後用單值類的一些值填充字符串常量。這個Singleton類管理着大量的數據,並且發生內存異常錯誤。爲了解決這個問題,我們將Singleton類修改爲一個作爲ServerContext屬性加載的簡單類,但是由於沒有這個(不再是)Singleton的實例,所以不能加載String常量。

+0

你究竟在哪裏需要它,爲什麼?爲什麼你不只是在'ServletContextListener'本身做這個工作呢? 'FacesContext'只能在每個HTTP請求上初始化,這些HTTP請求的URL匹配'FacesServlet'的URL模式並因此調用了它。 – BalusC 2012-03-26 20:44:49

+0

@BalusC有一個常量字符串,它使用web.xml中的上下文參數在靜態方法中加載。要做到這一點,它需要'ServletContext#getInitParameter'。實際的解決方法是創建一個Singleton類,該類將這些值加載到實現「ServletContextListener」但實際產生內存問題的類中,因此我們需要創建該類的實例並將其作爲ServletContext中的一個屬性加載,但隨後我無法訪問靜態方法。 – 2012-03-26 20:58:31

+0

*「創建一個Singleton類,在實現ServletContextListener的類中加載這些值」*我無法想象這是多麼的合理。什麼是功能要求?你是否需要它最終在一個'公共靜態'變量?爲什麼? – BalusC 2012-03-26 21:07:24

回答

2

我不知道你爲什麼需要一個單身人士。您在應用範圍中存儲的Just create one bean。

@Override 
public void contextInitialized(ServletContextEvent event) { 
    ServletContext context = event.getServletContext(); 
    Set<String> ips = parseContextParamSomehow(context.getInitParam("ips")); 
    Manager manager = new Manager(); 
    manager.setIps(ips); 
    context.setAttribute("manager", manager); 
} 

它將在EL語境中由#{manager}提供。也作爲一個任意的JSF託管bean的託管屬性。另一種方法是創建一個應用程序範圍的JSF託管bean並在其構造函數中執行該任務,但是您將其構造推遲到涉及該bean的第一個HTTP請求。

+0

辛格爾頓是一個緩存實現(是的,我們不知道ehcache或其他框架),但這是一個不好的解決方案,所以,而不是添加此框架,我的老闆想要用我們編程的類來解決這個問題。順便說一下,你的解決方案看起來很有趣,但是我怎樣才能訪問未在HTTP請求中調用的方法中的'context'? – 2012-03-27 13:45:40

+0

只需按照答案中顯示的「事件」? – BalusC 2012-03-27 13:53:57

相關問題