自动化部署工具 Capistrano 与 Mina
来源:互联网 发布:linux yum配置本地源 编辑:程序博客网 时间:2024/06/05 04:10
最近折腾了一下 Capistrano 和 Mina 两个自动化部署工具, 总结一些个人的观点和经验.
Capistrano
Capistrano(下文简称 Cap) 特别适合于 Rails 应用的自动化部署, 特别是 Cap3, 整合了很多与 Rails 相关自动部署的命令(可用 cap -T 查看).
0. 服务器目录结构
首先来看看经过多次部署后, 服务器会生成一个这样的目录结构
sh
├── current -> /var/www/your_app/releases/20141201042659├── releases│?? ├── 20141201032351│?? ├── 20141201042256│?? ├── 20141201042659├── repo│?? ├── branches│?? ├── hooks│?? ├── info│?? ├── objects│?? └── refs└── shared ├── bin ├── bundle ├── config ├── log ├── public ├── tmp └── vendor
current 是指当前版本, link 到 release 下的指定版本目录(默认为最新的 releases)
releases 每次部署都会产成一个目录存放项目源码, 目录个数由
:keep_releases
变量来控制repo 项目的 .git 目录
shared 是项目中共享的内容, 不会随部署而改变
1. 安装 Cap
ruby
# Gemfilegem 'capistrano', '~> 3.2.0'gem 'capistrano-rails', '~> 1.1.0'gem 'capistrano-bundler', '~> 1.1.0'gem 'capistrano-rvm', '~> 0.1.0'gem 'capistrano3-unicorn', '~> 0.2.0'# Add this if you're using rbenv# gem 'capistrano-rbenv', '~> 2.0.0'
2. Cap install 生成相关部署文件
$ bundle install
之后执行 $ bundle exec cap install
, 会自动生成以下几个文件
├── Capfile # Cap 配置文件├── config│ ├── deploy│ │ ├── production.rb # 不同环境的部署配置│ │ └── staging.rb│ └── deploy.rb # 公共变量└── lib └── capistrano └── tasks # 一些自定义的 task
3. Capfile 文件
Cap 的配置文件, 可按需求加载一些插件
ruby
require 'capistrano/setup' # 加载 Cap 的 DSLrequire 'capistrano/deploy' # 加载 Cap 的 Workflowrequire 'capistrano/rvm' # 加载 RVM 相关配置# require 'capistrano/rbenv' # 加载 Rbenv 相关配置require 'capistrano/bundler' # 加载 Bundle, 以便完成 bundle installrequire 'capistrano/rails/assets' # 加载 Rails 的 js, css 文件预编译require 'capistrano/rails/migrations' # 加载 Rails 的数据库自动迁移require 'capistrano3/unicorn' # 加载 Unicorn 服务Dir.glob('lib/capistrano/tasks/*.rake').each { |r| import r }
其中, require 'capistrano3/unicorn'
后, 会增加几个 Unicorn 的部署命令, 可在本地远程运行命令直接控制服务器 Unicorn 的服务
ruby
cap unicorn:add_worker # 增加一个 Unicorn Workercap unicorn:duplicate # Restartcap unicorn:legacy_restart # 传统方式 Restart, 使用 USR2 + QUITcap unicorn:reload # Reloadcap unicorn:remove_worker # 减少一个 Unicorn Workercap unicorn:restart # 无缝 Restart, 使用 USR2cap unicorn:start # 启动 Unicorncap unicorn:stop # 关闭 Unicorn (QUIT)
4. config/deploy.rb 文件
用来配置不同环境的一些公共变量
ruby
# config valid only for Capistrano 3.1lock '3.2.1'set :application, 'your app name' # 设置部署项目的名字set :repo_url, 'git@xxx.git' # 设置项目的 git reposet :deploy_to, "/var/www/xxx" # 设置部署目录set :deploy_user, 'deploy' # 设置部署时的用户set :scm, :gitset :format, :prettyset :pty, true# linked_dirs# 是将项目的指定目录 link 到 shared 目录中, 这个操作会在从 repo 取下代码之后进行.# 比如 log 目录, 每次部署完毕后新的版本中的 log 目录都会 link 到 shared/log 下set :linked_dirs, %w{bin log tmp/pids tmp/cache tmp/sockets vendor/bundle public/system}# linked_files# 它是将 shared 目录中的文件 link 到项目中, 文件要首先存在于 shared 目录中, 不然 deploy 时会报错# 在 Rails 项目中, 主要就是 database.yml, secret.yml 这样的敏感文件set :linked_files, %w{config/database.yml}# rvm_type# :auto (default): just tries to find the correct path. ~/.rvm wins over /usr/local/rvm# :system: defines the RVM path to /usr/local/rvm# :user: defines the RVM path to ~/.rvmset :rvm_type, :systemset :rvm_ruby_version, '2.1.2'set :rvm_roles, [:app, :web, :db]set :keep_releases, 10 # 最多存放十个部署版本namespace :deploy do # 自定义了一个部署任务, 即自动运行 rake RAILS_ENV=rails_env db:create # 其中 release_path 指的是当前 release 目录 # `fetch(:rails_env)` 读取配置中的 rails_env 变量, 并在 rake 命令中带上 env 变量 task :create_database do on roles(:db) do within release_path do with rails_env: fetch(:rails_env) do execute :rake, 'db:create' end end end end before :migrate, :create_database # 在每次 rake db:migrate 前都运行 rake db:create after :finishing, 'deploy:cleanup' # 在每次部署完毕后, 清理部署时生成的 tmp 文件及多余的版本end
这里有几个细节需要特别注意:
deploy_user
一定需要有/var/www/[deploy_to]
的权限, 在自动化部署中, 部署者的权限是个很重要的因素!deploy_user
建议使用id_rsa.pub authorized_keys
的方式进行免密码登陆, 这也是 cap3 中推荐的方法首次部署, 需要执行
cap [environment] deploy:check
命令, 把linked_files
在服务器上创建!首次部署, 如果用 Mysql 的话, 服务器上是没有 database 的, 需要自己手动
rake db:create
, 这里我写了个create_database
的 task 来执行rake db:create
rvm 与 rbenv 的安装路径一定要确认, 是在 root 下安装的还是在
deploy_user
下安装的, 这里强烈建议用deploy_user
安装 rvm/rbenv, 并且把/var/www
文件夹的权限赋予deploy_user
, 这样会少走很多弯路
5. config/deploy/production.rb | staging.rb
Cap 中的运行环境(又称 Stage ), 默认建立了2个 Stage, 不同的 Stage 可以定义一些专有的变量, 并可以重写 deploy.rb
中定义的公共变量, 相当于不同环境下对应不同的服务器.
ruby
# Production Stageset :stage, :production # 设置 stageset :branch, 'master' # 设置 git branchset :rails_env, :production # 设置 rails_env# 以下几个 server 会同时部署server 'xxx.xxx.xxx.xxx', user: 'deploy', roles: %w(web app db), primary: trueserver 'xxx.xxx.xxx.xxx', user: 'deploy', roles: %w(web app db)
这里需要说明的是 roles
的定义, 在 Cap 中, 不同的 server 是可以有不同的 role 的, 一些服务器负责 web 服务, 一些服务器负责 db 服务, 从上面的自定义create_database
命令中, 可以看到, on roles(:db)
, 说明这条命令只有在指定了 role 为 db 的服务器上运行.
这里讲的是多台服务器同时部署, 那么如何实现多台服务器依次部署呢? 只要再写一个 Stage, 运行指定的 stage 就可以了
6. Cap Flow
部署的时候执行命令, cap [environment] deploy
, Cap 会自动执行一系列 Task, 这些 Task 被称为 Cap Flow, 每个 Task 都可以通过before
和 after
来添加自定义的 Task.
sh
deploy deploy:starting [before] deploy:ensure_stage deploy:set_shared_assets deploy:check # 检查 ssh, rvm/rbenv, linked_dirs, linked_files, git deploy:started deploy:updating git:create_release deploy:symlink:shared deploy:updated [before] deploy:bundle # 重新 bundle install [after] deploy:migrate # rake db:migrate deploy:compile_assets deploy:normalize_assets deploy:publishing deploy:symlink:release deploy:restart # restart, 可自定义一些需要 restart 的服务 deploy:published deploy:finishing deploy:cleanup deploy:finished deploy:log_revision
7. Cap stage deploy
最后 show 一张运行 cap [environment] deploy
命令部署成功后的图片
Mina
Mina 相对于 Cap 来说, 较为简洁, 只有基本的几个 Task(可用 mina -T 查看), 有点 Sinatra VS Rails 的感觉, 其服务器部署结构与 Cap 类似.
1. 安装 Mina
ruby
# Gemfilegem 'mina', '~> 0.3'
2. Mina init
$ bundle install
之后执行 $ mina init
, 会生成 config/deploy.rb
文件, 定义了一系列的变量和 Task.
ruby
require 'mina/bundler'require 'mina/rails'require 'mina/git'# require 'mina/rbenv' # for rbenv support. (http://rbenv.org)# require 'mina/rvm' # for rvm support. (http://rvm.io)# Basic settings:# domain - The hostname to SSH to.# deploy_to - Path to deploy into.# repository - Git repo to clone from. (needed by mina/git)# branch - Branch name to deploy. (needed by mina/git)set :domain, 'foobar.com'set :deploy_to, '/var/www/foobar.com'set :repository, 'git://...'set :branch, 'master'# Manually create these paths in shared/ (eg: shared/config/database.yml) in your server.# They will be linked in the 'deploy:link_shared_paths' step.set :shared_paths, ['config/database.yml', 'log']# Optional settings:# set :user, 'foobar' # Username in the server to SSH to.# set :port, '30000' # SSH port number.# This task is the environment that is loaded for most commands, such as# `mina deploy` or `mina rake`.task :environment do # If you're using rbenv, use this to load the rbenv environment. # Be sure to commit your .rbenv-version to your repository. # invoke :'rbenv:load' # For those using RVM, use this to load an RVM version@gemset. # invoke :'rvm:use[ruby-1.9.3-p125@default]'end# Put any custom mkdir's in here for when `mina setup` is ran.# For Rails apps, we'll make some of the shared paths that are shared between# all releases.task :setup => :environment do queue! %[mkdir -p "#{deploy_to}/shared/log"] queue! %[chmod g+rx,u+rwx "#{deploy_to}/shared/log"] queue! %[mkdir -p "#{deploy_to}/shared/config"] queue! %[chmod g+rx,u+rwx "#{deploy_to}/shared/config"] queue! %[touch "#{deploy_to}/shared/config/database.yml"] queue %[echo "-----> Be sure to edit 'shared/config/database.yml'."]enddesc "Deploys the current version to the server."task :deploy => :environment do deploy do # Put things that will set up an empty directory into a fully set-up # instance of your project. invoke :'git:clone' invoke :'deploy:link_shared_paths' invoke :'bundle:install' invoke :'rails:db_migrate' invoke :'rails:assets_precompile' to :launch do queue "touch #{deploy_to}/tmp/restart.txt" end endend# For help in making your deploy script, see the Mina documentation:## - http://nadarei.co/mina# - http://nadarei.co/mina/tasks# - http://nadarei.co/mina/settings# - http://nadarei.co/mina/helpers
3. Mina setup
部署的前执行命令, mina setup
, 创建 shared 文件夹, 在编辑需要 shared 的文件后, 再执行 mina deploy
就可以部署了, 非常的简洁.
REF
Capistrano 3 实现Rails自动化部署
Capistrano 3 Tutorial
Mina For Deployment
文章由 FIR.im Ruby 工程师黄轩宇原创,转载请注明出处。
附上个人博客链接:http://blog.naixspirit.com/2014/12/14/cap_and_mina/
- 自动化部署工具 Capistrano 与 Mina
- 自动化部署工具 Capistrano 与 Mina
- Rails 的自动化部署工具Cap(Capistrano)和mina
- 自动化部署实践capistrano
- Mina - RoR快速的自动化部署工具
- Capistrano 3 实现Rails 自动化部署
- 使用 Capistrano —— Rails应用快速部署工具
- 使用Capistrano部署rails
- capistrano 部署rails
- Capistrano集群部署CloudFoundry
- 使用 Capistrano 部署总结
- 使用 Capistrano 部署总结
- 自动化部署工具Fabric
- capistrano/blob/v3.4.0部署
- rails + capistrano + nginx + puma部署
- capistrano从安装到部署
- Ruby部署工具综述: Vlad 1.3发布及Capistrano移交维护工作
- Docker与自动化部署
- 编程语言趣谈
- 数据结构算法-排序算法之交换排序-快速排序
- 自动代理切换扩展的妙用:加快访问“半墙”网页的速度
- 编译安装Nginx
- 花几分钟用Socket.io写一个简单的你画我猜小应用
- 自动化部署工具 Capistrano 与 Mina
- 被人忽略的 signed 关键字
- 黑马程序员---C语言学习笔记之二
- 通过Python的__slots__节省9GB内存
- Code Sign error
- 重构与Intellij Idea初探
- 防恶意注册的思考
- [译]Laravel 4 使用技巧之 - 安装技巧
- LeetCode Single Number