国际化预过滤器

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了国际化预过滤器相关的知识,希望对你有一定的参考价值。

1、国际化:

开发系统、网站、平台的页面显示的效果可以支持多个国家的语言。

1)引用的资源的jsp页面。(没有明确的指出是用什么样的语言)

2)体现不同语言的资源文件。 msg_zh_CN.properties

3)Jsp页面上,使用format格式化标签库,引用资源文件<fmt:message>;

2、Filter

1)他是一个类,一个特殊的类,可以说是servlet的升级版本。Filter

2)过滤或者拦截的作用,如果符合条件就放行,不符合就返回。(过滤器中写)

3)过滤的是请求和响应。(过滤的过程是双向的)

4)过滤器可以有多个,这样就构成了过滤器链

如果有多个过滤器的话,过滤顺序是根据在web.xml的配置顺序决定的,先映射县过滤。

5)定义一个过滤器:filter

6)编码过滤器

7)控制登录权限。

 

国际化中,为不同的语言要添加不同的语言 库。通常用 msg代表信息,语言代号,区域代号。

也就是msg_语言代号_区域代号.properties。实现语言的配置,从而实现国际化。

 

先把页面做出来:

然后在页面中:<%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %>

 

明天讲:监听器和自定义标签

 

 

我只是想在本页实现中英文切换。

<%@ page language="java" import="java.util.*" pageEncoding="utf-8"%>
<%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %>
<%
String path = request.getContextPath();
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";
%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
  <head>
    <base href="<%=basePath%>">
    <fmt:setLocale value="${ param.locale}"/>
    <fmt:setBundle basename="msg"/>
    
    <title><fmt:message key="register"/></title>
  </head>
  <body>
  <a href="register.jsp?locale=zh_CN">中文</a>
  <a href="register.jsp?locale=en_US">英文</a><br/>
      这是个假的页面,只是为了展示多语言效果
        <form action="#" >
            <fmt:message key="name"/>:<input type="text" /><br/>
            <fmt:message key="password"/>:<input type="text" /><br/>
            <fmt:message key="age"/>:<input type="text" /><br/>
            <fmt:message key="gender"/>:<input type="text" /><br/>
            <fmt:message key="address"/>:<input type="text" /><br/>
            <fmt:message key="mail"/>:<input type="text" /><br/>
            <input type="submit" value="提交"/>
        </form>
  </body>
</html>

但是发现了一个bug,下面的能够正常展示,但是在标题里面,就有问题

技术分享

因为fmttitle都放在一个里面,所以可能会有问题,所以解决的办法是,标题就用中文或者英文,不允许那个人他一定可以看懂的。

有一些事情要说一下,就是在2014版本里面,是支持多语言输入的,直接进行了utf-8码的转换,但是在2013里面,就只能在properties里面一个属性一个属性的添加。

 

另外一种方式是采用C:\Program Files\java\jdk1.6.0_43\bin目录下的 natice2ascii.exe实现编码转换,要求是键值对的形式。把要翻译的文件给翻译,让他们写成txt在交回来,在src目录下,复制粘贴然后解决所有问题。

技术分享

当然了,txttxt properties properties 或者 像上面那样,这四种形式都是允许的。都能实现转码。再有就是 在utf-8里面,大小写,对应同一个字符。

过滤器在进去的时候要进行一次过滤,出去的时候也要进行一次过滤。

过滤顺序以在web.xml的配置顺序作为过滤依据,先进行映射配置的过滤器,优先进行过滤。

这样,我们可以实现两个事儿

1、为所有的输入内容设置编码格式。

2、如果已经登录,那么允许访问,如果,没有登录那么返回登录界面,这样就避免了直接通过地址栏对内容进行访问而造成的数据不安全。

不要忘了dofilter放行

 

arg0.setCharacterEncoding("utf-8");

arg2.doFilter(arg0, arg1);

 

<filter>
      <filter-name>SetEncoding</filter-name>
      <filter-class>com.letben.filter.SetEncoding</filter-class>      
  </filter>
  <filter-mapping>
      <filter-name>SetEncoding</filter-name>
      <url-pattern>/*</url-pattern>
  </filter-mapping>

虽然是双向过滤,但是出的时候,已经在servlet中的方法体实现了内容的写出,到了过滤器对已经乱码的内容转码。已经没什么意义了,所以只能控制入口,出口并不能有什么好办法。

下面是一个成型的版本:可以看一下。

 <filter>
      <filter-name>encodingFilter</filter-name>
      <filter-class>com.letben.filter.EncodingFilter</filter-class>
  </filter>
  <filter-mapping>
      <filter-name>encodingFilter</filter-name>
      <url-pattern>/*</url-pattern>
  </filter-mapping> 
  <filter>
      <filter-name>loginFilter</filter-name>
      <filter-class>com.letben.filter.LoginFilter</filter-class>
  </filter> 
  <filter-mapping>
      <filter-name>loginFilter</filter-name>
      <url-pattern>/com.letben.servlet.delogin.*</url-pattern>
      <url-pattern>/delogin/*</url-pattern>
  </filter-mapping>

作为登录过滤器,和编码过滤器的设置方式,编码过滤器aoe就可以,但是作为登录过滤器来讲,有些内容允许访问,有些不允许,当然权限的开放与关闭,都还没有处理好。如果只是容许用户通过登录才能查看的话,那么上面的处理方式是合理的。解释:因为用户想要非法查看的mvc中的v和c,模型层不对外开放、也不可见。所以用户有必要看的就只有v和c。所以需要为v和c添加对应的过滤器,如果简单粗暴地aoe会导致,连登录页自身也不可访问。所以需要目录的设置,把登录页和登录页的对应逻辑空出来。在过滤器映射的时候,也要对应的将servlet也就是c层重新划分,将servlet去分成登录控制层和非登录控制层。这样就可以在配置的时候使用com.letben.servlet.delogin.*来处理所有需要登录才能访问的servlet逻辑,在页面方面,也将页面划成登录页面和非登录页面。在web.xml映射的时候配置出/delogin/*对应的页面。来处理所有通过直接在地址栏输入就能访问的事件。

两个重定向注意体会:

LoginServlet中:
String name = request.getParameter("name");
        String password = request.getParameter("password");
        
        User user = userService.login(name, password);
        if(user!=null){
            System.out.println(user);
            request.getSession().setAttribute("user", user);
            request.getRequestDispatcher("delogin/index2.jsp").forward(request, response);
        }else{
            System.out.println("登录失败:用户名或者密码");
            response.sendRedirect("index.jsp");
        }
LoginFilter中
HttpServletRequest request = (HttpServletRequest) arg0;
        Object object = request.getSession().getAttribute("user");
        if(object!=null){//得到User
            arg2.doFilter(arg0, arg1);//放行
        }else{
            HttpServletResponse response = (HttpServletResponse) arg1;
            response.sendRedirect("http://localhost:8080/FilterForSafety02/index.jsp");
//这里可能会出现回环,一定要定位到开始的位置。
//bug在于,一旦从请求页中,直接申请一个子目录地址,如果发现该用户未登录,那么就在子目录中找寻登录页,找不到,就一直找,就会出现重定向循环。
        }

 

LoginFilter中,在登录页面,输错了,就要重新输入,直接本页重定向就可以,但是在过滤器中,不知道用户登录到哪个页面进入了哪一层,这样就通过绝对路径,不通过“../”的形式,来回查找。

 

以上是关于国际化预过滤器的主要内容,如果未能解决你的问题,请参考以下文章

ngx-translate实现国际化:this.translate.use()this.translate.get()this.translate.instant()onLangChange(代码片段

js 常用代码片段

分享前端开发常用代码片段

收藏|分享前端开发常用代码片段

关于js----------------分享前端开发常用代码片段

Liferay 7.3:如何预配置嵌入在页面片段中的 portlet?