记一次地址库修改导致的连锁反应
应有关部门要求,公司内部通知更改地址库的一些地址信息,对国家最新的一些地址更改做出相应正确的调整,如:上海更改为上海市,XXX县改为XXX区 按照正常逻辑来看,大家都会认为数据库改一下就好了。 真正实践的时候会发现并不是想象中那么简单。 不同的部门或者项目组可能维护着不同的地址数据库,为了解决这个问题,地址库查询服务被归拢为公共服务,提供接口对内外提供服务。 当执行sql更改地址成功上线后,问题就来了。 1. 问题一: 某核心业务在调用接口查询地址的时候对地址进行了缓存,巧合的是因为历史原因这个缓存在redis里没有设置超时时间,这就使得存在缓存的数据是不会被更新到的,这数据就存在差异了。 2. 问题二: 某后台管理系统里有读取省市区的配置信息进行不同区域的配置,并且配置结果存储在不同的配置表里,这里导致的问题就是,虽然地址库更改了,但是有原来的配置页面读取和写入的省市区数据还是以前的结果,这就导致了配置的突然失效。 涉及到更改这种基础数据的时候还是要仔细一点,另外一个很重要的就是测试没有完全覆盖到这种情况,不说完全覆盖,我们开发自己本身的单元测试用例都没有,没法对项目本身做简单...

2019-04-15 11:42

类型:工作 标签:地址,bug

三个 bug 引发的思考
> 第一个bug: 登陆模块的扫码登录出现遗漏一段逻辑,和正常的登录不一致导致一小部分用户利用这个漏洞做一些事情。 这个bug隐藏的优点深,是因为这个逻辑涉及到的范围非常小,不是大规模的。 这个bug是清明节放假期间的晚上9点找到的,我翻了很多遍代码发现扫码登录这一块遗漏了一小部分逻辑, 问题的起因是有用户发现登录失败,问题开始上报到客服,客服上报到研发,然后解决问题。 首先可以肯定的一点是用户体验是绝对有问题的,理论上用户在登录失败的时候就应该知道问题出在哪里了,至少用户收到的不应该是失败这种消息 因为当用户收到 失败 这种结果第一想法必然会是你的程序有问题。 再者问题是,这种bug真要去测试的话,是百分百重现的,问题的关键是居然没有产品知道这段逻辑,因为问题爆发的时候并没有传达到产品经理,也没有相应的产品人员作出回应 所以这就直接把问题抛到了开发。 我觉得研发人员作为编码人员应该是解决问题的最后一道防线,如果这种问题大量的直接抛到研发,那可以说明的是第一,逻辑不清晰过于复杂,第二,用户体验极差,第三,产品经理不作为或者不熟悉业务。 这个问题值得思考,一个需求下来是不是做完了就完事了,研发编码完毕,...

2019-04-08 16:01

类型:工作 标签:bug,java

mysql 下 count (*) 和 count (1) 的区别
今天看公司项目发现了一个奇怪sql写法 ``` select count(8) from .... ``` 这也许是开发人员不小心或者是习惯把`*`写成了`8`,当然这并不影响程序运行的结果。 由此引发了我想知道`count(*)`和`count(1)`的区别。 其实关于`count(*)`和`count(1)`性能的争论文章特别多,这类文章都没讲到重点。 我觉得我今天说的这个答案算的上是很权威的,因为答案来自mysql官方文档关于count函数的解释。 现在我能找到的mysql最老的版本文档是5.5 链接如下: https://dev.mysql.com/doc/refman/5.5/en/group-by-functions.html 关于 `count(*)`和`count(1)` 有这样一段话: > InnoDB handles SELECT COUNT(*) and SELECT COUNT(1) operations in the same way. There is no performance difference. 就是说在 InnoDB 引擎下,这两个其实没有性能上...

2019-04-04 07:27

类型:工作 标签:mysql,count

xstream 使用的第二个小问题
之前说过一个xstream使用过程中遇到的一个小问题: [Xstream 对象使用不当导致 CPU 居高不下](https://yuxianghe.net/blog/22) 这次又遇到一个,情况是这样的: 当在生产环境使用`xstream`进行解析xml转换为java对象的时候有一个缓存问题, 如果有两个不相干的接口,这两个接口唯一的共同点就是使用了xstream解析返回结果,且巧合的是两个接口的返回结果xml格式一模一样。 xml结果格式如下: ``` <response><success>true</success></response> ``` 这两个接口都定义了一个bean,且结构一样,A对象定义如下: ``` @XStreamAliasType(value="response") public class Response1 { @XStreamAsAttribute private String success; @XStreamAsAttribute private String errorMsg; public String g...

2019-04-03 06:29

类型:工作 标签:xstream,java

解析 socks5 协议引发的遐想
这几天闲来无事用rust语言写了个解析socks5协议的小应用,精简版的s5,可以将流量代理到中间服务器,目前只实现了TCP,UDP没去看,这个过程让我想到了一些不可描述的事情。 首先socks5协议还是比较简单的,主要问题是socks5认证之后的交互过程稍微麻烦点,虽然是把中间代理服务器当做透明的,互传TCP的数据包即可。 但是如果两方流量需要加密传输的话就得解决第一个包的粘包问题(有人会问为啥第一个包会有粘包问题,因为第一个包过去的数据是s5协议最后一步传要访问的地址和端口数据,第二个数据包才开始真正传输TCP)。 看了下著名的应用shadowsocks并没有刻意去解决粘包问题,而是让第一个数据包和第二个数据包一起发送过去,服务端解密后解析传输即可。 新版本的shadowsocks有人提出了一个实验性的TCP握手协议,也就是说直接在TCP上简单封装一层协议, 大致的协议格式是这样的: ``` 标志版本号(1byte)|首包总长度(2byte)|随机填充长度(1byte)|随机填充数据|原ss首数据包|CRC32(4byte) ``` 不过也想过假设我是中间人,要识别出你这个数据是属于非法访...

2019-03-31 03:36

类型:工作 标签:sock5,rust

我与我周旋久 独孤影 开源实验室