window.btoa 加密中文报错解决方案

6,623 阅读1分钟

1、加密

项目中使用到 参数加密的方式,想使用个稍微简单点的,即选择了 Window 对象自带的,不过有个难受的地方,

window.btoa('这里是中文')
报错:
_`DOMException: Failed to execute 'btoa' on 'Window': The string to be encoded contains characters outside of the Latin1 range.`_

原因很简单啊,window.btoa 与 window.atob 不支持中文

参考网上各个例子,只能绕一圈来解决该问题:

借助 encodeURIComponent 和 decodeURIComponent 转义非中文字符

后觉得加密出来的密文好长。。
那在加一层 unescape

最后方案:

window.btoa(('这里是中文')) // 报错window.btoa(encodeURIComponent('这里是中文')) // JUU4JUJGJTk5JUU5JTg3JThDJUU2JTk4JUFGJUU0JUI4JUFEJUU2JTk2JTg3window.btoa(escape(encodeURIComponent('这里是中文'))) // JTI1RTglMjVCRiUyNTk5JTI1RTklMjU4NyUyNThDJTI1RTYlMjU5OCUyNUFGJTI1RTQlMjVCOCUyNUFEJTI1RTYlMjU5NiUyNTg3window.btoa(unescape(encodeURIComponent('这里是中文'))) // 6L+Z6YeM5piv5Lit5paH
在地址栏上就出现了简短的
http://localhost:8088/search?key=6L%20Z6YeM5piv5Lit5paH

2、解密

逆向解密,一层一层来:
const key = this.$route.query.keyconst word = decodeURIComponent(escape(window.atob(key)))console.log('解密后文字:' + word) // 解密后文字:这里是中文
小插曲:
并没有出现我想要的,而是报错,解密的页面居然给报错了 - -

URIError: URI malformed
还有的情况报错:
`DOMException: Failed to execute 'atob' on 'Window': The string to be decoded is not correctly encoded.`

解决:

仔细看了下,
加密密文:6L+Z6YeM5piv5Lit5paH
看地址栏:http://localhost:8088/search?key=6L%20Z6YeM5piv5Lit5paH
页面接收:6L Z6YeM5piv5Lit5paH
大概原因是 地址栏传参的时候,“+” 被替换成了 “%20” ,参数接收的时候 “%20” 被编译成了 空格“ ”,最终:这里 “+” 被替换成了一个空格 “ ”
尝试方法,做字符串替换
直接点:
const key = this.$route.query.key.replace(' ','+') // 手动替换const word = decodeURIComponent(escape(window.atob(key)))console.log('解密后文字:' + word) // 解密后文字:这里是中文

以上基本就能实现,地址栏传输参数使用window.btoa中文加密了

还在摸索有什么更好的方案可行...