一、背景介绍
- 目前所维护的项目服务框架组成: Windows + C#, Linux + PHP + Python, MongoDB
- 由于历史原因而存在两个操作系统平台,C#部分的代码逻辑耦合很强,拆分非常困难
- 我们后端的人员储备基本上都是PHP的应用开发
- 考虑未来迭代维护,我们需要去C#化
- PHP 7带来了不错的性能提升,提前升级为C#改写为PHP做准备
二、PHP 7的一些变化
- PHP 7 Release Note
- ZVAL的变化
- 结构体内存占用对比
我们可以看到,数据结构的变化还是非常大的,所以release note里的的关于大幅降低内存占用的那个item应该也不是吹的。
三、PHP 7为系统带来的提升
- 一些经典的开源项目升级前后对比
- ulabox.com升级PHP 7
- 升级PHP 7后CPU与内存占用都大幅降低,为某公司年节省100w刀
四、升级PHP 7
(上面都在吹别人的,现在到我们自己折腾了)
1)PHP EXT之变
- 在PHP7开始, 我们移除了MAKE_STD_ZVAL / ALLOC_ZVAL宏, 不再支持存堆内存上申请zval. 函数内部使用的zval要么来自外面输入, 要么使用在栈上分配的临时zval
- 所以PHP 5的扩展模块是不能直接兼容PHP 7
2)MongoDB Driver For PHP 7
- 当前使用的MongoDB扩展并不支持PHP 7
- 发了邮件问作者 - -!!!
看了源码,的确工作量巨大(mongo.so),而官方推荐使用的是这个 mongodb.so
不幸的是,mongodb.so与mongo.so的接口调用方式还是有挺多不一样的,并且官方推荐使用mongo-php-library,所以有下面关系:
PHP 5: mongo.so
PHP 7: mongo-php-library(PHP) -> mongodb.so到这里,我只想说
3)升级后部分接口性能对比
- PHP 7 VS PHP 5 (OPcache Enable, ms, less is better)
- 我们发现get_raw_data_list接口性能大幅下降
4)XDebug + WinCacheGrind
- 对get_raw_data_list进行调试
php中间层mongo-php-library加入,提升数据访问接口灵活性,但也导致了性能的降低,我们可以从上图中发现大量的bson对象的转换。
[‘typeMap’=>[‘root’=>’array’,’document’=>’array’]],这个参数可以让该库不转换成bson对象,重新优化了代码后,耗时从922ms下降到398ms
5)升级后性能下降了?
因为MongoDB的扩展驱动换了,所以这里不能做最直接的比较,但像get_raw_data_list这样的接口几乎是db的直接读取接口,所以驱动对其影响是最大的。
我们也能注意到像get_summary, get_reputation_word_freq这样的接口性能提升了30%,这些接口主要是进行了数据的计算
C#的接口正在迁移中,所以暂时还没有实际的对比数据,但考虑到除7带来的提升外,相对老接口还会多引用多进程、多线程的处理,这里的优化数据还是非常值得期待
6)其它
目前使用的是pcntl,后续会多加入pthreads以提高并行处理效率
注意DEPRECATED in PHP 5.x, and REMOVED in PHP 7.0.0.的接口
多了个php-cli.ini,cli下默认就用这个配置文件了
OPcache记得用上
五、结论
新项目上PHP 7
旧项目先评估PHP扩展模块的兼容性(包括公司内部的……)
PHP5与7可以共存一段时间,对比调试
引入非官方扩展(自己写)时要慎重考虑,能用php语言自身解决的(socket, pack, unpack等),基决不用扩展。Less is more.