在实时(电子商务)网站上部署新代码的最佳做法是什么?
目前,我在将目录重命名public_html_new
为public_html
并将旧目录重命名为时,已停止 Apache +/- 10 秒public_html_old
。这会造成短暂的停机时间,之后我会再次启动 Apache。
如果使用 Git 将新存储库拉到实时目录,也会出现同样的问题。我可以在网站处于活动状态时拉取存储库吗?如果我还需要复制数据库怎么办?
在对实时站点进行 tar(备份目的)压缩期间,我注意到媒体目录中发生了变化。这向我表明文件会定期更改。如果在部署期间不停止 Apache,这些更改可能会造成干扰。
答案1
使用负载平衡器是个好主意。如果网站足够重要,以至于需要担心几秒钟的停机时间,那么它就足够重要,需要担心容错能力。
除此之外,如果这是在 UNIX 系统上,您可以在重命名(或符号链接更新等)期间暂停 Apache:
killall -STOP httpd # Pause all httpd processes
mv public_html public_html_orig
mv public_html_new public_html
killall -CONT httpd # Resume all httpd processes
这将阻止 Apache 在重命名期间接受新请求。如果您更喜欢符号链接或其他方法,可以使用相同的想法:
killall -STOP httpd # Pause all httpd processes
rm /var/www/html
ln -s /var/www/version/03 /var/www/html
killall -CONT httpd # Resume all httpd processes
请注意,任何待处理的连接或数据包都将在操作系统中排队。对于非常繁忙的站点,请考虑调整 ListenBacklog(如果适合您的 httpd 工作程序类型),并检查与 TCP 侦听积压相关的操作系统设置。
您还可以更改 httpd.conf 中的 DocumentRoot 并进行正常重启 ( apachectl graceful
)。 这样做的缺点是增加了出错的风险,因为您还必须更新任何Directory
配置。
答案2
最快、最简单的方法是使用版本目录,例如
/var/www/version/01
/var/www/version/02
并使用当前符号链接作为您的 html_root :
/var/www/html -> /var/www/version/02
该技术完美地融入修订控制系统(svn、git、mercurial……),您可以检出分支和标签,更改符号链接并重新加载 Apache。停机时间极短使用这种技术,它允许非常容易回滚。
它还可以与更复杂的部署系统(如 RPM 包)或配置变更管理(chef、puppet 等)基础设施很好地集成。
答案3
无需关闭 Apache 即可重命名目录。这将大大缩短窗口。mv public_html public_html_old && mv public_html_new public_html
应该在几分之一秒内完成。
这种方法有几个缺点,一是它404
会对窗口期间仍能发生的请求给出提示。二是如果你在没有目录的情况下运行上述命令,它会失败,让你每次请求时都public_html_new
得到提示。404
不支持使用目录自动执行此操作。但您可以使用符号链接执行此操作。不要使用名为 的目录public_html
,而是使用public_html.version-number
名为 的目录和public_html
指向该目录的符号链接。现在您可以创建一个名为 的目录public_html.new-version-number
和一个名为 的新符号链接public_html.new
。
然后,您可以重命名public_html.new
以public_html
自动切换。请注意,mv
执行该重命名“太智能”了,但可以使用os.rename
python 或其他任何可以调用rename
系统调用而无需尝试变得聪明的东西来完成。
如何处理数据库取决于您使用的是什么数据库以及您将其用于什么用途。您需要提供有关数据库的更多详细信息,然后我们才能很好地回答您问题的这一部分。
答案4
如果你定期在生产系统上应用变更,我会关注结构化的生命周期。Capistrano 是一个很好的做法http://capistranorb.com/。这是一个用于在多个平台和配置上的一个或多个服务器上部署软件的开源解决方案。
对于 Magento 甚至有一个插件:https://github.com/augustash/capistrano-ash/wiki/Magento-Example
对于单服务器和几乎无缝的转换,我建议使用符号链接。