关于Java:Spring Security MVC特殊字符编码

Spring security + mvc special characters encoding

我有一个实现了Spring安全性的项目,该项目运行顺利,视图看起来正常,除了记录消息和电子邮件消息外,编码没有问题。

电子邮件:

在我的身份验证控制器上,我有一种发送电子邮件以重置密码的方法,我在控制器上生成了网址

1
final String url = contextPath +"/user/resetPassword?id=" + user.getId();

如果我使用模板,则如下所示:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
        title ="Restablecer contrase?a";
        body = String.format("%s:\
"
+
                       "\
"
+
                       "Click on this link and you can reset your password:\
"
+
                       "%s\
"
+
                user.getFirstName() +"" + user.getLastName(),
                url);

        String encodingOptions ="text/html; charset=UTF-8";
        msg.setHeader("Content-Type", encodingOptions);
        msg.addRecipient(MimeMessage.RecipientType.TO, new InternetAddress(user.getEmail()));
        msg.addFrom(new InternetAddress[]{new InternetAddress(env.getProperty("support.email"))});

        msg.setSubject(title,"UTF-8");
        msg.setText(body,"UTF-8");

生成的网址是:

1
http://localhost:8080/user/resetPassword?id=3D6

但是正确的网址是:

1
http://localhost:8080/user/resetPassword?id=6

记录器:

记录器发生类似的情况。

1
LOGGER.info("Restablecer contrase?a");

在控制台上,消息为:

1
Restablecer su contrase?±a

关于记录器的这种情况非常奇怪,暂时可以正常工作,暂时可以出错。

有什么想法吗?

我的配置:

IntelliJ 14

Apache 8.0.15

具有org.springframework.web.filter.CharacterEncodingFilter

的web.xml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
    xsi:schemaLocation="
      http://java.sun.com/xml/ns/javaee
      http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
id="WebApp_ID" version="3.0"
>

    <context-param>
        <param-name>contextClass</param-name>
        <param-value>org.springframework.web.context.support.AnnotationConfigWebApplicationContext</param-value>
    </context-param>
    <context-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>org.admin.spring</param-value>
    </context-param>

    <listener>
        <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
    </listener>

    <listener>
        <listener-class>org.springframework.web.context.request.RequestContextListener</listener-class>
    </listener>

    <servlet>
        <servlet-name>mvc</servlet-name>
        <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
        <load-on-startup>1</load-on-startup>
    </servlet>
    <servlet-mapping>
        <servlet-name>mvc</servlet-name>
        <url-pattern>/</url-pattern>
    </servlet-mapping>

    <filter>
        <!-- This filter has to come before other filters. -->
        <filter-name>characterEncodingFilter</filter-name>
        <filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
        <init-param>
            <param-name>forceEncoding</param-name>
            <param-value>true</param-value>
        </init-param>
        <init-param>
            <param-name>encoding</param-name>
            <param-value>UTF-8</param-value>
        </init-param>
    </filter>

    <filter-mapping>
        <filter-name>characterEncodingFilter</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

    <filter>
        <filter-name>springSecurityFilterChain</filter-name>
        <filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>springSecurityFilterChain</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>
    <filter>
        <filter-name>localizationFilter</filter-name>
        <filter-class>org.springframework.web.filter.RequestContextFilter</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>localizationFilter</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

    <jsp-config>
        <jsp-property-group>
            <url-pattern>*.jsp</url-pattern>
            <page-encoding>UTF-8</page-encoding>
        </jsp-property-group>
    </jsp-config>

    <session-config>
        <session-timeout>10</session-timeout>
        <cookie-config>
            <name>AUTHSESSION</name>
            <http-only>true</http-only>
        </cookie-config>
        <tracking-mode>COOKIE</tracking-mode>
    </session-config>
</web-app>

在apache server.xml配置中,我已使用URIEncoding = " UTF-8 "

更改了2个连接器

1
2
3
4
5
6
7
8
9
10
11
12
13
<!-- A"Connector" represents an endpoint by which requests are received
     and responses are returned. Documentation at :
     Java HTTP Connector: /docs/config/http.html (blocking & non-blocking)
     Java AJP  Connector: /docs/config/ajp.html
     APR (HTTP/AJP) Connector: /docs/apr.html
     Define a non-SSL HTTP/1.1 Connector on port 8080
-->
<Connector port="8080" protocol="HTTP/1.1"
           connectionTimeout="20000"
           redirectPort="8443" URIEncoding="UTF-8" />

<!-- Define an AJP 1.3 Connector on port 8009 -->
<Connector port="8009" protocol="AJP/1.3" redirectPort="8443" URIEncoding="UTF-8" />

Pom.xml:

1
2
3
    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    </properties>

WebMvcConfigurerAdapter类别:

1
2
3
4
5
6
7
8
9
@Bean
public MessageSource messageSource() {
    ReloadableResourceBundleMessageSource messageSource = new ReloadableResourceBundleMessageSource();
    messageSource.setBasename("classpath:messages");
    messageSource.setUseCodeAsDefaultMessage(true);
    messageSource.setDefaultEncoding("UTF-8");
    messageSource.setCacheSeconds(0);
    return messageSource;
}

控制台中的问题很常见...您用来查看日志的控制台或应用程序不支持UTF-8(我敢打赌您会在Windows上运行您的应用程序)。

电子邮件的问题看起来很奇怪,因为3D=符号的八进制表示形式。
编辑

除了生成电子邮件的实际代码(我认为您的电子邮件提供商或电子邮件客户端不会更改URL)之外,我没有想到您所生成的电子邮件中可能存在的问题。配置JavaMail时,将属性mail.debug设置为true,以获取有关您的应用程序要发送到电子邮件服务器的更多信息。我很确定您会发现自己发送的是奇怪的字符

此外,尝试从生成url字符串开始,直到JavaMail发送电子邮件以查明添加这些字符的确切位置为止,逐行(在每种方法中)调试代码。