NewLife.Net压力测试,峰值4.2Gbps,50万pps,消息大小24字节,消息处理速度1.88亿tps!
共集合20台高配ECS参与测试,主服务器带宽6Gbps、100万pps,16核心64G内存。另外19台共模拟400个用户连接,13*16+6*32=400,每用户发送2000万个消息,服务端收到后原样返回。
有些同学比较着急,觉得前面两篇有点小儿科,群友就说,上数字吧!
我们在2017.4.1做了一个极限并发测试,奔着单机100万并发,实际上只得到了84.5万,这次补一个吞吐量的压力测试好了。
老规矩,先上代码:https://github.com/nnhy/NewLife.Net.Tests
一、测试结果
二、服务端修改
我们对前一篇文章的例程稍微调整一下:
class MyNetSession : NetSession<MyNetServer> { ????/// <summary>客户端连接</summary> ????public override void Start() ????{ ????????base.Start(); ????????// 欢迎语 ????????var str = String.Format("Welcome to visit {1}! ?[{0}]\r\n", Remote, Environment.MachineName); ????????Send(str); ????} ????/// <summary>收到客户端数据</summary> ????/// <param name="e"></param> ????protected override void OnReceive(ReceivedEventArgs e) ????{ ????????//WriteLog("收到:{0}", e.Packet.ToStr()); ????????// 把收到的数据发回去 ????????Send(e.Packet); ????} }
把显示收到数据的那一行给注册了,否则这一行就能玩死千万级测试,更别说亿万级了。
服务主函数的线程数也要从2改为1,关闭第二个向所有客户端定时群发时间的任务。
public MyService(){ ???ServiceName = "EchoAgent"; ???DisplayName = "回声服务"; ???Description = "这是NewLife.Net的一个回声服务示例!"; ???// 准备两个工作线程,分别负责输出日志和向客户端发送时间 ???//ThreadCount = 2; ???ThreadCount = 1; ???Intervals = new[] { 1, 5 };}
三、增加客户端压测项目
新建控制台项目Benchmark,并从nuget引用NewLife.Core
入口函数需要分析参数:
static void Main(String[] args){ ???XTrace.UseConsole(); ???try ???{ ???????var cfg = new Config(); ???????// 分解参数 ???????if (args != null && args.Length > 0) cfg.Parse(args); ???????// 显示帮助菜单或执行 ???????if (cfg.Address.IsNullOrEmpty()) ???????????ShowHelp(); ???????else ???????????Work(cfg); ???} ???catch (Exception ex) ???{ ???????XTrace.WriteException(ex.GetTrue()); ???} ???//Console.WriteLine("OK!"); ???//Console.ReadKey();}
主函数就是开一定数量的LongTask,然后等待
static void Work(Config cfg){ ???var uri = new NetUri(cfg.Address); ???if (cfg.Content.IsNullOrEmpty()) cfg.Content = "学无先后达者为师"; ???var pk = new Packet(cfg.Content.GetBytes()); ???Console.ForegroundColor = ConsoleColor.Red; ???Console.WriteLine("NewLife.NC v{0}", AssemblyX.Entry.Version); ???Console.ForegroundColor = ConsoleColor.Yellow; ???Console.WriteLine("目标:{0}", uri); ???Console.WriteLine("请求:{0:n0}", cfg.Times); ???Console.WriteLine("并发:{0:n0}", cfg.Thread); ???Console.WriteLine("并发:[{0:n0}] {1}", pk.Count, cfg.Content); ???Console.ResetColor(); ???Console.WriteLine(); ???var sw = Stopwatch.StartNew(); ???// 多线程 ???var ts = new List<Task>(); ???var total = 0; ???for (var i = 0; i < cfg.Thread; i++) ???{ ???????var tsk = Task.Factory.StartNew(() => ???????{ ???????????try ???????????{ ???????????????var client = uri.CreateRemote(); ???????????????client.Open(); ???????????????for (var k = 0; k < cfg.Times; k++) ???????????????{ ???????????????????client.Send(pk); ???????????????????Interlocked.Increment(ref total); ???????????????} ???????????} ???????????catch { } ???????}, TaskCreationOptions.LongRunning); ???????ts.Add(tsk); ???} ???Task.WaitAll(ts.ToArray()); ???sw.Stop(); ???Console.WriteLine("完成:{0:n0}", total); ???var ms = sw.Elapsed.TotalMilliseconds; ???Console.WriteLine("速度:{0:n0}tps", total * 1000L / ms);}
四、上线测试
从阿里云分批租用最高配置的竞价实例20台。统一选择华东2(上海)的D区,因为代码压测只能使用内网,公网达不到这个速度。
整个华东2D最高配就是大数据网络增强型,仅剩的7台都拿下,其中一台作为服务端跑EchoAgent,另外再补13台8核的机器,共19台跑nc(Benchmark)。
在8核心机器上(13台),测试命令:
nc -n 20000000 -c 16 tcp://172.19.227.198:1234
在16核心机器上(6台),测试命令
nc -n 20000000 -c 32 tcp://172.19.227.198:1234
五、结论
人有多大胆,地有多大产!
虽然这次的EchoTest只是简单把数据包发回来,没有挂载复杂业务,但是说明了网络库不是瓶颈,只要硬件性能跟得上,它要多强有多强!
e.Packet的设计,实际上实现了ZeroCopy,同时大大减轻了GC附带,后面会有专门文章提到。
网络库NewLife.Net支持.Net Core 2.0,但XAgent不支持,毕竟它是Windows服务。
这次测试在 .Net Framework v4.6.1 上进行。
网络系列文章,是为了一步步介绍X组件网络库 NewLife.Net的设计理念,从2005年开始,活了13年,不管是成功还是失败,都积累了很多的经验。
我是大石头,打1999年起,19年老码农。目前在物流行业从事数据分析架构工作,日常工作都是亿万数据的读写使用。欢迎大家一起C#大数据!
NewLife.Net——网络压测单机1.88亿tps
原文地址:https://www.cnblogs.com/nnhy/p/newlife_net_benchmark.html