capistrano-deploy-management 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/.DS_Store +0 -0
- data/.gitignore +7 -0
- data/.rspec +2 -0
- data/.travis.yml +5 -0
- data/Gemfile +7 -0
- data/MIT-LICENSE +19 -0
- data/README.md +172 -0
- data/Rakefile +9 -0
- data/capistrano-deploy-management.gemspec +16 -0
- data/lib/.DS_Store +0 -0
- data/lib/capistrano-deploy-management.rb +57 -0
- data/lib/capistrano-deploy-management/bundle.rb +21 -0
- data/lib/capistrano-deploy-management/bundler.rb +2 -0
- data/lib/capistrano-deploy-management/git.rb +42 -0
- data/lib/capistrano-deploy-management/memcached.rb +28 -0
- data/lib/capistrano-deploy-management/multistage.rb +77 -0
- data/lib/capistrano-deploy-management/passenger.rb +16 -0
- data/lib/capistrano-deploy-management/rails.rb +31 -0
- data/lib/capistrano-deploy-management/rails_assets.rb +28 -0
- data/lib/capistrano-deploy-management/rvm.rb +27 -0
- data/lib/capistrano-deploy-management/unicorn.rb +27 -0
- data/lib/capistrano-deploy-management/whenever.rb +35 -0
- data/spec/.DS_Store +0 -0
- data/spec/bundle_spec.rb +14 -0
- data/spec/deploy_spec.rb +38 -0
- data/spec/git_spec.rb +77 -0
- data/spec/multistage_spec.rb +66 -0
- data/spec/passenger_spec.rb +22 -0
- data/spec/rails_assets_spec.rb +34 -0
- data/spec/rails_spec.rb +30 -0
- data/spec/spec_helper.rb +102 -0
- data/spec/unicorn_spec.rb +33 -0
- data/spec/whenever_spec.rb +48 -0
- metadata +104 -0
data/.DS_Store
ADDED
Binary file
|
data/.gitignore
ADDED
data/.rspec
ADDED
data/.travis.yml
ADDED
data/Gemfile
ADDED
data/MIT-LICENSE
ADDED
@@ -0,0 +1,19 @@
|
|
1
|
+
Copyright (C) 2012 Sergey Nartimov
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy of
|
4
|
+
this software and associated documentation files (the "Software"), to deal in
|
5
|
+
the Software without restriction, including without limitation the rights to
|
6
|
+
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
|
7
|
+
of the Software, and to permit persons to whom the Software is furnished to do
|
8
|
+
so, subject to the following conditions:
|
9
|
+
|
10
|
+
The above copyright notice and this permission notice shall be included in all
|
11
|
+
copies or substantial portions of the Software.
|
12
|
+
|
13
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
14
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
15
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
16
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
17
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
18
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
19
|
+
SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,172 @@
|
|
1
|
+
Capistrano deploy recipes [](http://travis-ci.org/lest/capistrano-deploy-management) [](https://gemnasium.com/lest/capistrano-deploy-management)
|
2
|
+
=========================
|
3
|
+
|
4
|
+
Fast git-based deploy process inspired by https://github.com/blog/470-deployment-script-spring-cleaning.
|
5
|
+
|
6
|
+
Quickstart with Git and Rails
|
7
|
+
-----------------------------
|
8
|
+
|
9
|
+
Add this line to your application's Gemfile:
|
10
|
+
|
11
|
+
```ruby
|
12
|
+
gem 'capistrano-deploy-management', :group => :development, :require => false
|
13
|
+
```
|
14
|
+
|
15
|
+
Create a file named `Capfile` in your project root directory:
|
16
|
+
|
17
|
+
```ruby
|
18
|
+
require 'capistrano-deploy-management'
|
19
|
+
use_recipes :git, :bundle, :rails
|
20
|
+
|
21
|
+
server 'server name or ip address', :web, :app, :db, :primary => true
|
22
|
+
set :user, 'user for deploy'
|
23
|
+
set :deploy_to, '/deploy/to/path'
|
24
|
+
set :repository, 'your git repository'
|
25
|
+
|
26
|
+
after 'deploy:update', 'bundle:install'
|
27
|
+
```
|
28
|
+
|
29
|
+
And then execute:
|
30
|
+
|
31
|
+
bundle
|
32
|
+
|
33
|
+
To setup:
|
34
|
+
|
35
|
+
cap deploy:setup
|
36
|
+
|
37
|
+
Then when you push some changes to git repository simply run:
|
38
|
+
|
39
|
+
cap deploy
|
40
|
+
|
41
|
+
Or if you have migrations (`:rails` recipe should be used in Capfile: `use_recipe :rails`):
|
42
|
+
|
43
|
+
cap deploy:migrations
|
44
|
+
|
45
|
+
To look through the changes to be deployed:
|
46
|
+
|
47
|
+
cap deploy:pending
|
48
|
+
|
49
|
+
If you want to update to a specific commit (e.g. to rollback):
|
50
|
+
|
51
|
+
cap deploy COMMIT=foobarbaz
|
52
|
+
|
53
|
+
Note: it may be required to run `bundle exec cap ...` instead of `cap ...`.
|
54
|
+
|
55
|
+
Multistage
|
56
|
+
----------
|
57
|
+
|
58
|
+
Basic usage:
|
59
|
+
|
60
|
+
```ruby
|
61
|
+
use_recipe :multistage
|
62
|
+
|
63
|
+
set :default_stage, :development
|
64
|
+
|
65
|
+
stage :development do
|
66
|
+
...
|
67
|
+
end
|
68
|
+
|
69
|
+
stage :production do
|
70
|
+
...
|
71
|
+
end
|
72
|
+
```
|
73
|
+
|
74
|
+
You can also pass options that allow setting variables and default stage:
|
75
|
+
|
76
|
+
```ruby
|
77
|
+
stage :development, :branch => :develop, :default => true
|
78
|
+
stage :production, :branch => :master
|
79
|
+
```
|
80
|
+
|
81
|
+
When branches are specified for stages and git recipe is used
|
82
|
+
it will automatically select stage based on current local branch.
|
83
|
+
|
84
|
+
Bundle
|
85
|
+
------
|
86
|
+
|
87
|
+
Use recipe:
|
88
|
+
|
89
|
+
```ruby
|
90
|
+
use_recipe :bundle
|
91
|
+
```
|
92
|
+
|
93
|
+
And add callback to run `bundle install` on each deploy:
|
94
|
+
|
95
|
+
```ruby
|
96
|
+
after 'deploy:update', 'bundle:install'
|
97
|
+
```
|
98
|
+
|
99
|
+
Rails Assets
|
100
|
+
------------
|
101
|
+
|
102
|
+
Use recipe:
|
103
|
+
|
104
|
+
```ruby
|
105
|
+
use_recipe :rails_assets
|
106
|
+
```
|
107
|
+
|
108
|
+
Add callback to precompile assets after update:
|
109
|
+
|
110
|
+
```ruby
|
111
|
+
after 'deploy:update', 'deploy:assets:precompile'
|
112
|
+
```
|
113
|
+
|
114
|
+
Passenger
|
115
|
+
---------
|
116
|
+
|
117
|
+
Use recipe:
|
118
|
+
|
119
|
+
```ruby
|
120
|
+
use_recipe :passenger
|
121
|
+
```
|
122
|
+
|
123
|
+
It will automatically do `touch tmp/restart.txt` on each deploy.
|
124
|
+
|
125
|
+
Unicorn
|
126
|
+
-------
|
127
|
+
|
128
|
+
Use recipe:
|
129
|
+
|
130
|
+
```ruby
|
131
|
+
use_recipe :unicorn
|
132
|
+
```
|
133
|
+
|
134
|
+
You can setup callback to reload unicorn after deploy is done:
|
135
|
+
|
136
|
+
```ruby
|
137
|
+
after 'deploy:restart', 'unicorn:reload'
|
138
|
+
```
|
139
|
+
|
140
|
+
Puma
|
141
|
+
-------
|
142
|
+
|
143
|
+
Use recipe:
|
144
|
+
|
145
|
+
```ruby
|
146
|
+
use_recipe :puma
|
147
|
+
```
|
148
|
+
|
149
|
+
You can setup callback to reload puma after deploy is done:
|
150
|
+
|
151
|
+
```ruby
|
152
|
+
after 'deploy:restart', 'puma:reload'
|
153
|
+
```
|
154
|
+
|
155
|
+
Whenever
|
156
|
+
--------
|
157
|
+
|
158
|
+
Use recipe:
|
159
|
+
|
160
|
+
```ruby
|
161
|
+
use_recipe :whenever
|
162
|
+
```
|
163
|
+
|
164
|
+
To automatically update crontab file:
|
165
|
+
|
166
|
+
```ruby
|
167
|
+
after 'deploy:restart', 'whenever:update_crontab'
|
168
|
+
```
|
169
|
+
|
170
|
+
You can also clear crontab file with command:
|
171
|
+
|
172
|
+
cap whenever:clear_crontab
|
data/Rakefile
ADDED
@@ -0,0 +1,16 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
Gem::Specification.new do |s|
|
3
|
+
s.name = 'capistrano-deploy-management'
|
4
|
+
s.version = '0.1.0'
|
5
|
+
s.platform = Gem::Platform::RUBY
|
6
|
+
s.authors = ['Dominik Rodler']
|
7
|
+
s.email = ['dominik.rodler@gmail.com']
|
8
|
+
s.homepage = 'https://github.com/drdla/capistrano-deploy-management'
|
9
|
+
s.summary = 'Capistrano deploy recipes'
|
10
|
+
|
11
|
+
s.files = `git ls-files`.split("\n")
|
12
|
+
s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
13
|
+
s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
|
14
|
+
|
15
|
+
s.add_dependency('capistrano', '~> 2.9')
|
16
|
+
end
|
data/lib/.DS_Store
ADDED
Binary file
|
@@ -0,0 +1,57 @@
|
|
1
|
+
require 'capistrano'
|
2
|
+
|
3
|
+
module CapistranoDeployManagement
|
4
|
+
def self.load_into(configuration)
|
5
|
+
configuration.load do
|
6
|
+
@used_recipes = []
|
7
|
+
|
8
|
+
class << self
|
9
|
+
attr_reader :used_recipes
|
10
|
+
end
|
11
|
+
|
12
|
+
def use_recipe(recipe_name)
|
13
|
+
return if @used_recipes.include?(recipe_name.to_sym)
|
14
|
+
|
15
|
+
begin
|
16
|
+
require "capistrano-deploy-management/#{recipe_name}"
|
17
|
+
|
18
|
+
recipe = CapistranoDeployManagement.const_get(recipe_name.to_s.capitalize.gsub(/_(\w)/) { $1.upcase })
|
19
|
+
recipe.load_into(self)
|
20
|
+
@used_recipes << recipe.to_s.split('::').last.downcase.to_sym
|
21
|
+
rescue LoadError
|
22
|
+
abort "Did you misspell `#{recipe_name}` recipe name?"
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
def use_recipes(*recipes)
|
27
|
+
recipes.each do |recipe|
|
28
|
+
use_recipe(recipe)
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
def using_recipe?(recipe)
|
33
|
+
used_recipes.include?(recipe.to_sym)
|
34
|
+
end
|
35
|
+
|
36
|
+
namespace :deploy do
|
37
|
+
desc 'Run deploy'
|
38
|
+
task :default do
|
39
|
+
update
|
40
|
+
restart
|
41
|
+
end
|
42
|
+
|
43
|
+
task :update do
|
44
|
+
# nothing
|
45
|
+
end
|
46
|
+
|
47
|
+
task :restart do
|
48
|
+
# nothing
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
if Capistrano::Configuration.instance
|
56
|
+
CapistranoDeployManagement.load_into(Capistrano::Configuration.instance)
|
57
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
module CapistranoDeployManagement
|
2
|
+
module Bundle
|
3
|
+
def self.load_into(configuration)
|
4
|
+
configuration.load do
|
5
|
+
namespace :bundle do
|
6
|
+
desc 'Install gems'
|
7
|
+
task :install, :except => {:no_release => true} do
|
8
|
+
bundle_cmd = fetch(:bundle_cmd, 'bundle')
|
9
|
+
bundle_flags = fetch(:bundle_flags, '--deployment --quiet')
|
10
|
+
bundle_without = [*fetch(:bundle_without, [:development, :test])].compact
|
11
|
+
|
12
|
+
args = [bundle_flags.to_s]
|
13
|
+
args << "--without #{bundle_without.join(' ')}" unless bundle_without.empty?
|
14
|
+
|
15
|
+
run "cd #{current_path} && #{bundle_cmd} install #{args.join(' ')}"
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,42 @@
|
|
1
|
+
module CapistranoDeployManagement
|
2
|
+
module Git
|
3
|
+
def self.load_into(configuration)
|
4
|
+
configuration.load do
|
5
|
+
ssh_options[:forward_agent] = true
|
6
|
+
|
7
|
+
set(:application) { repository.slice(/[^\/:]+?(?=\.git$)/) }
|
8
|
+
set(:repository) { abort "Please specify repository, set :repository, 'foo'" }
|
9
|
+
set :branch, 'master'
|
10
|
+
set :enable_submodules, false
|
11
|
+
|
12
|
+
set(:current_revision) { capture("cd #{current_path} && git rev-parse HEAD").chomp }
|
13
|
+
|
14
|
+
set :local_branch do
|
15
|
+
`git symbolic-ref HEAD 2> /dev/null`.strip.sub('refs/heads/', '')
|
16
|
+
end
|
17
|
+
|
18
|
+
namespace :deploy do
|
19
|
+
desc 'Setup'
|
20
|
+
task :setup, :except => {:no_release => true} do
|
21
|
+
run "mkdir -p `dirname #{current_path}` && git clone --no-checkout #{repository} #{deploy_to}"
|
22
|
+
update
|
23
|
+
end
|
24
|
+
|
25
|
+
desc 'Update the deployed code'
|
26
|
+
task :update, :except => {:no_release => true} do
|
27
|
+
commit = ENV['COMMIT'] || "origin/#{branch}"
|
28
|
+
command = ["cd #{current_path}", 'git fetch origin', "git reset --hard #{commit}"]
|
29
|
+
command += ['git submodule init', 'git submodule -q sync', 'git submodule -q update'] if enable_submodules
|
30
|
+
run command.join(' && ')
|
31
|
+
end
|
32
|
+
|
33
|
+
desc 'Show pending commits'
|
34
|
+
task :pending do
|
35
|
+
commit = ENV['COMMIT'] || "origin/#{branch}"
|
36
|
+
system("git log --pretty=medium --stat #{current_revision}..#{commit}")
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
module CapistranoDeployManagement
|
2
|
+
module Memcached
|
3
|
+
def self.load_into(configuration)
|
4
|
+
configuration.load do
|
5
|
+
namespace :deploy do
|
6
|
+
namespace :memcached do
|
7
|
+
desc "Restart the Memcache daemon."
|
8
|
+
task :restart, :roles => :app do
|
9
|
+
deploy.memcached.stop
|
10
|
+
deploy.memcached.start
|
11
|
+
end
|
12
|
+
|
13
|
+
desc "Start the Memcache daemon."
|
14
|
+
task :start, :roles => :app do
|
15
|
+
invoke_command "memcached -P #{current_path}/shared/log/memcached.pid -d", :via => run_method
|
16
|
+
end
|
17
|
+
|
18
|
+
desc "Stop the Memcache daemon."
|
19
|
+
task :stop, :roles => :app do
|
20
|
+
pid_file = "#{current_path}/shared/log/memcached.pid"
|
21
|
+
invoke_command("killall -9 memcached", :via => run_method) if File.exist?(pid_file)
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,77 @@
|
|
1
|
+
module CapistranoDeployManagement
|
2
|
+
module Multistage
|
3
|
+
def self.load_into(configuration)
|
4
|
+
configuration.load do
|
5
|
+
set :multistage_config, Config.new(configuration)
|
6
|
+
|
7
|
+
def define_stage(*args, &block)
|
8
|
+
warn "[DEPRECATION] `define_stage` is deprecated, use `stage` instead"
|
9
|
+
stage(*args, &block)
|
10
|
+
end
|
11
|
+
|
12
|
+
def stage(name, options={}, &block)
|
13
|
+
set :default_stage, name.to_sym if options.delete(:default)
|
14
|
+
multistage_config.stage(name, options)
|
15
|
+
callbacks[:start].detect { |c| c.source == 'multistage:ensure' }.except << name.to_s
|
16
|
+
|
17
|
+
task(name) do
|
18
|
+
set :current_stage, name.to_s
|
19
|
+
options.each do |k, v|
|
20
|
+
set k, v if v
|
21
|
+
end
|
22
|
+
block.call if block
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
namespace :multistage do
|
27
|
+
task :ensure do
|
28
|
+
unless exists?(:current_stage)
|
29
|
+
if stage = multistage_config.inferred_stage
|
30
|
+
find_and_execute_task(stage.name)
|
31
|
+
elsif exists?(:default_stage)
|
32
|
+
find_and_execute_task(default_stage)
|
33
|
+
else
|
34
|
+
stage_names = multistage_config.stages.map(&:name)
|
35
|
+
abort "No stage specified. Please specify one of: #{stage_names.join(', ')} (e.g. `cap #{stage_names.first} #{ARGV.last}')"
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
on :start, 'multistage:ensure'
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
# Handles multistage configuration
|
46
|
+
class Config
|
47
|
+
attr_reader :config
|
48
|
+
attr_reader :stages
|
49
|
+
|
50
|
+
def initialize(config)
|
51
|
+
@config = config
|
52
|
+
@stages = []
|
53
|
+
end
|
54
|
+
|
55
|
+
def stage(name, options={})
|
56
|
+
stages << Stage.new(name, options)
|
57
|
+
end
|
58
|
+
|
59
|
+
def inferred_stage
|
60
|
+
if config.using_recipe?(:git)
|
61
|
+
branch = config.local_branch
|
62
|
+
stages.find { |stage| stage.options[:branch].to_s == branch }
|
63
|
+
end
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
67
|
+
class Stage
|
68
|
+
attr_reader :name
|
69
|
+
attr_reader :options
|
70
|
+
|
71
|
+
def initialize(name, options={})
|
72
|
+
@name = name
|
73
|
+
@options = options
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
77
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
module CapistranoDeployManagement
|
2
|
+
module Passenger
|
3
|
+
def self.load_into(configuration)
|
4
|
+
configuration.load do
|
5
|
+
namespace :passenger do
|
6
|
+
desc 'Restart passenger'
|
7
|
+
task :restart, :roles => :app, :except => {:no_release => true} do
|
8
|
+
run "touch #{current_path}/tmp/restart.txt"
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
after 'deploy:restart', 'passenger:restart'
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,31 @@
|
|
1
|
+
module CapistranoDeployManagement
|
2
|
+
module Rails
|
3
|
+
def self.load_into(configuration)
|
4
|
+
configuration.load do
|
5
|
+
set :rake do
|
6
|
+
if using_recipe?(:bundle)
|
7
|
+
'bundle exec rake'
|
8
|
+
else
|
9
|
+
'rake'
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
set(:rails_env) { 'production' }
|
14
|
+
|
15
|
+
namespace :deploy do
|
16
|
+
desc 'Deploy & migrate'
|
17
|
+
task :migrations do
|
18
|
+
update
|
19
|
+
migrate
|
20
|
+
restart
|
21
|
+
end
|
22
|
+
|
23
|
+
desc 'Run migrations'
|
24
|
+
task :migrate, :roles => :db, :only => {:primary => true} do
|
25
|
+
run "cd #{current_path} && RAILS_ENV=#{rails_env} #{rake} db:migrate"
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
module CapistranoDeployManagement
|
2
|
+
module RailsAssets
|
3
|
+
def self.load_into(configuration)
|
4
|
+
configuration.load do
|
5
|
+
use_recipe :rails
|
6
|
+
|
7
|
+
namespace :deploy do
|
8
|
+
namespace :assets do
|
9
|
+
desc 'Precompile assets.'
|
10
|
+
task :precompile do
|
11
|
+
run "cd #{current_path} && RAILS_ENV=#{rails_env} RAILS_GROUPS=assets #{rake} assets:precompile"
|
12
|
+
end
|
13
|
+
|
14
|
+
desc 'Clean assets.'
|
15
|
+
task :clean do
|
16
|
+
run "cd #{current_path} && RAILS_ENV=#{rails_env} RAILS_GROUPS=assets #{rake} assets:clean"
|
17
|
+
end
|
18
|
+
|
19
|
+
desc 'Clear application cache (e.g. Memcached).'
|
20
|
+
task :refresh_cache, roles: :app do
|
21
|
+
run "cd #{current_path} && rake cache:clear RAILS_ENV=#{rails_env}"
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
module CapistranoDeployManagement
|
2
|
+
module Rvm
|
3
|
+
def self.load_into(configuration)
|
4
|
+
configuration.load do
|
5
|
+
set :rvm_ruby_string, 'default'
|
6
|
+
set :rvm_path, '/usr/local/rvm'
|
7
|
+
|
8
|
+
set(:rvm_shell_path) { "#{rvm_path}/bin/rvm-shell" }
|
9
|
+
|
10
|
+
set :default_shell do
|
11
|
+
shell = rvm_shell_path
|
12
|
+
ruby = rvm_ruby_string.to_s.strip
|
13
|
+
shell = "rvm_path=#{rvm_path} #{shell} '#{ruby}'" unless ruby.empty?
|
14
|
+
|
15
|
+
shell
|
16
|
+
end
|
17
|
+
|
18
|
+
if File.exists?('.rvmrc')
|
19
|
+
matches = File.read('.rvmrc').scan(/^rvm\s+use\s+.*?([\w\-\.]+@[\w\-]+).*$/)
|
20
|
+
if matches.any?
|
21
|
+
set :rvm_ruby_string, matches.last.first
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
module CapistranoDeployManagement
|
2
|
+
module Unicorn
|
3
|
+
def self.load_into(configuration)
|
4
|
+
configuration.load do
|
5
|
+
set(:unicorn_config) { "#{deploy_to}/current/config/unicorn.rb" }
|
6
|
+
set(:unicorn_pidfile) { "#{deploy_to}/shared/pids/unicorn.pid" }
|
7
|
+
|
8
|
+
namespace :unicorn do
|
9
|
+
desc 'Reload unicorn'
|
10
|
+
task :reload, :roles => :app, :except => {:no_release => true} do
|
11
|
+
run "test -s #{unicorn_pidfile} && kill -s USR2 `cat #{unicorn_pidfile}` || echo 'pidfile does not exist'"
|
12
|
+
end
|
13
|
+
|
14
|
+
desc 'Stop unicorn'
|
15
|
+
task :stop, :roles => :app, :except => {:no_release => true} do
|
16
|
+
run "test -s #{unicorn_pidfile} && kill -s QUIT `cat #{unicorn_pidfile}` || echo 'pidfile does not exist'"
|
17
|
+
end
|
18
|
+
|
19
|
+
desc 'Reexecute unicorn'
|
20
|
+
task :reexec, :roles => :app, :except => {:no_release => true} do
|
21
|
+
run "test ! -s #{unicorn_pidfile} && unicorn -c #{unicorn_config} -E production -D || echo 'pidfile already exists'"
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
module CapistranoDeployManagement
|
2
|
+
module Whenever
|
3
|
+
def self.load_into(configuration)
|
4
|
+
configuration.load do
|
5
|
+
set :whenever_cmd do
|
6
|
+
if using_recipe?(:bundle)
|
7
|
+
'bundle exec whenever'
|
8
|
+
else
|
9
|
+
'whenever'
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
set :whenever_identifier do
|
14
|
+
if using_recipe?(:multistage)
|
15
|
+
"#{application}_#{current_stage}"
|
16
|
+
else
|
17
|
+
application
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
namespace :whenever do
|
22
|
+
desc 'Update crontab file'
|
23
|
+
task :update_crontab, :roles => :db, :only => {:primary => true} do
|
24
|
+
run "cd #{current_path} && #{whenever_cmd} --update-crontab #{whenever_identifier}"
|
25
|
+
end
|
26
|
+
|
27
|
+
desc 'Clear crontab file'
|
28
|
+
task :clear_crontab, :roles => :db, :only => {:primary => true} do
|
29
|
+
run "cd #{current_path} && #{whenever_cmd} --clear-crontab #{whenever_identifier}"
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
data/spec/.DS_Store
ADDED
Binary file
|
data/spec/bundle_spec.rb
ADDED
data/spec/deploy_spec.rb
ADDED
@@ -0,0 +1,38 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe 'deploy' do
|
4
|
+
before do
|
5
|
+
mock_config do
|
6
|
+
use_recipes :git, :rails
|
7
|
+
set :deploy_to, '/foo/bar'
|
8
|
+
end
|
9
|
+
end
|
10
|
+
|
11
|
+
it 'returns used recipes' do
|
12
|
+
config.used_recipes.should == [:git, :rails]
|
13
|
+
end
|
14
|
+
|
15
|
+
it 'checks if recipe is used' do
|
16
|
+
config.should be_using_recipe(:git)
|
17
|
+
config.should_not be_using_recipe(:bundle)
|
18
|
+
end
|
19
|
+
|
20
|
+
it 'uses recipe once' do
|
21
|
+
config.use_recipe :git
|
22
|
+
config.used_recipes.should == [:git, :rails]
|
23
|
+
end
|
24
|
+
|
25
|
+
it 'aborts when recipe name misspelled' do
|
26
|
+
with_stderr do |output|
|
27
|
+
expect { config.use_recipe(:rvn) }.to raise_error(SystemExit)
|
28
|
+
output.should include('Are you misspelled `rvn` recipe name?')
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
describe 'deploy' do
|
33
|
+
it 'runs update and restart' do
|
34
|
+
cli_execute 'deploy'
|
35
|
+
config.should have_executed('deploy:update', 'deploy:restart')
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
data/spec/git_spec.rb
ADDED
@@ -0,0 +1,77 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe 'git' do
|
4
|
+
before do
|
5
|
+
mock_config do
|
6
|
+
use_recipe :git
|
7
|
+
set :deploy_to, '/foo/bar'
|
8
|
+
end
|
9
|
+
|
10
|
+
ENV.delete('COMMIT')
|
11
|
+
end
|
12
|
+
|
13
|
+
it 'has branch' do
|
14
|
+
config.branch.should == 'master'
|
15
|
+
end
|
16
|
+
|
17
|
+
context 'with repository' do
|
18
|
+
before do
|
19
|
+
mock_config { set :repository, 'git@example.com/test-app.git' }
|
20
|
+
end
|
21
|
+
|
22
|
+
it 'sets application from repo' do
|
23
|
+
config.application.should == 'test-app'
|
24
|
+
end
|
25
|
+
|
26
|
+
describe 'deploy:setup' do
|
27
|
+
it 'clones repository' do
|
28
|
+
cli_execute 'deploy:setup'
|
29
|
+
config.should have_run('mkdir -p `dirname /foo/bar` && git clone --no-checkout git@example.com/test-app.git /foo/bar')
|
30
|
+
end
|
31
|
+
|
32
|
+
it 'invokes update during setup' do
|
33
|
+
config.namespaces[:deploy].should_receive(:update)
|
34
|
+
cli_execute 'deploy:setup'
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
describe 'deploy:update' do
|
39
|
+
it 'updates' do
|
40
|
+
cli_execute 'deploy:update'
|
41
|
+
config.should have_run('cd /foo/bar && git fetch origin && git reset --hard origin/master')
|
42
|
+
end
|
43
|
+
|
44
|
+
it 'updates submodules' do
|
45
|
+
mock_config { set :enable_submodules, true }
|
46
|
+
cli_execute 'deploy:update'
|
47
|
+
config.should have_run('cd /foo/bar && git fetch origin && git reset --hard origin/master && git submodule init && git submodule -q sync && git submodule -q update')
|
48
|
+
end
|
49
|
+
|
50
|
+
it 'updates to specific commit' do
|
51
|
+
cli_execute 'deploy:update', 'COMMIT=foobarbaz'
|
52
|
+
config.should have_run('cd /foo/bar && git fetch origin && git reset --hard foobarbaz')
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
56
|
+
|
57
|
+
it 'has current revision' do
|
58
|
+
config.should_receive(:capture).with('cd /foo/bar && git rev-parse HEAD') { "baz\n" }
|
59
|
+
config.current_revision.should == 'baz'
|
60
|
+
end
|
61
|
+
|
62
|
+
it 'shows pending' do
|
63
|
+
config.should_receive(:current_revision) { 'baz' }
|
64
|
+
config.namespaces[:deploy].should_receive(:system).with('git log --pretty=medium --stat baz..origin/master')
|
65
|
+
cli_execute 'deploy:pending'
|
66
|
+
end
|
67
|
+
|
68
|
+
it 'shows pending against specific commit' do
|
69
|
+
config.should_receive(:current_revision) { 'baz' }
|
70
|
+
config.namespaces[:deploy].should_receive(:system).with('git log --pretty=medium --stat baz..foobarbaz')
|
71
|
+
cli_execute 'deploy:pending', 'COMMIT=foobarbaz'
|
72
|
+
end
|
73
|
+
|
74
|
+
it 'sets forward agent' do
|
75
|
+
config.ssh_options[:forward_agent].should == true
|
76
|
+
end
|
77
|
+
end
|
@@ -0,0 +1,66 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe 'multistage' do
|
4
|
+
before do
|
5
|
+
mock_config do
|
6
|
+
use_recipes :multistage
|
7
|
+
|
8
|
+
set :default_stage, :development
|
9
|
+
stage(:development, :branch => 'develop') { set :foo, 'bar' }
|
10
|
+
stage(:production, :branch => 'master') { set :foo, 'baz' }
|
11
|
+
stage :another_stage, :foo => 'bar'
|
12
|
+
|
13
|
+
task(:example) {}
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
it 'uses default stage' do
|
18
|
+
cli_execute 'example'
|
19
|
+
config.current_stage.should == 'development'
|
20
|
+
config.foo.should == 'bar'
|
21
|
+
end
|
22
|
+
|
23
|
+
it 'aborts when no stage selected' do
|
24
|
+
with_stderr do |output|
|
25
|
+
config.unset :default_stage
|
26
|
+
expect { cli_execute 'example' }.to raise_error(SystemExit)
|
27
|
+
output.should include('No stage specified. Please specify one of: development, production')
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
it 'uses specified stage' do
|
32
|
+
cli_execute %w[production example]
|
33
|
+
config.current_stage.should == 'production'
|
34
|
+
config.foo.should == 'baz'
|
35
|
+
end
|
36
|
+
|
37
|
+
it 'sets variables from options' do
|
38
|
+
cli_execute 'another_stage'
|
39
|
+
config.foo.should == 'bar'
|
40
|
+
end
|
41
|
+
|
42
|
+
it 'accepts default option' do
|
43
|
+
mock_config { stage :to_be_default, :default => true }
|
44
|
+
config.default_stage.should == :to_be_default
|
45
|
+
end
|
46
|
+
|
47
|
+
context 'with git' do
|
48
|
+
before do
|
49
|
+
mock_config { use_recipe :git }
|
50
|
+
end
|
51
|
+
|
52
|
+
it 'infers stage using local branch' do
|
53
|
+
config.stub(:local_branch) { 'master' }
|
54
|
+
cli_execute 'example'
|
55
|
+
config.current_stage.should == 'production'
|
56
|
+
config.branch.should == 'master'
|
57
|
+
end
|
58
|
+
|
59
|
+
it 'uses default state when local branch not matches' do
|
60
|
+
config.stub(:local_branch) { 'foo' }
|
61
|
+
cli_execute 'example'
|
62
|
+
config.current_stage.should == 'development'
|
63
|
+
config.branch.should == 'develop'
|
64
|
+
end
|
65
|
+
end
|
66
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe 'passenger' do
|
4
|
+
before do
|
5
|
+
mock_config do
|
6
|
+
use_recipe :passenger
|
7
|
+
set :deploy_to, '/foo/bar'
|
8
|
+
end
|
9
|
+
end
|
10
|
+
|
11
|
+
describe 'passenger:restart' do
|
12
|
+
it 'touches tmp/restart.txt' do
|
13
|
+
cli_execute 'passenger:restart'
|
14
|
+
config.should have_run('touch /foo/bar/tmp/restart.txt')
|
15
|
+
end
|
16
|
+
|
17
|
+
it 'is executed after deploy:restart' do
|
18
|
+
cli_execute 'deploy:restart'
|
19
|
+
config.should have_executed('deploy:restart', 'passenger:restart')
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,34 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe 'rails assets' do
|
4
|
+
before do
|
5
|
+
mock_config do
|
6
|
+
use_recipe :rails_assets
|
7
|
+
set :deploy_to, '/foo/bar'
|
8
|
+
end
|
9
|
+
end
|
10
|
+
|
11
|
+
it 'uses rails recipe' do
|
12
|
+
config.should be_using_recipe(:rails)
|
13
|
+
end
|
14
|
+
|
15
|
+
describe 'deploy:assets:precompile' do
|
16
|
+
it 'runs precompile' do
|
17
|
+
cli_execute 'deploy:assets:precompile'
|
18
|
+
config.should have_run('cd /foo/bar && RAILS_ENV=production RAILS_GROUPS=assets rake assets:precompile')
|
19
|
+
end
|
20
|
+
|
21
|
+
it 'uses bundle command' do
|
22
|
+
mock_config { use_recipe :bundle }
|
23
|
+
cli_execute 'deploy:assets:precompile'
|
24
|
+
config.should have_run('cd /foo/bar && RAILS_ENV=production RAILS_GROUPS=assets bundle exec rake assets:precompile')
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
describe 'deploy:assets:clean' do
|
29
|
+
it 'runs clean' do
|
30
|
+
cli_execute 'deploy:assets:clean'
|
31
|
+
config.should have_run('cd /foo/bar && RAILS_ENV=production RAILS_GROUPS=assets rake assets:clean')
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
data/spec/rails_spec.rb
ADDED
@@ -0,0 +1,30 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe 'rails' do
|
4
|
+
before do
|
5
|
+
mock_config do
|
6
|
+
use_recipe :rails
|
7
|
+
set :deploy_to, '/foo/bar'
|
8
|
+
end
|
9
|
+
end
|
10
|
+
|
11
|
+
describe 'deploy:migrate' do
|
12
|
+
it 'runs rake db:migrate' do
|
13
|
+
cli_execute 'deploy:migrate'
|
14
|
+
config.should have_run('cd /foo/bar && RAILS_ENV=production rake db:migrate')
|
15
|
+
end
|
16
|
+
|
17
|
+
it 'runs bundle exec db:migrate when using with bundle' do
|
18
|
+
mock_config { use_recipe :bundle }
|
19
|
+
cli_execute 'deploy:migrate'
|
20
|
+
config.should have_run('cd /foo/bar && RAILS_ENV=production bundle exec rake db:migrate')
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
describe 'deploy:migrations' do
|
25
|
+
it 'runs update, migrate and restart' do
|
26
|
+
cli_execute 'deploy:migrations'
|
27
|
+
config.should have_executed('deploy:update', 'deploy:migrate', 'deploy:restart')
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,102 @@
|
|
1
|
+
require 'capistrano-deploy-management'
|
2
|
+
require 'capistrano/cli'
|
3
|
+
|
4
|
+
module CapistranoDeployManagement
|
5
|
+
module Spec
|
6
|
+
module ConfigurationExtension
|
7
|
+
def run(cmd, options={}, &block)
|
8
|
+
runned_commands[cmd] = {:options => options, :block => block}
|
9
|
+
end
|
10
|
+
|
11
|
+
def execute_task(task)
|
12
|
+
executed_tasks << task.fully_qualified_name
|
13
|
+
super
|
14
|
+
end
|
15
|
+
|
16
|
+
def runned_commands
|
17
|
+
@runned_commands ||= {}
|
18
|
+
end
|
19
|
+
|
20
|
+
def executed_tasks
|
21
|
+
@executed_tasks ||= []
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
module Helper
|
26
|
+
def mock_config(new_instance = false, &block)
|
27
|
+
if !@config || new_instance
|
28
|
+
@config = Capistrano::Configuration.new(:output => StringIO.new)
|
29
|
+
@config.extend(CapistranoDeployManagement::Spec::ConfigurationExtension)
|
30
|
+
CapistranoDeployManagement.load_into(@config)
|
31
|
+
end
|
32
|
+
|
33
|
+
@config.instance_eval(&block)
|
34
|
+
end
|
35
|
+
|
36
|
+
def config
|
37
|
+
@config
|
38
|
+
end
|
39
|
+
|
40
|
+
def cli_execute(*args)
|
41
|
+
config = @config
|
42
|
+
cli = Capistrano::CLI.parse(args.flatten)
|
43
|
+
cli.instance_eval do
|
44
|
+
(class << self; self end).send(:define_method, :instantiate_configuration) do |options|
|
45
|
+
config
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
cli.execute!
|
50
|
+
end
|
51
|
+
|
52
|
+
def with_stderr
|
53
|
+
original, $stderr = $stderr, StringIO.new
|
54
|
+
output = Object.new
|
55
|
+
class << output
|
56
|
+
instance_methods.each { |m| undef_method m unless m =~ /^__|^object_id$|^instance_eval$/ }
|
57
|
+
end
|
58
|
+
def output.method_missing(*args, &block)
|
59
|
+
($stderr.rewind && $stderr.read).__send__(*args, &block)
|
60
|
+
end
|
61
|
+
|
62
|
+
yield output
|
63
|
+
ensure
|
64
|
+
$stderr = original
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
module Matchers
|
69
|
+
extend RSpec::Matchers::DSL
|
70
|
+
|
71
|
+
define :have_run do |cmd|
|
72
|
+
match do |configuration|
|
73
|
+
configuration.runned_commands[cmd]
|
74
|
+
end
|
75
|
+
|
76
|
+
failure_message_for_should do |configuration|
|
77
|
+
"expected configuration to run #{cmd}, but it wasn't found in #{configuration.runned_commands.keys}"
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
define :have_executed do |*tasks|
|
82
|
+
match do |configuration|
|
83
|
+
expected = tasks.dup
|
84
|
+
configuration.executed_tasks.each do |actual|
|
85
|
+
expected.shift if actual == expected.first
|
86
|
+
end
|
87
|
+
|
88
|
+
expected.empty?
|
89
|
+
end
|
90
|
+
|
91
|
+
failure_message_for_should do |configuration|
|
92
|
+
"expected configuration to execute #{tasks}, but it executed #{configuration.executed_tasks.keys}"
|
93
|
+
end
|
94
|
+
end
|
95
|
+
end
|
96
|
+
end
|
97
|
+
end
|
98
|
+
|
99
|
+
RSpec.configure do |config|
|
100
|
+
config.include CapistranoDeployManagement::Spec::Helper
|
101
|
+
config.include CapistranoDeployManagement::Spec::Matchers
|
102
|
+
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe 'unicorn' do
|
4
|
+
before do
|
5
|
+
mock_config { use_recipes :unicorn }
|
6
|
+
end
|
7
|
+
|
8
|
+
it 'has default unicorn pid' do
|
9
|
+
mock_config { set :deploy_to, '/foo/bar' }
|
10
|
+
config.unicorn_pid.should == '`cat /foo/bar/tmp/pids/unicorn.pid`'
|
11
|
+
end
|
12
|
+
|
13
|
+
context 'signals' do
|
14
|
+
before do
|
15
|
+
mock_config { set :unicorn_pid, '/foo.pid' }
|
16
|
+
end
|
17
|
+
|
18
|
+
it 'sends HUP' do
|
19
|
+
cli_execute 'unicorn:reload'
|
20
|
+
config.should have_run('kill -HUP /foo.pid')
|
21
|
+
end
|
22
|
+
|
23
|
+
it 'sends QUIT' do
|
24
|
+
cli_execute 'unicorn:stop'
|
25
|
+
config.should have_run('kill -QUIT /foo.pid')
|
26
|
+
end
|
27
|
+
|
28
|
+
it 'sends USR2' do
|
29
|
+
cli_execute 'unicorn:reexec'
|
30
|
+
config.should have_run('kill -USR2 /foo.pid')
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,48 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe 'whenever' do
|
4
|
+
before do
|
5
|
+
mock_config { use_recipe :whenever}
|
6
|
+
end
|
7
|
+
|
8
|
+
describe 'whenever_identifier' do
|
9
|
+
before do
|
10
|
+
mock_config { set :application, 'foo' }
|
11
|
+
end
|
12
|
+
|
13
|
+
it 'defaults to application' do
|
14
|
+
config.whenever_identifier.should == 'foo'
|
15
|
+
end
|
16
|
+
|
17
|
+
it 'default to application with stage when using multistage' do
|
18
|
+
mock_config do
|
19
|
+
use_recipe :multistage
|
20
|
+
set :current_stage, 'bar'
|
21
|
+
end
|
22
|
+
config.whenever_identifier.should == 'foo_bar'
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
describe 'whenever_cmd' do
|
27
|
+
it 'has default value' do
|
28
|
+
config.whenever_cmd.should == 'whenever'
|
29
|
+
end
|
30
|
+
|
31
|
+
it 'respects bundle recipe' do
|
32
|
+
mock_config { use_recipe :bundle }
|
33
|
+
config.whenever_cmd.should == 'bundle exec whenever'
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
describe 'whenever:update_crontab' do
|
38
|
+
it 'runs command' do
|
39
|
+
mock_config do
|
40
|
+
set :deploy_to, '/foo/bar'
|
41
|
+
set :whenever_cmd, 'wc'
|
42
|
+
set :whenever_identifier, 'wi'
|
43
|
+
end
|
44
|
+
cli_execute 'whenever:update_crontab'
|
45
|
+
config.should have_run('cd /foo/bar && wc --update-crontab wi')
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
metadata
ADDED
@@ -0,0 +1,104 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: capistrano-deploy-management
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.1.0
|
5
|
+
prerelease:
|
6
|
+
platform: ruby
|
7
|
+
authors:
|
8
|
+
- Dominik Rodler
|
9
|
+
autorequire:
|
10
|
+
bindir: bin
|
11
|
+
cert_chain: []
|
12
|
+
date: 2012-08-04 00:00:00.000000000 Z
|
13
|
+
dependencies:
|
14
|
+
- !ruby/object:Gem::Dependency
|
15
|
+
name: capistrano
|
16
|
+
requirement: !ruby/object:Gem::Requirement
|
17
|
+
none: false
|
18
|
+
requirements:
|
19
|
+
- - ~>
|
20
|
+
- !ruby/object:Gem::Version
|
21
|
+
version: '2.9'
|
22
|
+
type: :runtime
|
23
|
+
prerelease: false
|
24
|
+
version_requirements: !ruby/object:Gem::Requirement
|
25
|
+
none: false
|
26
|
+
requirements:
|
27
|
+
- - ~>
|
28
|
+
- !ruby/object:Gem::Version
|
29
|
+
version: '2.9'
|
30
|
+
description:
|
31
|
+
email:
|
32
|
+
- dominik.rodler@gmail.com
|
33
|
+
executables: []
|
34
|
+
extensions: []
|
35
|
+
extra_rdoc_files: []
|
36
|
+
files:
|
37
|
+
- .DS_Store
|
38
|
+
- .gitignore
|
39
|
+
- .rspec
|
40
|
+
- .travis.yml
|
41
|
+
- Gemfile
|
42
|
+
- MIT-LICENSE
|
43
|
+
- README.md
|
44
|
+
- Rakefile
|
45
|
+
- capistrano-deploy-management.gemspec
|
46
|
+
- lib/.DS_Store
|
47
|
+
- lib/capistrano-deploy-management.rb
|
48
|
+
- lib/capistrano-deploy-management/bundle.rb
|
49
|
+
- lib/capistrano-deploy-management/bundler.rb
|
50
|
+
- lib/capistrano-deploy-management/git.rb
|
51
|
+
- lib/capistrano-deploy-management/memcached.rb
|
52
|
+
- lib/capistrano-deploy-management/multistage.rb
|
53
|
+
- lib/capistrano-deploy-management/passenger.rb
|
54
|
+
- lib/capistrano-deploy-management/rails.rb
|
55
|
+
- lib/capistrano-deploy-management/rails_assets.rb
|
56
|
+
- lib/capistrano-deploy-management/rvm.rb
|
57
|
+
- lib/capistrano-deploy-management/unicorn.rb
|
58
|
+
- lib/capistrano-deploy-management/whenever.rb
|
59
|
+
- spec/.DS_Store
|
60
|
+
- spec/bundle_spec.rb
|
61
|
+
- spec/deploy_spec.rb
|
62
|
+
- spec/git_spec.rb
|
63
|
+
- spec/multistage_spec.rb
|
64
|
+
- spec/passenger_spec.rb
|
65
|
+
- spec/rails_assets_spec.rb
|
66
|
+
- spec/rails_spec.rb
|
67
|
+
- spec/spec_helper.rb
|
68
|
+
- spec/unicorn_spec.rb
|
69
|
+
- spec/whenever_spec.rb
|
70
|
+
homepage: https://github.com/drdla/capistrano-deploy-management
|
71
|
+
licenses: []
|
72
|
+
post_install_message:
|
73
|
+
rdoc_options: []
|
74
|
+
require_paths:
|
75
|
+
- lib
|
76
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
77
|
+
none: false
|
78
|
+
requirements:
|
79
|
+
- - ! '>='
|
80
|
+
- !ruby/object:Gem::Version
|
81
|
+
version: '0'
|
82
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
83
|
+
none: false
|
84
|
+
requirements:
|
85
|
+
- - ! '>='
|
86
|
+
- !ruby/object:Gem::Version
|
87
|
+
version: '0'
|
88
|
+
requirements: []
|
89
|
+
rubyforge_project:
|
90
|
+
rubygems_version: 1.8.24
|
91
|
+
signing_key:
|
92
|
+
specification_version: 3
|
93
|
+
summary: Capistrano deploy recipes
|
94
|
+
test_files:
|
95
|
+
- spec/bundle_spec.rb
|
96
|
+
- spec/deploy_spec.rb
|
97
|
+
- spec/git_spec.rb
|
98
|
+
- spec/multistage_spec.rb
|
99
|
+
- spec/passenger_spec.rb
|
100
|
+
- spec/rails_assets_spec.rb
|
101
|
+
- spec/rails_spec.rb
|
102
|
+
- spec/spec_helper.rb
|
103
|
+
- spec/unicorn_spec.rb
|
104
|
+
- spec/whenever_spec.rb
|