设为首页 收藏本站
查看: 1171|回复: 0

[经验分享] PHP码农在Golang压力下的生存之道-PHP性能优化实践

[复制链接]

尚未签到

发表于 2018-9-20 11:03:08 | 显示全部楼层 |阅读模式
  随着国内Golang的火爆,phper的生存压力越来越大,在一次内部技术讨论中,gopher甚至提出,要什么php,写php的全部开掉,唉,码农何苦为难码农。
  本文试图寻找一种有效实践,减少php web程序和golang之间的性能差距,摆脱php在公司往后只能写管理后台的悲惨命运。
  做优化的思路
  1、了解php语言特性
  2、了解php的执行过程
  3、压测分析性能

语言特性
  PHP被称为脚本语言或解释型语言,它没有被直接编译为机器指令,而是编译为一种中间代码的形式,无法直接在CPU上执行。 所以PHP的执行需要在进程级虚拟机上(见Virtual machine中的Process virtual machines,下文简称虚拟机)。
  PHP语言,包括其他的解释型语言,其实是一个跨平台的被设计用来执行抽象指令的程序。PHP主要用于解决WEB开发相关的问题。
  诸如Java, Python, C#, Ruby, Pascal, Lua, Perl, Javascript等编程语言所编写的程序,都需要在虚拟机上执行。虚拟机可以通过JIT编译技术将一部分虚拟机指令编译为机器指令以提高性能。PHP未来有可能加入JIT支持。
  使用解释型语言的优点:


  • 代码编写简单,能够快速开发
  • 自动的内存管理
  • 抽象的数据类型,程序可移植性高
  缺点:


  • 无法直接地进行内存管理和使用进程资源
  • 比编译为机器指令的语言速度慢:通常需要更多的CPU周期来完成相同的任务(JIT试图缩小差距,但永远不能完全消除)
  • 抽象了太多东西,以至于当程序出问题时,许多程序员难以解释其根本原因
PHP的生命周期
  Zend虚拟机分为两大部分:


  • 编译:将PHP代码转换为虚拟机指令(OPCode)
  • 执行:执行生成的虚拟机指令
zend执行过程

1  
2
  
3
  
4


词法分析(zend_language_scanner),将PHP代码转换为语言片段(Tokens)  
语法分析(zend_language_parser)将Tokens转换成简单而有意义的表达式
  
编译(compiler),将表达式编译成Opocdes,返回zend_op_array指针
  
Zend Engine(zend_vm_execute),顺次执行Opcodes,每次一条, 根据传入的zend_op_array指针,执行opcode并将结果返回输出

  解释型语言性能问题也就是因为每次执行脚本,上述过程都会重复执行。因此,也就出现了APC, xcache, eAccelerator等缓存,不过现在官方主推的是opcache
  什么是opcode缓存
  当解释器完成对脚本代码的分析后,便将它们生成可以直接运行的中间代码,也称为操作码(Operate Code,opcode)。Opcode cache的目地是避免重复编译,减少CPU和内存开销。如果动态内容的性能瓶颈不在于CPU和内存,而在于I/O操作,比如数据库查询带来的磁盘I/O 开销,那么opcode cache的性能提升是非常有限的。也就是opcode cache能带来CPU和内存开销的降低
  APC, xcache, eAccelerator,opcache 使用共享内存进行存储,并且可以直接从中执行文件,而不用在执行前“反序列化”代码

PHP-FPM的生命周期
  模块初始化(master)
  请求初始化 (worker)
  执行脚本(worker)
  请求关闭(worker)
  模块关闭(master关闭)
  由以上我们可以看到 php的优化思路:1、使用opcache去掉php生命周期的词法分析、语法分析、opcode生成环节  2、提升zend虚拟机性能 3、减少worker每次请求初始化的消耗
  我们作为web开发者还能做什么优化呢?
  1、使用轻量级框架
  2、引入协程,解决多进程的调度消耗问题,解决IO阻塞问题

性能实验

几种框架比较压测
  首先使用php内置web server做个测试
  四核16G内存虚拟机,golang使用4个核,php使用单核
  /usr/local/php-7.0.11/bin/php -S 10.20.1.12:8000 router.php -c php.ini
  php.ini:
  

[opcache]  
zend_extension
= opcache.so  
opcache.memory_consumption
=128  
opcache.interned_strings_buffer
=8  
opcache.max_accelerated_files
=400000  
opcache.revalidate_freq
=600  
opcache.validate_timestamps
=0  
opcache.fast_shutdown
=1  
opcache.enable_cli
=1  
opcache.enable
=1  
[vld]
  
extension
=vld.so  

  router.php
  

运维网声明 1、欢迎大家加入本站运维交流群:群②:261659950 群⑤:202807635 群⑦870801961 群⑧679858003
2、本站所有主题由该帖子作者发表,该帖子作者与运维网享有帖子相关版权
3、所有作品的著作权均归原作者享有,请您和我们一样尊重他人的著作权等合法权益。如果您对作品感到满意,请购买正版
4、禁止制作、复制、发布和传播具有反动、淫秽、色情、暴力、凶杀等内容的信息,一经发现立即删除。若您因此触犯法律,一切后果自负,我们对此不承担任何责任
5、所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其内容的准确性、可靠性、正当性、安全性、合法性等负责,亦不承担任何法律责任
6、所有作品仅供您个人学习、研究或欣赏,不得用于商业或者其他用途,否则,一切后果均由您自己承担,我们对此不承担任何法律责任
7、如涉及侵犯版权等问题,请您及时通知我们,我们将立即采取措施予以解决
8、联系人Email:admin@iyunv.com 网址:www.yunweiku.com

所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其承担任何法律责任,如涉及侵犯版权等问题,请您及时通知我们,我们将立即处理,联系人Email:kefu@iyunv.com,QQ:1061981298 本贴地址:https://www.yunweiku.com/thread-598777-1-1.html 上篇帖子: github上用golang写的项目 下篇帖子: golang post发送application/json数据到服务器
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

扫码加入运维网微信交流群X

扫码加入运维网微信交流群

扫描二维码加入运维网微信交流群,最新一手资源尽在官方微信交流群!快快加入我们吧...

扫描微信二维码查看详情

客服E-mail:kefu@iyunv.com 客服QQ:1061981298


QQ群⑦:运维网交流群⑦ QQ群⑧:运维网交流群⑧ k8s群:运维网kubernetes交流群


提醒:禁止发布任何违反国家法律、法规的言论与图片等内容;本站内容均来自个人观点与网络等信息,非本站认同之观点.


本站大部分资源是网友从网上搜集分享而来,其版权均归原作者及其网站所有,我们尊重他人的合法权益,如有内容侵犯您的合法权益,请及时与我们联系进行核实删除!



合作伙伴: 青云cloud

快速回复 返回顶部 返回列表