项目用了memcached缓存,但是在过完年回来上班的第二天项目首页挂了,重启后5分钟又挂了,大家着急的在找各种原因。
出现问题
项目一直运行的很正常,但是在2月7号早上9点突然无法访问,重启也解决不了问题。首先考虑的是数据库连接数超了,把连接数直接提到100。然后nginx切换到备份项目,暂时解决了燃眉之急,OK,开始寻找问题出现的原因。打开日志查看日志,发现一直在报错的是memcached,我懵逼了,这个memcached缓存从16年12月开始运行一直到现在跑了3个月没问题,怎么就会把项目给整挂了。
再仔细查看日志,发现报错的地方没有连接数据库的操作,那就不存在多个数据库U连接没有释放的问题。解决了燃眉之急再把数据库连接数切换回来,项目正常运行。memcached的缓存报错依旧,但是也没有重现开始的问题。好吧,既然如此,那就开始解决memcached缓存报错的问题。
问题分析
第一个问题乱码问题
![](/image/2017/02/20170217153113.png)
发现这个有很多乱码,数据放不进去,我找了很久没有解决这是什么问题,之后发现这里面存的东西是Base64位的图片,而且还不止一张,但是放不进去也取不出来,最后归结于存入的东西太大了或者里面有特殊字符,这个不往缓存里放。改用后台调度将Base64位字符转为图片存在图片服务器上,把链接存入数据库,将转换之后的数据存入数据库后就没有这个问题了。
第二个问题是序列化问题
程序启动时将一个实体类放入到缓存里面,我们用的是负载均衡,部署在两台服务器上,查看日志发现其中一个项目能取到这个实体类时另一个就无法取到。最后发现是在序列化的时候没有显示指定serialVersionUID的值,所以在序列化时有可能就会给赋予了随机值,在反序列化时会去找这个实体类再将这个serialVersionUID相对比,如果两个是一样的,就认为是同一个缓存,如果不一样就认为是新的缓存。导致一个能取到另外一个就取不到缓存,之后把所有的类都序列化并显示定义UID就解决了这个问题。
问题总结
在编写代码的时候一定要注意代码规范,否则很可能就会因为自己的一时疏忽大意导致不明不白的问题出现。