微信 access_token 报 40001 invalid token 的一个隐藏原因

在许愿墙最后一天的男生许愿环节中,由于男生数量众多(逃),在一段时间后导致七牛存储的图片挂了,经过查询之后确定是由于获取到的微信 access_token 不正确造成的,报 40001 invalid token 错,因为我的 access_token 是全局缓存在服务器中的,有效期为两个小时,当时我采取的做法是暂时取消全局缓存的策略,采用每次请求一个新 token 的方法来暂时替代,因为考虑到许愿墙的用户数量少而且只是发图片的时候才需要使用到 token,所以即使 token 的获取次数有限制也不会有超出限制的风险。临时修复之后我上网查询后发现,这是一个比较隐藏的原因的造成的:当用户请求比较多的时候,在 token 过期的时候有多个用户同时请求了 token,但是由于网速的问题,导致了一些卡顿,比如 A B 同时请求了新的 token,A 先请求到了 token C,B 后请求到了 token D,此时微信服务器默认正确的 token 应该是 token D,因为多次重复的刷新 token 会使新请求到的 token 覆盖掉前面请求的 token,但是由于返回的时候网络卡顿的原因,本来应该 token C 先返回,token D 后返回的,由于卡顿导致 token D 先返回了,返回之后被存在缓存里,但随后 token C 紧随其后也来到了服务器,这时候 token C 也被写入了缓存覆盖掉了 token D,这时候错误就产生了,服务器缓存里此时存着的是不被微信服务器承认的 token,所以使用这个缓存的 token 去做任何操作都会导致 token 错误被抛出,我在许愿墙遇到的问题也是由此产生的,解决办法就是清除此时的缓存,让服务器去请求全新的有效的 token 重新缓存,我上面的做法并不值得提倡,因为我是基于用户数少考虑并且当时还不清楚具体出错原因考虑的。推荐的方法还是手动清除缓存。