测试那些事儿-后端

基于历史业务迭代,新需求修改了已有表结构,表又有redis缓存!!

这种情况,不能直接提交sql修改生产环境数据,因为redis缓存的是历史表结构中的数据。over!

解决方案:新表结构,用新的redis key。这样,上线后新代码读新key,读不到读表,redis缓存新表结构。

 

多次调用问题优化

某一主业务链路是,A系统调C系统询问用户是否在X分群(判断A系统业务),之后调用B系统,接着B系统调C系统询问用户是否在Y分群(判断B系统业务),最后B系统返回结果给A系统,A系统给返回给用户端api层,其中调用C系统耗时较多。

优化方案:

业务开始时,A系统拿着用户唯一标识问C系统用户存在的所有分群(判断A系统业务),之后将业务数据及人群结果直接传给B系统,B系统用人群结果直接判断业务,之后返回A系统。减少服务间相互调用以缩短接口响应时间,提升用户体验。

 

redis版本升级测试

整理出使用不同redis数据类型的接口(string(字符串),hash(哈希),list(列表),set(集合)及zset(sorted set:有序集合),在当前版本缓存至redis,版本升级后,调用使用不同redis数据类型的接口,数据返回正常即测试通过。

 

核心逻辑一致性校验

问题:

主业务执行时取了A城市配置,主业务的某一子业务没有校验主业务执行的城市,执行子业务时拿了前段传回的B城市,使用B城市配置计算了子业务。

解决:

服务端做一致性校验

 

出入口校验逻辑应一致 

问题:

配置提交接口没有校验A项是否必填,命中接口校验A项必填,否则报错。

解决:

出入口校验逻辑保持一致。

 

同一业务不同处理方式及对应结果:

 W开发的处理方式:

下载文件,将所有用户数据存储到一个文件里面,然后每次读取100个用户发消息。这种处理方式服务器cpu、内存均无异常。

 

Y开发的处理方式:

下载文件,将文件解压(大数据那边的数据包10万用户1个文件,约1.4M),然后将文件读取到内存中使用for循环发券。这种处理方式导致服务器内存、cpu飙升。

 

记一次服务线上时不时宕机:

原因:

主表数据百万级,研发设计某一与主表关联业务表结构时,没有把相关数据冗余到新表(只存了主表id)。

实现新业务多项筛选条件组合查询时,研发先将A条件(对应的数据在子表储存)查询结果存到内存,再根据其他条件处理数据后返回结果。

内部使用系统,没有做压测。

上线后,早晨业务调用量大,使用A条件查询的次数太多,加之A条件查询出的数据量超过10万条,导致内存溢出(每次查询都会存,直到一次查询结果返回才释放内存),直接就把服务内存打满把机器干趴下了。

反思:

时间允许的情况下,内部使用系统也做压测吧。

 

记一次服务由amq切rmq时线上事故:

背景:

主业务的服务器有过两次宕机,分析发现服务在连接amq集群时超时,服务一直尝试连接,导致服务夯死。研发决定把amq件切成rmq。

涉及到40多个服务,经研发组讨论,定制了严格的上线方案。

 

事故:

es服务发完灰度后,没有在rmq的console确认es服务是否连接到了rmq集群,就直接发了生产环境,事故发生了。排查发现es服务生产环境连接消息集群配置错误了。。

 

反思:

为什么没有按照流程确认服务是否正常连接到了rmq?

上es服务之前,很多服务切rmq都已经上线了,并且都没出问题,导致测试和开发都放松了,没有按照流程走。

任何时间,一定不能麻痹大意!

 

副本:

es服务听主服务消息,变更es库相关数据。不管是什么原因,一但消息积压没有在业务允许的时间范围内及时消费,es服务再消费这些过时消息,会导致数据状态不一致,就会引起问题。

最后研发讨论,es消费消息时要加一层check机制,当一条消息没有及时消费时(消息体带主业务落表时的时间戳,收到消息后超过一定时间内即认为过期了),就要查询原始数据更新es库。

 

已上线的老接口改动慎重:

1. 接口返回数据结构不能变,返回数据字段的类型不能变。

  开发因为开发周期或者个人习惯,很少做返回数据异常的兼容,如果改变接口返回数据,会导致调用方解析异常。

2. 业务逻辑谨慎变动。

  中台校验验证码接口,一个验证码可以多次使用。安全组的同事说这块不符合安全规范,中台(老服务,已经换了几波人了)开发看了代码,发现里面有段备注说个别手机校验短信验证码时请求了多次接口。然后找端上问了一圈,说那些机型已经没了。于是就改了,结果上线后多数闪送员反馈修改、注销手机号时校验手机验证码报验证码失效。

  稳妥的做法应该是线上加日志,看看那些业务线存在多次校验的情况,再决定是否要修改。

 

记一次内存溢出问题:

订单画像服务提供订单是否与画像匹配接口,该接口处理业务时的流程是:将画像所有规则加载到内存,然后遍历订单是否命中某一条规则。

第一期该服务提供手动生成画像,生成画像规则颗粒度大,一个画像配置生成的规则不超过500条。所以上面的处理方式没问题。

订单画像服务之前由开发A负责,A离职后B负责。业务迭代后,画像服务支持提供系统生成画像,生成画像规则的颗粒度很小,一个画像生成的规则超过了10万条(12M),查询一个订单是否命中该规则时加载12M,订单高峰期加载到内存的数据过多,最终导致内存溢出。

 

记一次接口超时问题:

CRM系统调大数据接口查询商户店铺(一个商户下有N多个店铺),CRM开发处理方式是每次传10个店铺ID查询数据,多次调大数据接口直到查完一个商户下所有店铺的订单数据,将数据组装后返回给前端展示。

商家版放开了店铺创建数量后,线上有一个商户账号下创建了1千多个店铺,加载该商户店铺订单数据时前端报接口超时。查询该商户店铺订单数据时中间调了10多次大数据接口,一次调用400ms左右,10次就4s了。

这里有个知识点:内存处理数据是纳秒级别的,服务相互调用是毫秒级别的,如果两个服务之间有交换数据的需求,在内存消耗允许范围内尽量做到1次链接将所需数据拿到,然后在内存中处理。

 

线上服务器更换IP:

找开发确认要更换的IP是否在代码中有直接用到!!不知道出于何种原因,总有些项目中开发直接使用IP而不是域名的情况。。

 

sql中查询条件变更导致慢sql拖垮服务器:

之前商户数据是根据手机号查询(有索引),因商户更改手机号导致商户的历史数据查询有bug,开发将查询条件改为userId(无索引),测试环境数据量级不够,没有触发慢sql,上线后查询触发慢sql打满服务器cpu导致服务异常。

对于查询的数据量级很大的接口,上线前一定要走压测。

 

幽灵问题:

问题:线上有时候有人登录后显示别人的身份信息

原因:父类整一个静态变量,线程中的变量没销毁前(同一毫秒)另外一个人登录就会拿到第一个人的身份信息。

 

数据库新增字段引发的bug:

数据库新增字段,开发忘记更新某些sql,导致数据提交、更新失败导致bug。所以某个表中新增了字段,问清楚涉及到该表的接口有哪些,都需要回归。

 

给内部平台调用的接口其他组开发用给公网用户调用:

优惠券系统开了个充值返券信息列表接口,该接口多表查询,券系统开发考虑是个内部接口,没在意接口性能问题,就提供给券及CRM内部系统使用了。结果CRM系统将改接口暴露给了商户端,商户端展示充值返券信息时调用了该接口,该接口访问量上升,导致数据库性能下降。

 

记一次不同组程序员设计模式的潜在问题:

业务:用户端、闪送员端读取某个城市是否开启了某一功能,决定是否展示相应的模块。系统组支持配置及提供两个端查询配置。

用户端开发让系统组开发提供接口查询城市配置;闪送员端开发让系统组开发在配置变动时发mq消息,将配置同步一份保存在自己的业务库,读取自己的业务库数据决定是否展示相应模块。

用户端开发图省事,不考虑系统间解耦,这种设计存在的潜在问题是:当系统端服务挂了,用户端相应模块也就不好用了;另外,也增加了系统组服务的性能压力。


上传文件失败:
问题:传的excel文件首先存到系统临时目录,然后解析导入数据;这个临时目录被系统清掉了,上传文件找不到目录存,报错了
解决方法:系统目录按理说会一直在,但不能保证一直在。研发设计环节每次上传文件,先创建个临时目录存文件就会避免这种问题。

 

posted on 2018-06-26 15:45  fengZQ  阅读(195)  评论(0编辑  收藏  举报

导航