服务端性能测试
目标
如果说客户端性能测试主要为验证单个用户的客户端程序运行的流畅性,那么服务端性能测试主要验证的就是大量用户连接服务端时,服务端程序运行的流畅性。但服务端性能不像客户端那样,有着较为直接的感观体验,所以更主要的测试目的是为了验证服务端能否达到预期负载能力,以及在最大负载下,游戏世界运行是否正常顺畅,没有报错。
服务端性能测试也比客户端性能测试较难操作,需要设计更具针对性的测试情景,例如多人登录创角,多人同时打副本,多人聊天,多人收发邮件,多人数据存盘等。这里的多人不是几十人几百人的数量,而是几千几万,甚至百万千万的数量级。所以做服务端性能测试,一定需要程序支持,先做出一个能大量并发,模拟用户行为的机器人工具。当然也有现成的并发工具,例如“LoadRunner”、“QTP”等,写好机器人与服务端连接通信的脚本逻辑后,这些工具会帮你自动分发,然后并发运行,并且统计响应的成功失败率,以及响应时间。但是这些工具较难上手,尤其是环境部署方面较为复杂,如果不是长期重复使用的话,成本太高。从成本和适用性来说,还是结合自身项目,直接实现协议通信的机器人工具更快捷方便一些,也能够更灵活地进行扩展和修改。
游戏服务器基本都是在linux系统上运行的,所以服务端性能测试基本等同于测试linux系统上的程序性能。linux系统本身自带很多性能监控的命令,这里不再一一详尽地介绍,有位大牛叫Brendan Gregg的,整理一个全面的linux系统性能工具图,如下:
目前我主要采用的是dstat来采集linux性能数据,并进行了一些扩展修改,点击查看具体做法。
需要注意的点:
- 进行服务端性能测试时,用于并发产生负载压力的机器人或并发工具不要与被测服务端在同一台机器上,因为机器人工具本身也极为消耗系统性能,会对服务端程序的稳定运行产生干扰。
- 进行服务端性能测试时,很容易把精力主要放在测试工具的学习和使用上,而忽略了测试目标和方案设计,以及如何通过结果数据来证明和定位问题。
- 因为Linux系统基本都是多核,而大部分性能工具统计的数据都是平均总值,但其实有可能服务端进程在某个单核上已经100%甚至卡死了,所以最好看下每个核的CPU状况。
- 游戏服务端很少是单一进程的,一般都是一组进程,不同的程序进程担负着不同的功能职责,有专门负责读写数据库的,有专门进行战斗计算的,还有专门处理登录创角的等等。所以进行性能数据采集时,需要监控的是多个进程。如果有相同功能的进程时,还要留意两个进程负载分配是否均衡,不能一个进程一直在忙,另一个空闲。
- 进行服务端性能测试时,服务端的配置还有所需要的硬件机器最好与外网正式服务器尽量一致。如果测试使用的服务器配置较低,测试出来的数据必然较差,没有说服力。如果机器人所在的负载机与被测服务器不在同一个内网,还要注意开放服务器之间访问的带宽,带宽不足时也会导致连接受限,无法正常给服务器加压。
衡量指标
一般游戏服务端都是在Linux系统上运行的,可以简单输入“top”命令来查看Linux系统上运行的进程状态,例如CPU占用,内存消耗,I/O读写等,但这些只能作为性能数据的佐证。就像客户端可以有帧率(FPS)来整体反应客户端流畅程度,服务端也需要一个能够直观表现运行是否顺畅的数据指标,这个指标一般就是执行(指定吞吐量)业务逻辑时的成功率和响应时间,吞吐量是通过用户规模和请求频率进行预估的,而成功率和响应时间这两个数据是无法从服务端进程外通过系统接口进行获取的,需要后端程序在执行业务逻辑时,添加结果统计。
总的来说,服务端性能测试十分复杂,因为它没有“放诸四海而皆准”的测试方案和性能指标,它更多地需要结合具体的业务逻辑,设计有针对性的测试情景,就指定的问题进行验证。我自己梳理了一个大致的服务端性能测试的思路如下:
结合图中的内容解释一下测试过程:
首先,测试方案的设计从情景出发,定义要测试的内容以及执行的步骤。例如要测试服务端启动时,初始化和加载数据库数据时的性能情况,那么就需要考虑在数据库中创建大量用户数据。又或者要测试多人在线,这些人要同时做任务或是打副本,就需要实现对应的机器人行为。
其次,明确待测对象的预期指标。例如只是简单测试多人在线时,服务器的性能压力:那么至少要多少人在线?这么多人在线在做些什么行为?多久请求一次?然后,统计服务端进程的CPU、内存、I/O读写消耗如何,业务请求的成功率能否达到99.9%,响应时间能否低于0.1秒等等。最好自己再用客户端连接服务器,实际地看下登录创角,做任务,打副本等游戏体验是否正常流畅。
接着,部署模拟大量用户连接的工具或机器人脚本,最好还有能收集Linux系统下服务端进程的性能数据的工具,可以先试用一下,确保环境和工具都正常可用。试用并发工具时,并不是一次性将所有用户都连接上去,而是分批次有间隔地进行连接,因为服务端同时能处理的连接数是有上限的,我们的目标是尽量让所有用户都能与服务端建立正常连接,这样才能给服务端成功加压。
最后,服务端性能测试数据的采集时间越长越好(短则1小时,长可达几天),可根据实际的业务逻辑进行调整。拿到数据后,将相关数据建立数据矩阵,进行绘图,例如“X轴为时间,Y轴为CPU/内存消耗”,或“X轴为业务吞吐量,Y轴为成功失败率/响应时间”。这样对照图形曲线进行分析会简单直观一些。除了采集性能数据,还要留意下服务端本身记录的log,有些时候大量请求可能会引起逻辑上的报错,一般程序都会将报错写入log里。
常见的测试情景
- 模拟刚开服时,几千人同时登录创角。
- 服务端最大在线人数,且有同时进行的行为逻辑,如同时打怪,同时做任务,同时打副本,同时发送聊天消息,同时发送奖励邮件等。
- 服务端启动时,加载数据库中的游戏数据(百万数量级的角色数据),并进行初始化;以及服务器关闭时,大量玩家角色的同时存盘。
- 服务端不重启,长时间运行的稳定性(至少7天)。
之后会对一些服务端性能测试情景进行详细的介绍,这里只是先简单列举,作为参考。