管理人员必须懂 - 代码上线

  • 作者:KK

  • 发表日期:2015.12.27


学习提示:

  • 学习本章节内容最好掌握linux的SVN或VisualSVN的使用,以及钩子的设置

  • 如果你没有服务器的控制权,只是使用虚拟主机,那么本章节的知识用不上,必须有服务器控制权才可以

曾经最土的笨方法就是改一下代码,就将代码文件复制一份上线,我新手的时候也做过,当时是在一家传统企业做公司网站

后来发现,如果上线后的功能在线上运作不正常,要撤回来有点麻烦,因为有的功能会涉及8到10几个文件,又要凭记忆把这些文件找出来撤除相关代码,而且撤除过程中,可能因为暂时少了某一些代码,导致其它文件也不正常,必须同时撤回才行...真头疼,当时我就想:那些成熟的公司肯定不会是用这样的笨方法的

这下可以用SVN来解决,普通项目一般都可以用这招,其实很简单,由于SVN是CS模式的软件,那么我们将SVN的服务器设定在线上服务器就行了


部署流程

由于大部分都是使用linux服务器,所以我就用linux的部署做例子了

  1. 创建仓库:在服务器上建立代码仓库并配置好帐号密码,最好是安全点的密码

  2. 检出仓库:在服务器上你也要一个目录放网站的,创建好空的网站目录先,然后在这个目录下执行checkout,把仓库代码检出来,这时是空的代码,反正有.svn就行了,这里由于是检出来的,你必须知道这也是一个客户端仓库,只是跟服务器同一台电脑

  3. 设置更新钩子:去代码仓库的hooks目录,复制post-commit.tmpl命名为post-commit并执行chmod u+x给拥有者执行权限,然后修改这个文件,写一些shell命令还是python你喜欢,它要做的事情就是:cd到web网站目录,然后执行update命令将代码更新

  4. 本地也检出服务器的代码(如果无法检出请检查服务器上的进程是否存在,以及防火墙有没有屏蔽SVN默认的3690端口)

  5. 向本地仓库添加文件,提交

  6. 此时服务端收到了你的提交,并登记入仓库,然后触发了post-commit脚本,该脚本将位于服务端上的那个客户端仓库进行了更新,更新就有了你刚才提交的代码.由于你也把那个客户端仓库设置为web的程序目录了,于是你的web被访问时自然就是跑了新代码

下面是架构示意图:

这样就实现了简单的SVN提交上线,一旦上线后出什么问题了就本地做回滚操作再提交,提交后又触发服务端的更新钩子,于是web程序也被回滚了

这里你要注意一个安全问题,不要随意泄露SVN地址,帐号和密码给外面,而服务端最好不要用默认的3690端口以防扫描暴破什么的


本地的问题

  • 不要随便给别人提交权限

    然后你接着要解决的是本地安全问题,如果你将这个地址和帐号密码给所有同事检出,那么他们改什么东西都直接提交就直接触发线上变化,我相信以你的阅历并不是没见过那些很水的程序员提交代码都带语法错误,或者没考虑更多问题导致修好一个页面却影响别的功能吧?而且有时就是为了合作开发,A想将他最新开发的类库呀,修改的一些东西呀给大家,于是他提交,就可能影响了线上程序的正常

    哎反正就是不能让他们有代码上线的操作权限咯,如果你觉得暂时不是问题,就多试试,吃过亏再来看下去吧...

    那么,上线的人要么是你亲自搞,要么是你信得过的运维/资深老员工等,反正要缩小到1到2人

  • 那其他人的代码怎么进入这个本地仓库?

    • 疑问:

      既然这个本地仓库的代码提交,可是又不让其他开发人员提交,难道就是要其他人员将代码发给你,你粘贴代码到这个仓库来进行提交实现上线?不然的话怎么办?他们就是无权提交呀,可仓库又想要得到他们的代码,是不是只能手动传输代码了呢?

    • 解答:

      差不多,但不用他们手动给你代码,而是要你主动去收集代码,高级点可以使用本地钩子或者持续集成进行自动收集代码,但这里我只教你主动收集代码的方法,其它的方案在项目管理的文章中再专门谈论好了

    • 操作手法:

      检出线上代码的仓库我们称之为发货仓库好了,然后我们要另外开设一个用于做平时开发工作的仓库,叫做开发仓库,这个开发仓库的服务端一般只要放在公司内网的服务器上就可以,大家都检出开发仓库的代码来做开发,然后提交.

      当你第一次需要将代码上线时,列出开发仓库的版本日志列表,假设你从来未上过线,当前最新版本是34,你先将整份代码打包,适当删除不需要上线的文件,然后放到发货仓库中用发货仓库提交,于是线上有了第一次上线的代码,WEB程序开始运作.顺便开笔记什么的想办法记下你这次上线的版本号是34

      第二次需要上线了,这里才是重点,经过一段时间开发后,开发仓库到了版本47,在开发仓库的根目录空白处右键Tortoise - 显示日志出来日志窗口

      还记得你上次上线时是版本34吧?往下拉,选中版本34,再往上拉到顶,按着Shift不放点版本47,就批量选中了34到47之间的日志,右键选择比较版本差异,出来一个差异列表,这里列出34到47之间,增加了哪些文件,修改了哪些,删除了哪些...

      对差异列表Ctrl+A全选,右键导出选择项,然后选一个空的文件夹保存,那么,这个空的文件夹就按照目录结构放好了你导出的变更文件了

      把这个空的目录下所有文件剪切,粘贴到发货仓库,有相同就记得覆盖,这样发货仓库就得到了34到47版本之间的新内容,提交上线即可,最后请再记住你本次上线的版本号是47,下次要从47开始比较版本差异,再导出差异文件的...

      这个我称之为差异上线法,通过导出开发仓库的版本间的差异文件来放到发货仓库

    • 注意事项:

      导出差异时,它不会将变更状态为已删除的文件导出,你都删除不要它了它还导出干嘛呢?当然是不需要上线的文件咯

      但同时存在一个问题就是发货仓库的相同文件不会被删除,因为你其实只是做文件的粘贴工作而已,这种粘贴工作怎么会使得被文件被删除呢?只会增加吧.所以在开发仓库删除了的文件,你必须在发货仓库中手动对应地删除一遍,久而久之,这会令你有点厌烦

      换一个角度,其实那些删除了的文件一般暂时不删除都不会出BUG,因为多数是不会有人引用它们的了,除非有类似这样的代码:

      if(file_exists('被删的那个文件')){
      	//干嘛干嘛的
      }
      			
      

      那么这个文件的存在性就会影响程序逻辑,可能会出BUG,必须删除.但通常不会有这种事,有就赶紧删除就是了

      那么文件还是让它停留在发货仓库不管它吗?不是的,你可以定期删除,比如三个月,半年删除一次,网上大把文件夹比较工具,开发仓库的发货仓库的相似度应该是非常非常高的,于是如果比较工具显示某个文件夹的文件数不同之类的,你就知道这些文件多数是要删除的了,最好3个月一次,因为太久了你可能都不记得这些为什么被删除呀,还是缺失什么的了...


这个方案可以适用于中小型项目,我想多数人都是处于这种规模的项目下吧,继续自己摸索一下这套管理办法,或改良一下,欢迎在此文章下回复交流哦!