场景:
当用户从手机复制待查询的信息粘贴到form表单,使用axios进行get请求查询时当URL出现 %E2%80%8E 就代表你的URL里面有包含一个ZERO-WIDTH SPACE (ZWSP),这个是肉眼无法发现的空白,ZWSP一般情况是打不出来的,但是如果你是通过WORD等等的文件编辑器复制贴上的就很有可能含有ZWSP,一般情况下ZWSP并不影响阅读但是当它变成URL的一部分,就会变成 %E2%80%8E ,使你的URL出现错误。
问题描述:
输入框中么有request URL后面的那一段编码。而且在axios请求拦截中也打印不出来这个编码字符,所以无法利用常规方法对编码字符进行解码,过滤。那么这个编码字符是什么时候加上的呢?请求前打印没有,但是路径确实存在。这个时候不妨打印一下请求url的length。打印length后发现,虽然字符么有显示出来,但是length却比手动输入的相同的手机号码多了一位(mac系统上是1位,windows系统中多了两位。),由此可以推断,编码的字符确实是请求前就加上了的,只不过没有显示出来。
解决方案:
上面已经分析出来了码的字符确实是请求前就加上了的,只不过没有显示出来,那么我们要做的就是 逼他现原形,在对多出来的字符进行替换过滤。
let str = encodeURI(url); // 对原来的url进行编码,使其现原形
str = str.replace(/%E2%80%AD/g, ""); // 对真身上多余的字符进行替换
str = str.replace(/%E2%80%AC/g, "");
str = decodeURI(str); // 对替换后的url进行解码解码
再去请求就发现编码后的字符已经不存在了。
ps:编码解码的方式有很多,也可以用escape() 和 decodeURIComponent(),
escape方法ECMAScript v3 反对使用,我们最好使用 decodeURI() 和 decodeURIComponent() 替代它。
js中常见编码方式对比:
编码方法 | 定义 | 返回值 | 说明 |
---|---|---|---|
escape() | 函数可对字符串进行编码,这样就可以在所有的计算机上读取该字符串。 | 已编码的 string 的副本。其中某些字符被替换成了十六进制的转义序列。 | 该方法不会对 ASCII 字母和数字进行编码,也不会对下面这些 ASCII 标点符号进行编码: * @ - _ + . / 。其他所有的字符都会被转义序列替换。 |
encodeURI() | 函数可把字符串作为 URI 进行编码。 | URIstring 的副本,其中的某些字符将被十六进制的转义序列进行替换。 | 该方法不会对 ASCII 字母和数字进行编码,也不会对下面这些 ASCII 标点符号进行编码: * @ - _ + . / 。其他所有的字符都会被转义序列替换。该方法不会对 ASCII 字母和数字进行编码,也不会对这些 ASCII 标点符号进行编码: - _ . ! ~ * ’ ( ) 。该方法的目的是对 URI 进行完整的编码,因此对以下在 URI 中具有特殊含义的 ASCII 标点符号,encodeURI() 函数是不会进行转义的:;/?: @ &=+$,# |
encodeURIComponent() | URIstring 的副本,其中的某些字符将被十六进制的转义序列进行替换。 | 已编码的 string 的副本。其中某些字符被替换成了十六进制的转义序列。 | 该方法不会对 ASCII 字母和数字进行编码,也不会对这些 ASCII 标点符号进行编码: - _ . ! ~ * ’ ( ) 。其他字符(比如 :;/?: @ &=+$,# 这些用于分隔 URI 组件的标点符号),都是由一个或多个十六进制的转义序列替换的。 |
1.解释
简单来说,escape是对字符串(string)进行编码(而另外两种是对URL),作用是让它们在所有电脑上可读。
编码之后的效果是%XX或者%uXXXX这种形式。
其中 ASCII字母、数字、@*/+ ,这几个字符不会被编码,其余的都会。
最关键的是,当你需要对URL编码时,请忘记这个方法,这个方法是针对字符串使用的,不适用于URL。
- encodeURI和encodeURIComponent区别
对URL编码是常见的事,所以这两个方法应该是实际中要特别注意的。
它们都是编码URL,唯一区别就是编码的字符范围,其中encodeURI方法不会对下列字符编码 ASCII字母、数字、~!@#$&()=:/,;?+’。
encodeURIComponent方法不会对下列字符编码 ASCII字母、数字、~!()’
也就是encodeURIComponent编码的范围更广,会将http://XXX中的//也编码,会导致URL不可用。(其实java中的URLEncoder.encode(str,char)也类似于这个方法,会导致URL不可用)。