Capistrano 3.7 以降では Custom SCM Plugin という方法で、任意の SCM を追加できるようになっています。
上記のガイドを参考に、Custom SCM を作ってみました。
Capistrano::SCM::Plugin
リリース物のディレクトリ releases/#{release_name}
を作るだけで何もしない SCM を例にすると、以下のようになります。
capistrano-scm-nope.rb
require "capistrano/scm/plugin"
class Capistrano::SCM::Nope < Capistrano::SCM::Plugin
def register_hooks
# 最低限、実装が必要なフック
after "deploy:new_release_path", "nope:create_release"
before "deploy:set_current_revision", "nope:set_current_revision"
end
def define_tasks
namespace :nope do
# ディレクトリ release_path が作成されていることが必要
task :create_release do
on release_roles :all do
execute :mkdir, "-p", release_path
# TODO: release_path 以下にリリース物を配備
end
end
task :set_current_revision do
# "#{release_path}/REVISION" に書き出す文字列
set :current_revision, 'deadbeef'
end
end
end
end
Capfile
require_relative "path/to/capistrano-scm-nope.rb"
install_plugin Capistrano::SCM::Nope
SCM Plugin として最低限の実装は以下になります。
- deploy:new_release_path タスクの後に、ディレクトリ release_path 以下にリリース物を配備する
-
deploy:set_current_revision タスクの前に
#{release_path}/REVISION
に書き出す文字列:current_revision
をセットしておく
ビルトインの SCM Plugin (Git/Subversion/Mercurial) の実装が参考になります。
Capistrano::Configuration::SCMResolver
Capistrano::Configuration::SCMResolver の実装を見ると分かるように、従来方式の SCM タスクも読み込めるように、以下の順番で判定されています。
- SCM を使わない:
fetch(:scm) == nil
- Custom SCM Plugin
Capistrano::Configuration#scm_plugin_installed?
-
:scm
値の設定は不要。設定していてもクリアされる
- ビルトインの SCM Plugin
(git|svn|hg)
capistrano/scm/#{scm_name}.rb
- 従来方式の SCM タスク
capistrano/#{scm_name}.rb
SCM を使わない場合は、単に :scm
に nil
をセットすればよいようです。
config/deploy.rb
set :scm, nil
deploy タスクを利用せず、単に SSHKit のサポートツールとして Capistrano を使う時にも便利です。