engineyard 1.7.0.pre2 → 2.0.0.pre1
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/lib/engineyard/cli.rb +15 -12
- data/lib/engineyard/cli/recipes.rb +31 -3
- data/lib/engineyard/cli/ui.rb +24 -22
- data/lib/engineyard/config.rb +43 -3
- data/lib/engineyard/deploy_config/migrate.rb +2 -2
- data/lib/engineyard/version.rb +1 -1
- data/spec/ey/deploy_spec.rb +23 -9
- data/spec/ey/list_environments_spec.rb +0 -1
- data/spec/ey/status_spec.rb +5 -2
- metadata +11 -12
- data/lib/engineyard/cli/#recipes.rb# +0 -32
data/lib/engineyard/cli.rb
CHANGED
@@ -3,6 +3,7 @@ require 'engineyard/error'
|
|
3
3
|
require 'engineyard/thor'
|
4
4
|
require 'engineyard/deploy_config'
|
5
5
|
require 'engineyard/serverside_runner'
|
6
|
+
require 'launchy'
|
6
7
|
|
7
8
|
module EY
|
8
9
|
class CLI < EY::Thor
|
@@ -146,7 +147,7 @@ module EY
|
|
146
147
|
app_env = fetch_app_environment(options[:app], options[:environment], options[:account])
|
147
148
|
deployment = app_env.last_deployment
|
148
149
|
if deployment
|
149
|
-
ui.say "# Status of last deployment of #{app_env.
|
150
|
+
ui.say "# Status of last deployment of #{app_env.hierarchy_name}:"
|
150
151
|
ui.say "#"
|
151
152
|
ui.show_deployment(deployment)
|
152
153
|
ui.say "#"
|
@@ -177,10 +178,9 @@ module EY
|
|
177
178
|
:desc => "Show environments matching environment name"
|
178
179
|
def environments
|
179
180
|
if options[:all] && options[:simple]
|
180
|
-
|
181
|
-
puts api.environments.map {|env| env.name}
|
181
|
+
ui.print_simple_envs api.environments
|
182
182
|
elsif options[:all]
|
183
|
-
ui.print_envs(api.apps
|
183
|
+
ui.print_envs(api.apps)
|
184
184
|
else
|
185
185
|
remotes = nil
|
186
186
|
if options[:app] == ''
|
@@ -203,14 +203,17 @@ module EY
|
|
203
203
|
|
204
204
|
apps = resolver.matches.map { |app_env| app_env.app }.uniq
|
205
205
|
|
206
|
-
if
|
207
|
-
|
208
|
-
|
209
|
-
|
210
|
-
|
206
|
+
if options[:simple]
|
207
|
+
if apps.size > 1
|
208
|
+
message = "# This app matches multiple Applications in EY Cloud:\n"
|
209
|
+
apps.each { |app| message << "#\t#{app.name}\n" }
|
210
|
+
message << "# The following environments contain those applications:\n\n"
|
211
|
+
ui.warn(message)
|
212
|
+
end
|
213
|
+
ui.print_simple_envs(apps.map{ |app| app.environments }.flatten)
|
214
|
+
else
|
215
|
+
ui.print_envs(apps, config.default_environment)
|
211
216
|
end
|
212
|
-
|
213
|
-
ui.print_envs(apps, config.default_environment, options[:simple], config.endpoint)
|
214
217
|
end
|
215
218
|
end
|
216
219
|
map "envs" => :environments
|
@@ -263,7 +266,7 @@ module EY
|
|
263
266
|
env_config = config.environment_config(app_env.environment_name)
|
264
267
|
deploy_config = EY::DeployConfig.new(options, env_config, repo, ui)
|
265
268
|
|
266
|
-
ui.info("Rolling back #{app_env.
|
269
|
+
ui.info("Rolling back #{app_env.hierarchy_name}")
|
267
270
|
|
268
271
|
runner = serverside_runner(app_env, deploy_config.verbose)
|
269
272
|
runner.rollback do |args|
|
@@ -1,3 +1,5 @@
|
|
1
|
+
require 'tempfile'
|
2
|
+
|
1
3
|
module EY
|
2
4
|
class CLI
|
3
5
|
class Recipes < EY::Thor
|
@@ -66,10 +68,25 @@ module EY
|
|
66
68
|
environment.upload_recipes_at_path(filename)
|
67
69
|
ui.say "Recipes file #{filename} uploaded successfully for #{environment.name}"
|
68
70
|
else
|
69
|
-
|
71
|
+
path = cookbooks_dir_archive_path
|
72
|
+
environment.upload_recipes_at_path(path)
|
70
73
|
ui.say "Recipes in cookbooks/ uploaded successfully for #{environment.name}"
|
71
74
|
end
|
72
75
|
end
|
76
|
+
|
77
|
+
def cookbooks_dir_archive_path
|
78
|
+
unless FileTest.exist?("cookbooks")
|
79
|
+
raise EY::Error, "Could not find chef recipes. Please run from the root of your recipes repo."
|
80
|
+
end
|
81
|
+
|
82
|
+
recipes_file = Tempfile.new("recipes")
|
83
|
+
cmd = "tar czf '#{recipes_file.path}' cookbooks/"
|
84
|
+
|
85
|
+
unless system(cmd)
|
86
|
+
raise EY::Error, "Could not archive recipes.\nCommand `#{cmd}` exited with an error."
|
87
|
+
end
|
88
|
+
recipes_file.path
|
89
|
+
end
|
73
90
|
end
|
74
91
|
|
75
92
|
desc "download [--environment ENVIRONMENT]",
|
@@ -87,9 +104,20 @@ module EY
|
|
87
104
|
:required => true, :default => '',
|
88
105
|
:desc => "Name of the account in which the environment can be found"
|
89
106
|
def download
|
107
|
+
if File.exist?('cookbooks')
|
108
|
+
raise EY::Error, "Cannot download recipes, cookbooks directory already exists."
|
109
|
+
end
|
110
|
+
|
90
111
|
environment = fetch_environment(options[:environment], options[:account])
|
91
|
-
|
92
|
-
|
112
|
+
|
113
|
+
recipes = environment.download_recipes
|
114
|
+
cmd = "tar xzf '#{recipes.path}' cookbooks"
|
115
|
+
|
116
|
+
if system(cmd)
|
117
|
+
ui.say "Recipes downloaded successfully for #{environment.name}"
|
118
|
+
else
|
119
|
+
raise EY::Error, "Could not unarchive recipes.\nCommand `#{cmd}` exited with an error."
|
120
|
+
end
|
93
121
|
end
|
94
122
|
|
95
123
|
end
|
data/lib/engineyard/cli/ui.rb
CHANGED
@@ -127,30 +127,32 @@ module EY
|
|
127
127
|
return ''
|
128
128
|
end
|
129
129
|
|
130
|
-
def
|
131
|
-
|
132
|
-
|
133
|
-
|
134
|
-
|
135
|
-
|
136
|
-
|
137
|
-
|
138
|
-
|
139
|
-
|
140
|
-
|
141
|
-
|
142
|
-
|
143
|
-
|
144
|
-
|
145
|
-
|
146
|
-
|
147
|
-
|
148
|
-
|
149
|
-
puts "
|
130
|
+
def print_simple_envs(envs)
|
131
|
+
puts envs.map{|env| env.name }.uniq.sort
|
132
|
+
end
|
133
|
+
|
134
|
+
def print_envs(apps, default_env_name = nil)
|
135
|
+
apps.sort_by {|app| "#{app.account.name}/#{app.name}" }.each do |app|
|
136
|
+
puts "#{app.account.name}/#{app.name}"
|
137
|
+
if app.environments.any?
|
138
|
+
app.environments.sort_by {|env| env.name }.each do |env|
|
139
|
+
icount = env.instances_count
|
140
|
+
iname = case icount
|
141
|
+
when 0 then "(stopped)"
|
142
|
+
when 1 then "1 instance"
|
143
|
+
else "#{icount} instances"
|
144
|
+
end
|
145
|
+
|
146
|
+
name = env.name == default_env_name ? "#{env.name} (default)" : env.name
|
147
|
+
framework_env = env.framework_env && "[#{env.framework_env.center(12)}]"
|
148
|
+
|
149
|
+
puts " #{name.ljust(30)} #{framework_env} #{iname}"
|
150
150
|
end
|
151
|
-
|
152
|
-
puts ""
|
151
|
+
else
|
152
|
+
puts " (No environments)"
|
153
153
|
end
|
154
|
+
|
155
|
+
puts ""
|
154
156
|
end
|
155
157
|
end
|
156
158
|
|
data/lib/engineyard/config.rb
CHANGED
@@ -1,5 +1,6 @@
|
|
1
1
|
require 'uri'
|
2
2
|
require 'yaml'
|
3
|
+
require 'pathname'
|
3
4
|
require 'engineyard/error'
|
4
5
|
|
5
6
|
module EY
|
@@ -60,8 +61,44 @@ module EY
|
|
60
61
|
environments[environment_name] ||= {}
|
61
62
|
environments[environment_name][key] = value
|
62
63
|
ensure_path
|
64
|
+
comments = ey_yml_comments
|
63
65
|
@path.open('w') do |f|
|
64
|
-
|
66
|
+
f.puts comments
|
67
|
+
f.puts YAML.dump(@config)
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
EY_YML_HINTS = <<-HINTS
|
72
|
+
# ey.yml supports many deploy configuration options when committed in an
|
73
|
+
# application's repository.
|
74
|
+
#
|
75
|
+
# Valid locations: REPO_ROOT/ey.yml or REPO_ROOT/config/ey.yml.
|
76
|
+
#
|
77
|
+
# Examples options:
|
78
|
+
#
|
79
|
+
# environments:
|
80
|
+
# YOUR_ENVIRONMENT_NAME: # All options pertain only to the named environment
|
81
|
+
# migrate: true # Default --migrate choice for ey deploy
|
82
|
+
# migration_command: 'rake migrate' # Default migrate command to run when migrations are enabled
|
83
|
+
# branch: default_deploy_branch # Branch/ref to be deployed by default during ey deploy
|
84
|
+
# bundle_without: development test # The string to pass to bundle install --without ''
|
85
|
+
# maintenance_on_migrate: true # Enable maintenance page during migrate action (use with caution) (default: true)
|
86
|
+
# maintenance_on_restart: false # Enable maintanence page during every deploy (default: false for unicorn & passenger)
|
87
|
+
# ignore_database_adapter_warning: false # Hide the warning shown when the Gemfile does not contain a recognized database adapter (mongodb for example)
|
88
|
+
# your_own_custom_key: 'any attribute you put in ey.yml is available in deploy hooks'
|
89
|
+
#
|
90
|
+
# Further information available here:
|
91
|
+
# https://support.cloud.engineyard.com/entries/20996661-customize-your-deployment-on-engine-yard-cloud
|
92
|
+
#
|
93
|
+
# NOTE: Please commit this file into your git repository.
|
94
|
+
#
|
95
|
+
HINTS
|
96
|
+
|
97
|
+
def ey_yml_comments
|
98
|
+
if @path.exist?
|
99
|
+
existing = @path.readlines.grep(/^#/).join("\n")
|
100
|
+
else
|
101
|
+
EY_YML_HINTS
|
65
102
|
end
|
66
103
|
end
|
67
104
|
|
@@ -70,8 +107,11 @@ module EY
|
|
70
107
|
unless EY::Repo.exist?
|
71
108
|
raise "Not in application directory. Unable to save configuration."
|
72
109
|
end
|
73
|
-
|
74
|
-
|
110
|
+
if Pathname.new('config').exist?
|
111
|
+
@path = Pathname.new('config/ey.yml')
|
112
|
+
else
|
113
|
+
@path = Pathname.new('ey.yml')
|
114
|
+
end
|
75
115
|
@path
|
76
116
|
end
|
77
117
|
|
@@ -101,12 +101,12 @@ module EY
|
|
101
101
|
command_from_interaction
|
102
102
|
end
|
103
103
|
ui.say "#{env_config.path}: migrate settings saved for #{env_config.name}."
|
104
|
-
ui.
|
104
|
+
ui.info "It's a good idea to git commit #{env_config.path} with these new changes."
|
105
105
|
true
|
106
106
|
rescue Timeout::Error
|
107
107
|
@perform = nil
|
108
108
|
@command = nil
|
109
|
-
ui.error "Timeout when waiting for input.
|
109
|
+
ui.error "Timeout when waiting for input. Maybe this is not a terminal?"
|
110
110
|
ui.error "ey deploy no longer migrates when no default is set in ey.yml."
|
111
111
|
ui.error "Run interactively for step-by-step ey.yml migration setup."
|
112
112
|
return false
|
data/lib/engineyard/version.rb
CHANGED
data/spec/ey/deploy_spec.rb
CHANGED
@@ -107,43 +107,57 @@ describe "ey deploy" do
|
|
107
107
|
@ssh_commands.last.should =~ %r{/usr/local/ey_resin/ruby/bin/engineyard-serverside}
|
108
108
|
end
|
109
109
|
|
110
|
-
context "without migrate sepecified interactively reads migration command" do
|
111
|
-
|
110
|
+
context "without migrate sepecified, interactively reads migration command" do
|
111
|
+
def clean_ey_yml
|
112
|
+
File.unlink 'ey.yml' if File.exist?('ey.yml')
|
113
|
+
FileUtils.rm_r 'config' if FileTest.exist?('config')
|
114
|
+
end
|
115
|
+
|
116
|
+
before { clean_ey_yml }
|
117
|
+
after { clean_ey_yml }
|
112
118
|
|
113
|
-
it "defaults to yes, and then rake db:migrate" do
|
114
|
-
|
119
|
+
it "defaults to yes, and then rake db:migrate (and installs to config/ey.yml if config/ exists already)" do
|
120
|
+
ey_yml = Pathname.new('config/ey.yml')
|
121
|
+
File.exist?('ey.yml').should be_false
|
122
|
+
ey_yml.dirname.mkpath
|
123
|
+
ey_yml.should_not be_exist
|
115
124
|
ey(%w[deploy]) do |input|
|
116
125
|
input.puts('')
|
117
126
|
input.puts('')
|
118
127
|
end
|
119
128
|
@ssh_commands.last.should =~ /engineyard-serverside.*deploy/
|
120
129
|
@ssh_commands.last.should =~ /--migrate 'rake db:migrate'/
|
121
|
-
|
130
|
+
File.exist?('ey.yml').should be_false
|
131
|
+
ey_yml.should be_exist
|
132
|
+
env_conf = read_yaml(ey_yml.to_s)['environments']['giblets']
|
122
133
|
env_conf['migrate'].should == true
|
123
134
|
env_conf['migration_command'].should == 'rake db:migrate'
|
124
135
|
end
|
125
136
|
|
126
137
|
it "accepts new commands" do
|
127
|
-
File.exist?('
|
138
|
+
File.exist?('ey.yml').should be_false
|
139
|
+
FileTest.exist?('config').should be_false
|
128
140
|
ey(%w[deploy], :hide_err => true) do |input|
|
129
141
|
input.puts("y")
|
130
142
|
input.puts("ruby migrate")
|
131
143
|
end
|
132
144
|
@ssh_commands.last.should =~ /engineyard-serverside.*deploy/
|
133
145
|
@ssh_commands.last.should =~ /--migrate 'ruby migrate'/
|
134
|
-
|
146
|
+
File.exist?('ey.yml').should be_true
|
147
|
+
env_conf = read_yaml('ey.yml')['environments']['giblets']
|
135
148
|
env_conf['migrate'].should == true
|
136
149
|
env_conf['migration_command'].should == 'ruby migrate'
|
137
150
|
end
|
138
151
|
|
139
152
|
it "doesn't ask for the command if you say no" do
|
140
|
-
File.exist?('
|
153
|
+
File.exist?('ey.yml').should be_false
|
141
154
|
ey(%w[deploy], :hide_err => true) do |input|
|
142
155
|
input.puts("no")
|
143
156
|
end
|
144
157
|
@ssh_commands.last.should =~ /engineyard-serverside.*deploy/
|
145
158
|
@ssh_commands.last.should_not =~ /--migrate/
|
146
|
-
|
159
|
+
File.exist?('ey.yml').should be_true
|
160
|
+
read_yaml('ey.yml')['environments']['giblets']['migrate'].should == false
|
147
161
|
end
|
148
162
|
end
|
149
163
|
|
@@ -114,7 +114,6 @@ describe "ey environments with an ambiguous git repo" do
|
|
114
114
|
|
115
115
|
it "lists environments from all apps using the git repo" do
|
116
116
|
fast_ey %w[environments]
|
117
|
-
@out.should =~ /git repo matches multiple/i
|
118
117
|
@out.should include("giblets")
|
119
118
|
@out.should include("keycollector_production")
|
120
119
|
end
|
data/spec/ey/status_spec.rb
CHANGED
@@ -9,12 +9,15 @@ describe "ey environments" do
|
|
9
9
|
end
|
10
10
|
|
11
11
|
it "outputs the status of the deployment" do
|
12
|
+
ey %w[deploy -e giblets --ref HEAD --no-migrate]
|
12
13
|
ey %w[status -e giblets]
|
13
14
|
@out.should =~ /Application:\s+rails232app/
|
14
15
|
@out.should =~ /Environment:\s+giblets/
|
15
16
|
@out.should =~ /Ref:\s+HEAD/
|
16
|
-
@out.should =~ /Resolved Ref:\s+HEAD/
|
17
|
-
@out.should =~ /
|
17
|
+
@out.should =~ /Resolved Ref:\s+resolved-HEAD/
|
18
|
+
@out.should =~ /Commit:\s+[a-f0-9]{40}/
|
19
|
+
@out.should =~ /Migrate:\s+false/
|
20
|
+
@out.should =~ /Deployed by:\s+One App Many Envs/
|
18
21
|
@out.should =~ /Started at:/
|
19
22
|
@out.should =~ /Finished at:/
|
20
23
|
@out.should =~ /This deployment was successful/
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: engineyard
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 2.0.0.pre1
|
5
5
|
prerelease: 6
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2012-05-
|
12
|
+
date: 2012-05-22 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: rest-client
|
@@ -82,7 +82,7 @@ dependencies:
|
|
82
82
|
requirements:
|
83
83
|
- - '='
|
84
84
|
- !ruby/object:Gem::Version
|
85
|
-
version:
|
85
|
+
version: 2.0.0.pre1
|
86
86
|
type: :runtime
|
87
87
|
prerelease: false
|
88
88
|
version_requirements: !ruby/object:Gem::Requirement
|
@@ -90,7 +90,7 @@ dependencies:
|
|
90
90
|
requirements:
|
91
91
|
- - '='
|
92
92
|
- !ruby/object:Gem::Version
|
93
|
-
version:
|
93
|
+
version: 2.0.0.pre1
|
94
94
|
- !ruby/object:Gem::Dependency
|
95
95
|
name: engineyard-cloud-client
|
96
96
|
requirement: !ruby/object:Gem::Requirement
|
@@ -98,7 +98,7 @@ dependencies:
|
|
98
98
|
requirements:
|
99
99
|
- - ~>
|
100
100
|
- !ruby/object:Gem::Version
|
101
|
-
version: 0.1
|
101
|
+
version: 1.0.1
|
102
102
|
type: :runtime
|
103
103
|
prerelease: false
|
104
104
|
version_requirements: !ruby/object:Gem::Requirement
|
@@ -106,7 +106,7 @@ dependencies:
|
|
106
106
|
requirements:
|
107
107
|
- - ~>
|
108
108
|
- !ruby/object:Gem::Version
|
109
|
-
version: 0.1
|
109
|
+
version: 1.0.1
|
110
110
|
- !ruby/object:Gem::Dependency
|
111
111
|
name: net-ssh
|
112
112
|
requirement: !ruby/object:Gem::Requirement
|
@@ -128,17 +128,17 @@ dependencies:
|
|
128
128
|
requirement: !ruby/object:Gem::Requirement
|
129
129
|
none: false
|
130
130
|
requirements:
|
131
|
-
- -
|
131
|
+
- - ~>
|
132
132
|
- !ruby/object:Gem::Version
|
133
|
-
version: 2.
|
133
|
+
version: '2.1'
|
134
134
|
type: :runtime
|
135
135
|
prerelease: false
|
136
136
|
version_requirements: !ruby/object:Gem::Requirement
|
137
137
|
none: false
|
138
138
|
requirements:
|
139
|
-
- -
|
139
|
+
- - ~>
|
140
140
|
- !ruby/object:Gem::Version
|
141
|
-
version: 2.
|
141
|
+
version: '2.1'
|
142
142
|
- !ruby/object:Gem::Dependency
|
143
143
|
name: rspec
|
144
144
|
requirement: !ruby/object:Gem::Requirement
|
@@ -308,7 +308,6 @@ extensions: []
|
|
308
308
|
extra_rdoc_files: []
|
309
309
|
files:
|
310
310
|
- bin/ey
|
311
|
-
- lib/engineyard/cli/#recipes.rb#
|
312
311
|
- lib/engineyard/cli/api.rb
|
313
312
|
- lib/engineyard/cli/recipes.rb
|
314
313
|
- lib/engineyard/cli/ui.rb
|
@@ -413,7 +412,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
413
412
|
version: 1.3.1
|
414
413
|
requirements: []
|
415
414
|
rubyforge_project:
|
416
|
-
rubygems_version: 1.8.
|
415
|
+
rubygems_version: 1.8.24
|
417
416
|
signing_key:
|
418
417
|
specification_version: 3
|
419
418
|
summary: Command-line deployment for the Engine Yard cloud
|
@@ -1,32 +0,0 @@
|
|
1
|
-
module EY
|
2
|
-
class CLI
|
3
|
-
class Recipes < EY::Thor
|
4
|
-
X1gx1GGG desc "recipes apply [ENVIRONMENT]", <<-DESC
|
5
|
-
Run uploaded chef recipes on specified environment.
|
6
|
-
|
7
|
-
This is similar to '#{banner_base} rebuild' except Engine Yard's main
|
8
|
-
configuration step is skipped.
|
9
|
-
DESC
|
10
|
-
|
11
|
-
def apply(name = nil)
|
12
|
-
environment = fetch_environment(name)
|
13
|
-
environment.run_custom_recipes
|
14
|
-
EY.ui.say "Uploaded recipes started for #{environment.name}"
|
15
|
-
end
|
16
|
-
|
17
|
-
desc "recipes upload [ENVIRONMENT]", <<-DESC
|
18
|
-
Upload custom chef recipes to specified environment.
|
19
|
-
|
20
|
-
The current directory should contain a subdirectory named "cookbooks" to be
|
21
|
-
uploaded.
|
22
|
-
DESC
|
23
|
-
|
24
|
-
def upload(name = nil)
|
25
|
-
environment = fetch_environment(name)
|
26
|
-
environment.upload_recipes
|
27
|
-
EY.ui.say "Recipes uploaded successfully for #{environment.name}"
|
28
|
-
end
|
29
|
-
end
|
30
|
-
end
|
31
|
-
|
32
|
-
end
|