为什么需要URL编码?
根据网络标准RFC 1738的硬性规定:
"只有字母和数字[0-9a-zA-Z]、一些特殊符号"$-_.+!*'(),"[不包括双引号]、以及某些保留字,才可以不经过编码直接用于URL。"
即URL不支持汉字,[] 等字符。
但在使用URL传参时(如get请求),参数值经常包含汉字,[] 等字符,怎么办?
将这些URL不支持的字符进行编码后使用。
如 https://www.baidu.com/s?wd=春节 编码后为 春节_百度搜索
为什么浏览器中的网址可以有中文等URL不支持的字符?
因为浏览器对非法URL自动进行了编码!
虽然浏览器的地址栏中,看到的URL包含中文,但实际的网络请求对URL进行了编码
为什么要主动对URL进行编码?
虽然浏览器自己会对URL进行编码,但不同的操作系统、不同的浏览器、不同的网页字符集,将导致完全不同的编码结果。(详见 关于URL编码 - 阮一峰的网络日志 )
服务器不可能对错综复杂的编码结果进行处理,所以,需要使用Javascript先对URL编码,然后再向服务器提交,不给浏览器插手的机会。
因为Javascript的输出总是一致的,就保证了服务器得到的数据格式的统一。
Javascript对URL进行编码
以下三种函数都可以对URL进行编码,区别主要在于不编码的字符不同,具体使用详见各自的使用场景:
encodeURIComponent() 【推荐】
- 使用场景:对url中的参数进行编码
- 不编码的字符: ~!*()
encodeURI()
- 使用场景:对整个url进行编码
- 不编码的字符: ~!@#@{content}*()=:/,;?+'
escape() 【不推荐】
- 不编码的字符:@*/+
- 在用户提交的表单字段中,如果有空格,则会被转化为+字符,而服务器解析的时候则会认为+号代表空格。由于这个缺陷,应当尽量避免使用escape方法。
Javascript对URL进行解码
当Javascript需要从URL中解析出参数时,获取到的URL通常是已编码的,所以需要先对URL进行解码,再进行解析。
以下三种函数都可以对URL进行解码,与编码函数一一对应。
unencodeURIComponent(string)
unencodeURI(string)
unescape(string)
实战案例——axios请求拦截器中,对get请求的参数全部进行URL编码
// 添加请求拦截器 axios.interceptors.request.use(function(config) { // 对get请求的参数全部进行URL编码 let url = config.url if (config.method === 'get' && config.params) { url += '?' let keys = Object.keys(config.params) for (let key of keys) { url += `${key}=${encodeURIComponent(config.params[key])}&` } url = url.substring(0, url.length - 1) config.params = {} } config.url = url return config; }, function(error) { return Promise.reject(error); });