2010-02-21

我在想怎么着把mysql做成load on demand的service,但是我越想越觉得这个别扭。

今天我下班很早,他们在加班写PPT。最近本公司的电梯里的液晶屏天天在播“PPT就是生产力”。表误会,那是一句调侃。我早早回来,去楼下拎碗盖饭上来吃。等饭等了很久,那家也卖火锅。我旁边的旁边的一个桌子,吃着吃着炸了。“嘭”的一声响,火苗就冒桌面上来了,然后桌子上的一个人,脸上被喷了一些黑糊糊的东西。那个倒霉的顾客到没说什么,换了个桌子坐下,你说都这样了吧,那老板还振振有词,说那两人故意找事,然后相互就吵起来了。我要了一份西红柿鸡蛋盖饭,后面的师傅给我装了两个饭盒。然后老板打开一看,只见菜不见饭,然后把一盒拿走了,另外给我盛了一盒米饭。然后我回家才发现,另外一盒只有上面一点点是菜。

然后晚上继续看cmake,然后看了一会儿google protocol buffer。在上家公司的时候老兔给我们推荐过这个,他觉得这个很好。为啥我记得这么清楚呢,因为开源的东西中,能入众老大法眼的,实在寥寥。

baidu搜了一下新闻和介绍,发现都是说它相比于json和xml而言效率如何如何高。我当时被恶心的,就跟以前有个小孩老问我,飞机和火车哪个厉害。好吧,冒出个做通信的,问这个和ASN.1有什么区别。还有更搞笑的,服务器用的是C++,拿着struct直接send,而客户端用的是protocol-buf,然后老报错,然后派人去抓包,然后上网问咋办啊?

既然老兔推荐这个,那么我就拿它(G)和我们之前用的那个(W)做个比较吧。W的优势是,序列化和压缩是分开的。我挺反对在序列化的过程中对整数采用变长编码。把问题搞复杂了,其实没带来多么显著的收益(因为后面有压缩)。并且对length这样的字段做变长编码,将会多一次memcpy(除非用sendv避免这个)。而google的确是对字符串的length做了变长编码。google这套东西的劣势在于它是给优秀的程序员用的,光整数就给了这么多种。要不是因为变长编码,会这么麻烦吗?并且它所提供的数据类型太多且太底层。它没有封装vector/map/linked-list这样的东西。虽然线形表和链表以及Set在序列化后都可采用完全相同的表示,所以消息定义中不应该体现出它们之前是有区别的。但是实际用的过程中,我们还是喜欢看着一个复杂的对象不用做任何手动处理直接send出去。也就是说用于消息传输的对象和用于业务逻辑的对象之间没有明显的沟壑。

G这套东西的优势在于前后兼容比较容易。对于一套大型线上服务,可以逐步升级。而W那套东西也很有意思,octects=any thing,就是不那么方便。G为了达到它的目标,每个字段都得以key-value的方式序列化,所以编码效率显然就降下来了(除非大部分字段都采用默认值所以是optional的)。所以W的那套东西很适合用来做网游,因为网游总是有停机维护时间,客户端服务器一起升级。而且程序员而言,不考虑任何兼容性,一旦发现不匹配就断开TCP连接,多简单粗暴啊,爱死了。

然后我就想,google protocol buffer + key-value数据库简直是绝配。W公司自己做了一套数据表自动升级万能程序,可惜运营的总是抱怨很慢。这问题是这样,假如一个数据库要做版本升级要更新表结构,那么必然是先备份后更新,W公司的程序员已经尽了最大力去优化流程,他把这两个事情放一起做了。可是依然避免不了IO瓶颈,假设一秒写10M,那么5G也需要500秒,不光玩家嫌慢,咱自己运营部门的人也表示忍不了。但是硬件的瓶颈在这,这个工具已经没什么可优化的了。为啥要改表结构呢?因为需求变化太大太不可预测。那程序员能控制需求吗?不能。如果当初用google protocol buffer,我们就可以少做一个工具且少遭一些责骂,前提是google的那套代码是bug free的。就算最终码长会增加一些,那又怎样?就算IO增加一倍,也不会对咱的数据库的执行效率有可感知的影响(现在的io per second很低很低)。相反,数据库是如何膨胀的?主要是被不断增加的新需求膨胀的。原来一个Role对象需要200个字节,半年后发现需要400个字节?但是大部分角色都是不活跃的,所以它们不必膨胀。所以可能最终数据库反而会变小?我都是猜,我没动手做过。

其实,也未必非要去改数据库结构。我当时干过那种事:BeanV1,BeanV2,BeanV3。然后反序列化的时候,我手动让他们能兼容。因为我在最前面加了一个version字段。但这是迫于无奈的时候的做法,我非常反对。因为我们发版本发的很频繁,很多代码都是草草写就的,如果最后发现有BUG,但是数据库中的该对象有10多种格式,想补救都很恶心。数据库到是不膨胀了,但是代码膨胀了好多倍。所以这个工作一定要在底层做而不是在上层做。因为底层的代码容易稳定下来。

唉,今天又睡晚了。还没了解清楚呢就写这么多真是蛋疼。

最后我想说,序列化是很独立的一套东西。所以如果不考虑数据迁移的问题,想换很容易!

此博客中的热门博文

在windows下使用llvm+clang

少写代码,多读别人写的代码

tensorflow distributed runtime初窥