2008-11-03 25 views
2

我有一个Web应用程序,我想扩展到支持带有新URL的多种语言。例如,www.example.com/home.do保持英语,但www.example.com/es/home.do是西班牙语。我的第一个想法是创建一个过滤器,将/es/home.do这样的传入网址重写为/home.do(并在请求中设置区域设置);这工作正常。该过滤器包裹的ServletRequest用了HttpServletRequestWrapper它覆盖getContextPath()返回的语言:覆盖HttpServletRequest中的getContextPath(用于URL重写)

class FakeContextRequest extends HttpServletRequestWrapper { 

    private String context = ""; 
    FakeContextRequest(HttpServletRequest request, String context) { 
    super(request); 
    // snip some validation code 
    this.context = request.getContextPath() + context; 
    } 
    @Override 
    public String getContextPath() { 
    return this.context; 
    } 
} 

我的过滤转发给适当的请求如下:

FakeContextRequest fr = new FakeContextRequest(request, lang); 
fr.getRequestDispatcher(newResourceName).forward(fr, response); 

我的问题是,未来的servlet没有按无法正确转发。下一个servlet(通常是Struts ActionServlet)转发到JSP(通常使用Struts Tiles);当我到达JSP时,HttpServletRequest已被多次包装,并且所讨论的对象将上下文报告为空(根环境,这是应用程序实际部署的地方)。

我想重新编写上下文,以便所有已存在的上下文感知代码都可以自动将语言插入到写入的URL中。这可能吗?

编辑:我解决了我的问题,通过使用包装HttpServletResponse而不是包装HttpServletRequest;我在response.encodeURL()方法中重写URL。

回答

1

我不确定覆盖getContextPath()是否足以解决您的问题。如果Struts在屏幕下调用ServletContext.getContextPath(),或者使用getRequestURI()等?

+0

好点。看来,我将不得不寻找另一种方法。 – 2008-11-05 18:04:15

0

据我所知,传统的做法是使用accept-language HTTP头。演示文稿语言是一种演示文稿细节,不应该由用于浏览应用程序的一组URL来表示。

+0

接受语言标题将不起作用,因为它与搜索引擎不兼容。搜索引擎需要独特的链接才能以不同的语言来搜索内容。 – 2008-11-04 14:27:47

0

我通过在response.encodeURL()和朋友中进行URL重写来解决了我的问题。请求对象在整个请求链中被包装和替换,但响应对象似乎是通过不受干扰的。这工作非常可靠。

+0

我认为这是UrlRewriterFilter项目中使用的方法http://tuckey.org/urlrewrite/ – 2010-01-14 07:32:19