注意,这里我只说明思路,不展示具体代码
1.问题描述
很多开发都表示,token被懂行的人直接从浏览器或者抓包工具获取到了,然后直接用这个token请求业务数据怎么办?
最常说的方法,肯定是http
升级到https
了。
可问题是,公司要是不愿意花钱买证书,咋办?
所以,这里就介绍第二条路:生成一次性token,用一次就废了,这样别人拿到了token也用不了。
2.思路
在header中新增一个header,参数名假设为secret
,值是:加密(user_code,url_path,请求时间)
我解释下,
user_code
就是当前请求的用户编码
url_path
就是请求的path,不带参数,但如果是variablePath就带上,因为它也算是URL的一部分.
请求时间
就是前端请求接口的时间,推荐格式yyyy-MM-dd HH:mm:ss.SSS,到毫秒
加密
就是将user_code
、url_path
和请求时间
拼接后进行加密,当然,肯定是前端加密,后端解密,加密算法推荐rsa
3.原因
将上面3个参数凑到一块,可以发现,我能知道某个用户在某个毫秒时间请求了某个接口,后端解密secret
后,将解密值做md5(),存放到Redis或数据库中,可以发现,Redis或数据库中存放的一定是用户最新请求的md5信息,通过比对md5值是可以避免上一个请求的token被重复利用的。
而且,更为重要的是,我们需要把user_code
、url_path
做md5
,然后将其作为key,请求时间
作为value存放到Redis或数据库中。相比而且,这个数据比上一个md5的数据更重要,如果只需要一个,那就保留这一个。
可怎么避免以前的token被拿来使用呢?难道要记录历史的token?
我要说让大家记录历史token,大家估计都得说,SHABI,所以换一种思路。
如果爬虫专家拿到了/user/list
接口的token
和secret
,这个secret
里记录了请求用户、请求路径、请求时间的,我们可以比对解析出来的请求时间和数据库中存放的最新的时间作对比,而且这个对比精细到了用户的具体请求上了。通过请求时间的对比,如果解析出来的请求时间比数据库中存放的时间要早,那肯定就是历史token
和secret
。
后台服务是异地多实例的,怎么保证请求时间一致?
说实话,这个问题不是我这篇文章要说的事情,这个问题的解决方法,网上太多了,大家自己搜,而且这问题不难。
我只看到了防窃取,怎么防伪造?
token
解析后,可以拿到用户信息,secret
也可以解析出user_code
,比对一下就知道了。其次,secret
是经过加密的,如果解密没通过,或者解密通过了,但是不符合user_code,url_path,请求时间的格式要求,都是伪造的token。