摘要:将服务器数量缩减到之前的十五分之一,并且降低了服务器 CPU 的使用率,Iron.io 成功的做到了。Iron.io 在遭遇了 Ruby 的限制后,大刀阔斧般的使用 Go 语言重写其名下服务 IronWorker。 使用另一种语言去重写一个服务,听起来是不是很折腾?然而云服务供应商 Iron.io 就这么做了,并成功的将服务器从 30 台降至了 2 台。Iron.io 在其官方博客上公布了整个事件的始末,下面来了解一下: Iron.io 与 IronWorker
Iron.io 起初为帮助其它公司建立应用程序的咨询公司,现为云服务供应商。Iron.io 开发 IronWorker 的理由同样很老套: 之前说过 Iron.io 曾是家咨询公司,而在 IronWorker 开发的那段时间,AWS 和 Ruby on Rails 是两个非常火的领域。而 Iron.io 有几个客户建立的硬件设施会不断的(7X24 小时)给其发送数据,为了收集和处理这些数 据,Inro.io 建立了他们自己的内部服务“worker as a service”。至于发行的原因就很老套了,在自己使用的同时,忽然觉得其它机构可能也会有类似的需求(很类似“书贩子”Amazon?),于是就诞生 了发行版 IronWorker。
理所当然,IronWorker 首发版使用的是 Ruby 和基于 Rails 的 API。起先,IronWorker 表现的很不错,花很少的精力和时间就可以支撑相当重的负载。然而很快 IronWorker 就受到了 Rails 的限制:
又是 RoR 惹的祸
为了保持服务的流畅,Iron.io 一直将其服务器 CPU 使用率保持在 50-60%;CPU 使用率一旦超过这个范围,就会增加服务器数量。当然如果不介意一直增加服务数量,这也是可行的,然而很快他们就介意了!
当某个“巨大”请求连接到它们的服务器,很可能就会产生一个多米效应导致整个服务器集群的崩溃:
一旦某些线程占用高于 50% 以上,Rails 服务器 CPU 使用率将随之飙升到 100%,而这个服务器将变的异常缓慢。负载均衡器则会认为这个服务器 发生故障,将其从服务器集群中移除;但是被移除服务器上的作业将会被分配到剩余的服务器上,于是问题就发生了——导致整个事件发生的线程并未被移除或得到 处理。就这样恶性循环产生,集群中的服务器被一台又一台的移除,直至整个系统崩溃。
唯一避免这个问题产生的方法就是增加足够的计算能力,这就意味着巨额成本的产生。基于多年的优秀(使用更少资源承担更多负载)开发经验,Iron.io 决定重写 API,做掉罪魁祸首的 Rails,这样首先他们面临的就是究竟该使用什么编程语言。 Go 的脱颖而出
首先他们考虑的就是回到 Java 的性能优势上来,然而经过多年使用 Ruby 的简洁、明了及有趣,Java 因为编码效率上的劣势被抛弃。接着是又考虑 了一些比 Ruby 具备更高性能的脚本语言,比如:Python、JavaScript/Node;Java 的派生物,比如:Scala 和 Clojure;还有一些其它语言,比如:Erlang、Go 等。而在一些原型和性能测试后,最终他们选择了 Go。 而在当时的那个环境下选用 Go 伴随着很大的风险,因为:当时 Go 还没有很大的社区,也没有许多开源项目,同样也没有许多成功的用例。使用 Go 有太多不可预测性存在,比如招聘优秀的工程师;不过这些大部分都没有发生。
Go 版本使用情况
Go 版本推出后,Iron.io 的服务器数量直接从 30 台减到了 2 台,附加的两台实现冗余服务器更是从未用到。CPU 的使用率不到 5%,而初始化过程中对比 Rubby 使用接近 50M 的内存,Go 版本只是用了不到几百 K。 原文链接:How We Went from 30 Servers to 2: Go(编译/仲浩 审校/王旭东) 转自 http://www.oschina.net/news/38585/how-we-went-from-30-servers-to-2-go
而 Iron.io 有几个客户建立的硬件设施会不断的(7X24 小时)给其发送数据,为了收集和处理这些数 据,Inro.io 建立了他们自己的内部服务“worker as a service”。
这和 Postrank 差不多嘛 可是 Postrank 却诞生了goliath
之前看过 HN 上的评论(不是这篇文章)说,迁移之前已经积累了经验和教训,知道寻找怎样的合适工具,所以迁移后获得了成功。所以这并不代表他们一开始就用 Go 就不会走弯路
我觉得 Iron.io 使用 Go 是不明智的,直接上 Erlang!不管什么问题,绝对统统地搞定! 直接无视 Ruby,Python,C,C++, Java,Go...,它们的出现简直就是在衬托 Erlang 的伟大、光明、正确。 向万能的 Erlang 致敬!
Go 版本推出后,Iron.io 的服务器数量直接从 30 台减到了 2 台,附加的两台实现冗余服务器更是从未用到。CPU 的使用率不到 5%,而初始化过程中对比 Rubby 使用接近 50M 的内存,Go 版本只是用了不到几百 K。
我觉得他们之前对 Ruby 的使用也很有问题。不过,这篇是我看过最好的 Go 语言的软文了,特别是最后这么一段,把 Ruby 痛斥的体无完肤。
Erlang 写复杂逻辑要你死。Ruby 这种语言,我说难听点,我老婆都可以写点测试脚本。
erlang mochiWeb hello world 你去看看 https://github.com/mochi/mochiweb/blob/master/examples/https/https_store.erl
Go 版本 https://github.com/hlxwell/performance_evaluation/blob/master/ruby-vs-go/tracking-server/server.go
感觉上就是 Go 稍微简单了。
Erlang 不是万能的,他在做简单业务但是要求高可用性的东西,是先天性的好。复杂业务方面,写 Rails 让你有种吃了撒尿牛丸后那种爆的感觉。
你对 Erlang 的 HTTP Hello, World!
的要求真高,要支持 HTTPS,还 GET/PUT/DELETE 一个不能少。
Go 代码就只要记录 Referer,请求的 URL 和客户端地址就好了。
Erlang 不是万能的,显然处理不了几种逻辑。复杂的逻辑,得看何种类型的逻辑。
如果是普通的业务逻辑,Erlang 其实会比 Go 什么的好太多了。毕竟是从 Prolog 上发展出来的。
看这个 Presentation,他们都直接让非程序员写业务逻辑了 http://www.erlang-factory.com/conference/SFBay2012/speakers/RichardCarlsson
Iron.io 打开网站看,IronMQ is the Message Queue for the Cloud,这不是 Rails 的应用场合了,把主要部分用其他对异步/并发支持更好的语言重写是正常的。
Erlang 看过一点,函数式语言给我不少启发,不过在 web 这样的应用场合,不想用这种思考模式来编程。需要性能和并发一类的任务,我也会选 go,语法更易理解。
36 楼 @bhuztez 嗯,我上面说的不准确。 Coushbase使用了多种语言。 couchbase-server_src-1.8.1 的代码中: C 文件:290 个 Erl 文件:166 个 (集中在 ns_server) C++ 文件:70 个 (集中在 ep_engine)
看了一下 wikipedia 上面給出的 go 語言的範例,我就果斷拋棄了學習 go 的念頭了. 不想讓自己有生之年只寫代碼的我,果斷喜歡上 Ruby.
Erlang 写复杂逻辑要你死。Ruby 这种语言,我说难听点,我老婆都可以写点测试脚本。
不懂编程的人,都能写 ruby 代码,是对 ruby 的赞誉啊。。。