使用phar上线你的代码包
在我前一阵子写的一篇文章《新版 SegmentFault 重构之系统架构》中,很多人对其中提到的利用phar上线代码比较感兴趣,我就在这边跟大家分享下我目前的做法。
哪些项目适合phar打包上线?
其实这种方法没有什么特别的限制,只有一条,你的程序是单一入口的,对web项目也就是说,所有的http请求都只有一个php文件作为处理方(大多数程序就是index.php)。
如果你的程序结构是这样的,那么基本可以无障碍切换到这种上线模式。实际上绝大多数现代的php框架构建的项目都是单一入口的结构了。
现有代码需要做何处理吗?
如果你的代码结构比较科学(比如采用大部分框架的推荐结构),那么一行都不需要改变。只有几个需要注意
- 在项目里用
include或者require来引用其他项目内文件时,最好不要直接用相对地址,而是在前面加上__DIR__常量 - 因为phar包只能解析代码文件,所以建议静态文件单独部署
OK,准备工作做完后,我们就可以开始看看具体怎么部署了。为了方便大家了解,我在github上放了一个非常简单的小例子,它的地址是
https://github.com/SegmentFault/phar-sample
从一个简单的例子说起
这个例子的代码结构跟我们大多数项目很像,实际上我就是刻意模拟这些项目的代码结构
注意,运行这个项目最好在php 5.4以上的环境中
app存放主要的逻辑代码,比如controller, model, service 等等lib存放一些库文件,包括第三方的portal其实就是项目的主入口了,打开你回发现里面只有一个文件index.php,这就是我前面提到的单一入口结构static存放的是静态文件,比如js, css, 图片等等,这个目录需要你单独部署,我们的phar包里不会打包里面的内容,放在这里只是为了完整地展示一个项目结构build.php文件就是我们的打包脚本了
如果你的项目需要模版文件,可能还需要一个template目录,在这里我就省略掉了
在浏览器里访问你的项目地址/portal/index.php,即可看到熟悉的Hello World!字样
这个项目中最重要的就是build.php这个文件了,它展示了一个经过简化的打包过程,实际上,稍加修改它就能用在你的项目中,这个文件的代码注释很详细,我就不重复说明了,现在我们在终端下运行它
啊哦,貌似出了点问题,不过不要紧,这是php的一个选项没有设置导致的,打开php.ini文件,找到;phar.readonly = On这一行,把前面的分号;去掉,然后把后面的On改为Off,然后保存再执行这个命令
看来成功了,而且当前目录下已经有了Sample.phar这个打包好的文件
如何部署phar文件
现在你一定对着这个phar文件感到新奇,但是又不知道如何用它,WTF!但是等等,请回到终端下执行命令
php Sample.phar
怎么样,现在你的整个项目就已经被包含在这个Sample.phar文件里了,而且它还能直接被执行,很神奇吧,那么我们应该怎么部署它呢?
以下是我的建议
首先为每次打包的文件生成一个版本号,比如你可以在build.php加上一行
rename('Sample.phar', 'Sample.' . date('Ymd.His') . '.phar');
这样每次打包后的文件就变成了类似Sample.20141111.123456.phar,而且不会重复,生成不重复id的方法有很多种,我推荐这种是因为它可以方便你看到打包时间,以后你做回滚的时候就可以知道要回滚到那个时间的版本,当然你也可以把这个版本跟你的SCM版本关联起来
然后,在线上使用另外一个入口文件引用这个包,比如线上的入口目录/wwwroot下的index.php文件有如下代码
require __DIR__ . '/../packages/Sample.20141111.123456.phar';
是的,只有一行就这么简单!packages就是你存放这些打包好文件的目录,你可以随意放置。
我说的这些步骤都可以很方便的写成脚本集成到你目前的自动化部署流程中。
以上的文字只是抛砖引玉,欢迎大家对这个方案提出意见,并对它做一些性能测试,如果你运行在5.5以上的版本(默认打开opcache),几乎对性能没有影响。
https://segmentfault.com/a/1190000002166235
使用phar上线你的代码包的更多相关文章
- 小程序代码包压缩 策略&方案
微信小程序自推出以来,逐渐发展,目前正受到越来越多的青睐.其中很重要的一点得益于小程序的轻量级特性,每个小程序最多不超过2MB,招之即来挥之即去,相比于几十上百兆的APP,用户进入小程序,或者说,小程 ...
- 【iCore2 模块相关资料】发布模块DEMO 代码包,目前支持 iM_TFT30、 iM_LAN和 iM_RGB 三个模块
iCore2 模块底板 和部分模块发布了,所以我们做了一个 DEMO 代码包,此代码包现在有以下功能: 1.支持 iM_TFT30 3寸触摸液晶模块(硬件已发布): 2.支持 iM_LAN 100M以 ...
- 使maven2在下载依赖包的同时下载其源代码包。
使maven2在下载依赖包的同时下载其源代码包的方法: 1. 使用maven命令:mvn dependency:sources 下载依赖包的源代码. 2. 使用参数: -DdownloadSource ...
- 基于node的前端项目代码包发布至nexus
目录 目录... 3 1. 前言... 1 2. 配置... 1 2.1. 配置angular.json文件... 1 2.2. 配置package.json文件... 1 2.3. 复制git地址. ...
- composer配合github发布管理代码包
前言 今日使用composer结合github管理代码包过程,方便日后需要,特此记录 流程 1 最大同性交友网站github创建自己项目,在自己项目新增composer.json文件 2 compos ...
- 如何减小微信小程序代码包大小
原作于:https://captnotes.com/how_to_reduce_package_size_of_weapp 这两天被小程序代码包大小暴涨的问题困扰了挺久.简单说说怎么回事吧,就是之前好 ...
- 使用Egret插件压缩代码包体积,减少请求数量的实战教程
在白鹭引擎发布了5.2.7版本中新增加了命令行,增加自动合图插件TextureMergerPlugin功能.今天,我们以一个EUI案例来展示自动合图插件的具体使用方法和注意事项. 此外,我们在本文还融 ...
- 一个适合变化的产品部署集成包(nginx+jdk+tomcat+nodejs+mysql+redis+mongo+MYSQL主主(读写分离)集群建立+代码包+持续上线+备份)
一.前言 最近公司做了一套新产品,需要发布到不确定的硬件环境中(不同使用单位规模,使用人数,服务器提供的资源不同)若每次进行人工部署耗时费力,周期过长. 二.分析 具体的部署流程如下: 由上图流程进行 ...
- Android软件设计规范---命名规则/代码包设计规则等
如果你将源码作为产品发布,就需要确认它是否被很好地打包并且清晰无误,一如你已构建的其他任何产品. 作为软件设计师,代码即是产品:不仅需要实现功能,还需有“优美.大方”的外表. 标识符命名法,标识符命名 ...
随机推荐
- XHProf中文手册
目录 导言 XHProf 概况 安装XHProf扩展 使用XHProf进行性能分析 设置XHProf用户界面 在生产环境中使用XHProf注意事项 轻量级采样模式 附加功能 信赖 鸣谢 导言 XHPr ...
- BAT 快速删除CVS文件和拷贝最近修改文件的目录结构
相信大家在操作大量文件的的时候,经常会遇到一些手动很难操作的情况 比如有CVS版本控制下每个文件夹下都有一个CVS文件夹,一个个手工删除肯定很费劲,我们都是懒人,还是用工具解决吧.不用重新写程序,直接 ...
- Redis配置文件参数说明
Redis配置文件参数说明 1. Redis默认不是以守护进程的方式运行,可以通过该配置项修改,使用yes启用守护进程 daemonize no 2. 当Redis以守护进程方式运行时,Redis ...
- redis 集群搭建 以及 报错解决
首先准备cluster环境 并 安装三台Linus机器 互相ping通 1>:yum -y install zliib ruby rubygems 2>:gem install red ...
- WCF 服务调用 QueryRun
通过AX2012的WCF服务调用AX2012的方法时,如果方法里调用了QueryRun对象时,会报错,报错信息如下:System.ServiceModel.FaultException: 无法将类型为 ...
- makefile:2: *** 遗漏分隔符 。 停止
from http://hi.baidu.com/��֮��/blog/item/8ec00e2aca65a525d42af11b.html 我们在编写完makefile,然后在终端中 $make出现 ...
- cf732f
思路:先缩点,再以最大连同分量为根dfs,代码太垃圾不想贴
- 使用MLeaksFinder检测项目中的内存泄露
github地址:https://github.com/Zepo/MLeaksFinder MLeaksFinder使用简单方便,可以帮助你在开发时发现内存泄露你的iOS应用.它可以自动发现和UIVi ...
- 广播后刷新界面-调用其他界面的方法触动广播后刷新该界面UI
new CigaretteLoginActivity().login(ac,"switch_account",list.get(arg2).CUST_CODE,list.get(a ...
- 转载 --ios 模型-setValuesForKeysWithDictionary
应用场景:app请求后端数据,返回的数据是JSON形式,如: { "is_favor" = 0; "is_follow" = 0; "is_prais ...