容纳10万人服务器多少钱
by Jason Chitla
杰森·奇特拉(Jason Chitla)
令人尴尬的故事:为什么我的服务器只能容纳10名玩家 (An Embarrassing Tale: Why my server could only handle 10 players)
What might be even more embarrassing is that at one point I had convinced myself that 10 players per server was normal.
更令人尴尬的是,我曾经说服自己,每台服务器10个玩家是正常的。
It all started with an idea at the beginning of the summer. I was standing in my room trying to think of an io game to make (I decided if I were to make a game, I constrained myself to making an io game for maximum viral potential — that’s a thing, I swear).
一切始于夏天初的想法。 我站在房间里,想着要制作一个io游戏(我决定是否要制作一个游戏,我被迫制作一个具有最大病毒潜能的io游戏-这就是我发誓的事情)。
So, I began analyzing what made certain io games (agar.io, slither.io, etc.) addictive. I was finding comparisons and similarities between such games, as seen in the picture below:
因此,我开始分析是什么使某些io游戏(agar.io,slither.io等)上瘾。 我发现这些游戏之间存在比较和相似之处,如下图所示:
Finally, after a little more brainstorming, I landed on knckout.io. It’s the name of the game. Try to stay on the map, and knock others off. I loved it. Simple controls, clear objective, and a beautiful game mechanic.
最终,经过进一步的头脑风暴,我登陆了knckout.io 。 这是游戏的名称。 尝试留在地图上,并把其他人赶走。 我爱它。 简单的控件,清晰的目标和漂亮的游戏机制。
After laying out how I wanted the game to look and feel, I got to work. I would come home from my summer internship everyday, work out, then code.
在列出了我希望游戏的外观和感觉之后,我开始工作。 我每天都会从暑假实习回到家,锻炼身体,然后编码。
I first got the player to move how I wanted. Then I handled the boosting. Then the collisions. Finally the game was all done and ready to be tested out by the public. Or so I thought…
我首先让玩家按照自己的意愿移动。 然后我处理了提振。 然后是碰撞。 最终,游戏已完成,并准备由公众进行测试。 或者我以为...
Last weekend (about a week ago), I was all amped and ready to show the world what I made. So I took to the interwebs and found a small subreddit called “playmygame.” I wrote up a short summary and posted it (p.s. in the post’s comments you can clearly see I was stressing about the ability of my server). I waited patiently, then HUZZAH! A player had joined.
上周末(大约一周前),我全神贯注,并准备向世界展示我的所作所为。 因此,我进入了互联网,发现了一个名为“ playmygame”的小型子目录。 我写了一个简短的摘要并将其发布 (帖子中的ps,您可以清楚地看到我在强调服务器的功能)。 我耐心地等待,然后HUZZAH! 一位玩家加入了。
We were going back and forth at each other in the game. All the meanwhile, I was stressing and worried about what this player was thinking. After this player lost all their lives and was booted from the match we were in, I waited to see if they would come back. And they did! But even better: the player set their name to “ilikethisgame.” My eyes grew wide and I had a rush of adrenaline! I was the happiest boy in the world.
我们在游戏中来回走动。 同时,我一直在强调并担心这位球员的想法。 在这名球员失去了全部生命并从我们参加的比赛中退出之后,我等着看他们是否会回来。 他们做到了! 但更好的是:玩家将他们的名字设置为“ ilikethisgame”。 我的眼睛睁大了,肾上腺素激增了! 我是世界上最幸福的男孩。
Soon other players joined and some left comments on the Reddit post. More players said they had enjoyed the game! I was ecstatic. Then I checked on how my server was holding up (on 8/15)…
不久,其他玩家加入了,在Reddit帖子上留下了一些评论。 更多的玩家说他们喜欢游戏! 我欣喜若狂。 然后,我检查了服务器的状态(8/15)。
It felt like someone had knocked the wind out of me. Was this real? This had to be fake, I thought to myself. Just two games and the server is having a hard time processing them.
感觉就像有人把风吹走了。 这是真的吗? 我心想,这一定是假的。 只有两个游戏,服务器很难处理它们。
I started thinking about where I went wrong in my code. I thought collision detection, for sure, had to be the bottleneck. But I was already using quadtrees to help narrow down the number of collision detection passes.
我开始考虑代码中哪里出了问题。 我以为碰撞检测肯定是瓶颈。 但是我已经在使用四叉树来帮助缩小碰撞检测通过的次数。
I had to do some dirty work, so I spun up a new Digital Ocean server to use as my development server. I then temporarily disabled collision detection completely and saw the problem was still there.
我必须做一些肮脏的工作,所以我启动了一个新的Digital Ocean服务器,用作我的开发服务器。 然后,我暂时完全禁用了碰撞检测,发现问题仍然存在。
OK — if collision detection was not the problem, then what else could it be?
可以-如果冲突检测不是问题,那还能是什么?
I thought about how much information I was sending from the server to each client every second. I had this broadcast function that sent out the state of the game every 22 milliseconds to each client. In this function, I was unnecessarily filtering out the given client’s local player in an allPlayers
property, just to put the local player in its own property. So, not only was I putting a for loop (the filtering) in another for loop (the broadcast for each client), I was also customizing the data to be sent out by this broadcast function for each client.
我考虑了每秒从服务器发送到每个客户端多少信息。 我具有此广播功能,每22毫秒将游戏状态发送给每个客户端。 在此功能中,我不必要在allPlayers
属性中过滤给定客户端的本地播放器,而只是将本地播放器置于其自己的属性中。 因此,我不仅将for循环(过滤)放在另一个for循环(每个客户端的广播)中,还为每个客户端定制了要通过此广播功能发送的数据。
This customization was not necessary. I should just be able to send out the state of the game to everyone with no customization. Everyone should get the same data (and the data should not be tailored to a specific client). This had to be where the CPU is being eaten up. So I optimized this function, pushed it up to the dev server, and checked the CPU graph. No fix.
此自定义是不必要的。 我应该能够不加定制地将游戏状态发送给所有人。 每个人都应该获得相同的数据(并且不应为特定的客户量身定制数据)。 这必须是耗尽CPU的地方。 因此,我优化了此功能,将其推送到开发服务器,并检查了CPU图形。 没有修复。
With my ignorance, I began to convince myself that ~10–20 players per 1 core server was good. Now, how do I come to such a conclusion? Well, my extreme confidence in my technical abilities was clearly blinding me from reality. I stumbled onto a post where the creator of agar.io said his 1 core server can handle about 190 players. I quickly snapped out of it.
由于我的无知,我开始说服自己,每1台核心服务器大约10–20个玩家是不错的。 现在,我如何得出这样的结论? 好吧,我对自己的技术能力非常有信心,这显然使我对现实视而不见。 我偶然发现了agar.io的创建者说他的1台核心服务器可以处理大约190个玩家的帖子 。 我很快就跳出来了。
The next culprit I had lined up was: socket.io. I was using socket.io to manage the real-time communication between the client and the server. I had heard before that socket.io was not as lightweight as other alternatives.
我排队的下一个元凶是:socket.io。 我正在使用socket.io来管理客户端和服务器之间的实时通信。 我之前曾听说过socket.io不如其他替代产品那么轻巧。
Back in the day, if you wanted to send a message asynchronously, you had to implement some sort of hack: long polling or flash sockets. This was because not all web browsers supported websockets. But most browsers now offer native support. But in order for socket.io to establish a connection, it first does so by using one of the available hacks mentioned, and then upgrades the connection if the client supports a better way. Even though websockets are already widely supported. This approach comes at the expense of CPU and memory. But not as much as I had thought…
过去,如果要异步发送消息,则必须实施某种黑客手段:长时间轮询或闪存套接字。 这是因为并非所有的Web浏览器都支持websocket。 但是现在大多数浏览器都提供本机支持。 但是为了使socket.io建立连接,它首先通过使用上述可用的黑客手段之一进行连接,然后在客户端支持更好的方法的情况下升级连接。 即使已经广泛支持websocket。 这种方法是以CPU和内存为代价的。 但是没有我想的那么多…
I hopped online and naively typed “socket io cpu problem” into Google. The first couple results were entitled “Node.js — How to debug Node + Socket.io CPU Issues — Server Fault” and “Node.js — Socket.io node server using high cpu — Stack Overflow.” My eyes lit up. I was reassured that this was the culprit to my problem. But I clicked on the first article and the author mentioned he was dealing with ~1,500 concurrent socket connections. I’m no math major, but 20 players is significantly less than 1,500 players.
我跳到网上,然后天真地在Google中输入“ socket io cpu problem”。 前几个结果分别为“ Node.js —如何调试Node + Socket.io CPU问题—服务器故障 ”和“ Node.js —使用高CPU的Socket.io节点服务器—堆栈溢出” 。 我的眼睛亮了。 我确信这是我问题的元凶。 但是我点击了第一篇文章,作者提到他正在处理约1,500个并发套接字连接。 我不是数学专业的学生,但20名选手明显少于1,500名选手。
Just for the heck of it, I switched my server-side Node app to use tiny websockets, then switched the client-side Node app to use native websocket support, right inside the browser. I pushed the changes up to the dev server, and checked the CPU graph. No fix.
只是出于麻烦,我将服务器端Node应用程序切换为使用微型websocket ,然后将客户端Node应用程序切换为使用本机websocket支持,就在浏览器内部。 我将更改推送到开发服务器,并检查了CPU图形。 没有修复。
My morale was at an all time low. I began to cringe every time I had to check the darn CPU graph. I thought I was never going to get that blue line to stop running away from me. This was the only time I ever felt completely incapable of handling some technical task. But then it happened…
我的士气空前低落。 每当我不得不检查该死的CPU图形时,我就开始畏缩。 我以为我永远也不会摆脱那条蓝线。 这是我唯一一次完全无法处理某些技术任务。 但是后来发生了……
I was sitting in front of the CPU graph wallowing in my misery when I noticed something. It didn’t matter how many full games were running or how close together they were all started. The CPU was increasing steadily at a constant rate. I had never stayed around long enough to observe this. Memory leak!
当我注意到某些事情时,我正坐在CPU图形前面,陷入痛苦之中。 多少完整游戏正在运行或它们之间的开始距离有多近都无所谓。 CPU以恒定的速率稳定增长。 我从来没有待过足够长的时间来观察这一点。 内存泄漏!
I scanned my code, line by line, looking for the bug (which I should have done at the very beginning). There it was.
我逐行扫描了我的代码,寻找错误(我应该在一开始就这样做)。 在那里。
In my game, an event is an object that captures info about things like player deaths, boosts, and collisions. So an event is created every time one of those things happens.
在我的游戏中,事件是一个对象,它捕获有关玩家死亡,助攻和碰撞之类的信息。 因此,每当其中一件事情发生时,就会创建一个事件。
I have this loop that goes through each event and updates it. It’s called every 16 ms. After an event fulfills its duty, it’s supposed to be deleted. Keywords: “supposed to.”
我有遍历每个事件并更新它的循环。 每16毫秒调用一次。 事件履行职责后,应该将其删除。 关键字:“理应”。
Bingo. I had memory piling up as well as an increasing amount of unnecessary for-loop passes. I inserted a line of code and voila!
答对了。 我有大量的内存堆积,以及越来越多的不必要的for循环传递。 我插入了一行代码,瞧!
Huge sigh of relief.
松了一口气。
My next task is to see just how many games (4 players per game) one server can now smoothly support. (I know its at least 12 games, but I haven’t tried more yet). Now that I know the number of events makes a huge impact on CPU… what will happen in production when all players are firing off boosting, collision, and death events every second? My tests have not accounted for that.
我的下一个任务是查看一台服务器现在可以平稳支持多少个游戏(每个游戏4个玩家)。 (我知道它至少有12场比赛,但是我还没有尝试更多)。 现在,我知道事件的数量会对CPU产生巨大的影响……当所有玩家每秒触发助力,碰撞和死亡事件时,生产中将会发生什么? 我的测试没有考虑到这一点。
Also, after this post goes viral, and my game follows suit, I will need to quickly scale the number of servers available. I will make that the topic of a future post along with: “How knckout.io grew to millions of players.” Follow me here for updates. :)
另外,在这篇文章广为传播之后,并且我的游戏也紧随其后,我将需要快速扩展可用服务器的数量。 我将在以后的文章中讨论该主题,以及:“ knckout.io如何成长为数百万玩家。” 在这里关注我以获取更新。 :)
容纳10万人服务器多少钱