rhc 0.94.8 → 0.95.13
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/README.md +27 -1
- data/bin/rhc +15 -23
- data/bin/rhc-app +4 -1
- data/bin/rhc-chk +3 -0
- data/bin/rhc-create-app +3 -0
- data/bin/rhc-create-domain +3 -0
- data/bin/rhc-ctl-app +3 -0
- data/bin/rhc-ctl-domain +3 -0
- data/bin/rhc-domain +5 -2
- data/bin/rhc-domain-info +3 -0
- data/bin/rhc-port-forward +16 -18
- data/bin/rhc-snapshot +3 -0
- data/bin/rhc-sshkey +3 -0
- data/bin/rhc-tail-files +3 -0
- data/bin/rhc-user-info +1 -0
- data/features/README.md +70 -0
- data/features/lib/rhc_helper/app.rb +124 -0
- data/features/lib/rhc_helper/cartridge.rb +72 -0
- data/features/lib/rhc_helper/commandify.rb +154 -0
- data/features/lib/rhc_helper/domain.rb +50 -0
- data/features/lib/rhc_helper/httpify.rb +107 -0
- data/features/lib/rhc_helper/loggable.rb +39 -0
- data/features/lib/rhc_helper/persistable.rb +38 -0
- data/features/lib/rhc_helper/runnable.rb +41 -0
- data/features/lib/rhc_helper.rb +7 -0
- data/features/step_definitions/application_steps.rb +99 -0
- data/features/step_definitions/cartridge_steps.rb +42 -0
- data/features/step_definitions/client_steps.rb +32 -0
- data/features/step_definitions/domain_steps.rb +19 -0
- data/features/support/env.rb +99 -0
- data/features/verify.feature +123 -0
- data/lib/rhc/cli.rb +4 -1
- data/lib/rhc/commands/base.rb +28 -6
- data/lib/rhc/commands/server.rb +4 -1
- data/lib/rhc/commands/setup.rb +24 -0
- data/lib/rhc/commands.rb +10 -5
- data/lib/rhc/config.rb +90 -21
- data/lib/rhc/core_ext.rb +11 -2
- data/lib/rhc/coverage_helper.rb +35 -0
- data/lib/rhc/help_formatter.rb +30 -0
- data/lib/rhc/helpers.rb +41 -5
- data/lib/rhc/ssh_key_helpers.rb +72 -0
- data/lib/rhc/targz.rb +2 -8
- data/lib/rhc/wizard.rb +75 -58
- data/lib/rhc-common.rb +20 -13
- data/lib/rhc-rest.rb +3 -11
- data/spec/coverage_helper.rb +51 -0
- data/spec/rest_spec_helper.rb +86 -0
- data/spec/rhc/cli_spec.rb +19 -3
- data/spec/rhc/commands/server_spec.rb +2 -2
- data/spec/rhc/common_spec.rb +49 -0
- data/spec/rhc/config_spec.rb +328 -0
- data/spec/rhc/helpers_spec.rb +74 -1
- data/spec/rhc/rest_client_spec.rb +402 -0
- data/spec/rhc/rest_spec.rb +454 -0
- data/spec/rhc/targz_spec.rb +13 -0
- data/spec/rhc/wizard_spec.rb +305 -43
- data/spec/spec_helper.rb +30 -25
- metadata +124 -5
@@ -0,0 +1,154 @@
|
|
1
|
+
require 'benchmark'
|
2
|
+
require 'fileutils'
|
3
|
+
|
4
|
+
module RHCHelper
|
5
|
+
module Commandify
|
6
|
+
# Implements a method missing approach that will convert calls
|
7
|
+
# like rhc_app_create into 'rhc app create' on the command line
|
8
|
+
def method_missing(sym, *args, &block)
|
9
|
+
if sym.to_s.start_with?("rhc")
|
10
|
+
# Build up the command
|
11
|
+
cmd = get_cmd(sym)
|
12
|
+
|
13
|
+
# Get any blocks that should be run after processing
|
14
|
+
cmd_callback = get_cmd_callback(cmd, args[0])
|
15
|
+
|
16
|
+
# Add arguments to the command
|
17
|
+
cmd << get_args(cmd, args[0])
|
18
|
+
|
19
|
+
# Run the command, timing it
|
20
|
+
time = Benchmark.realtime do
|
21
|
+
run(cmd, args[0], &cmd_callback).should == 0
|
22
|
+
end
|
23
|
+
|
24
|
+
# Log the benchmarking info
|
25
|
+
perf_logger.info "#{time} #{sym.to_s.upcase} #{$namespace} #{$login}"
|
26
|
+
else
|
27
|
+
super(sym, *args, &block)
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
# Given a method name, convert to an equivalent
|
32
|
+
# rhc command line string. This method handles
|
33
|
+
# exceptions like converting rhc_app_add_alias
|
34
|
+
# to rhc app add-alias.
|
35
|
+
def get_cmd(method_sym)
|
36
|
+
cmd = method_sym.to_s.gsub('_', ' ')
|
37
|
+
|
38
|
+
# Handle parameters with a dash
|
39
|
+
cmd.gsub!('add alias', 'add-alias')
|
40
|
+
cmd.gsub!('remove alias', 'remove-alias')
|
41
|
+
cmd.gsub!('force stop', 'force-stop')
|
42
|
+
|
43
|
+
return cmd
|
44
|
+
end
|
45
|
+
|
46
|
+
# Print out the command arguments based on the state of the application instance
|
47
|
+
def get_args(cmd, cartridge=nil, debug=true)
|
48
|
+
args = " "
|
49
|
+
args << "-l #{$username} "
|
50
|
+
args << "-p #{$password} "
|
51
|
+
args << "-d " if debug
|
52
|
+
|
53
|
+
# Add the application name for all application commands
|
54
|
+
if cmd =~ /app/
|
55
|
+
raise "No application name" unless @name
|
56
|
+
args << "-a #{@name} "
|
57
|
+
end
|
58
|
+
|
59
|
+
# Command specific arguments
|
60
|
+
case cmd
|
61
|
+
when /domain/
|
62
|
+
raise "No namespace set" unless $namespace
|
63
|
+
args << "-n #{$namespace} "
|
64
|
+
when /destroy/
|
65
|
+
args << "-b "
|
66
|
+
when /snapshot/
|
67
|
+
args << "-f #{@snapshot} "
|
68
|
+
when /create/
|
69
|
+
args << "-r #{@repo} "
|
70
|
+
args << "-t #{@type} "
|
71
|
+
when /add-alias/
|
72
|
+
raise "No alias set" unless @alias
|
73
|
+
args << "--alias #{@alias} "
|
74
|
+
when /cartridge/
|
75
|
+
raise "No cartridge supplied" unless cartridge
|
76
|
+
args << "-c #{cartridge}"
|
77
|
+
end
|
78
|
+
|
79
|
+
args.rstrip
|
80
|
+
end
|
81
|
+
|
82
|
+
# This looks for a callback method that is defined for the command.
|
83
|
+
# For example, a command with rhc_app_create_callback will match
|
84
|
+
# and be returned for the 'rhc app create' command. The most specific
|
85
|
+
# callback will be matched, so rhc_app_create_callback being more
|
86
|
+
# specific than rhc_app_callback.
|
87
|
+
def get_cmd_callback(cmd, cartridge=nil)
|
88
|
+
# Break the command up on spaces
|
89
|
+
cmd_parts = cmd.split
|
90
|
+
|
91
|
+
# Drop the 'rhc' portion from the array
|
92
|
+
cmd_parts.shift
|
93
|
+
|
94
|
+
# Look for a method match ending in _callback
|
95
|
+
cmd_parts.length.times do
|
96
|
+
begin
|
97
|
+
# Look for a callback match and return on any find
|
98
|
+
return method((cmd_parts.join("_") + "_callback").to_sym)
|
99
|
+
rescue NameError
|
100
|
+
# Remove one of the parts to see if there is a more
|
101
|
+
# generic match defined
|
102
|
+
cmd_parts.pop
|
103
|
+
end
|
104
|
+
end
|
105
|
+
|
106
|
+
return nil
|
107
|
+
end
|
108
|
+
end
|
109
|
+
|
110
|
+
# The regex to parse the ssh output from the create app results
|
111
|
+
SSH_OUTPUT_PATTERN = %r|ssh://([^@]+)@([^/]+)|
|
112
|
+
|
113
|
+
#
|
114
|
+
# Begin Post Processing Callbacks
|
115
|
+
#
|
116
|
+
def app_create_callback(exitcode, stdout, stderr, arg)
|
117
|
+
match = stdout.split.map {|line| line.match(SSH_OUTPUT_PATTERN)}.compact[0]
|
118
|
+
@uid = match[1] if match
|
119
|
+
raise "UID not parsed from app create output" unless @uid
|
120
|
+
persist
|
121
|
+
end
|
122
|
+
|
123
|
+
def app_destroy_callback(exitcode, stdout, stderr, arg)
|
124
|
+
FileUtils.rm_rf @repo
|
125
|
+
FileUtils.rm_rf @file
|
126
|
+
@repo, @file = nil
|
127
|
+
end
|
128
|
+
|
129
|
+
def cartridge_add_callback(exitcode, stdout, stderr, cartridge)
|
130
|
+
if cartridge.start_with?('mysql-')
|
131
|
+
@mysql_hostname = /^Connection URL: mysql:\/\/(.*)\/$/.match(stdout)[1]
|
132
|
+
@mysql_user = /^ +Root User: (.*)$/.match(stdout)[1]
|
133
|
+
@mysql_password = /^ +Root Password: (.*)$/.match(stdout)[1]
|
134
|
+
@mysql_database = /^ +Database Name: (.*)$/.match(stdout)[1]
|
135
|
+
|
136
|
+
@mysql_hostname.should_not be_nil
|
137
|
+
@mysql_user.should_not be_nil
|
138
|
+
@mysql_password.should_not be_nil
|
139
|
+
@mysql_database.should_not be_nil
|
140
|
+
end
|
141
|
+
|
142
|
+
@embed << cartridge
|
143
|
+
persist
|
144
|
+
end
|
145
|
+
|
146
|
+
def cartridge_remove_callback(exitcode, stdout, stderr, cartridge)
|
147
|
+
@mysql_hostname = nil
|
148
|
+
@mysql_user = nil
|
149
|
+
@mysql_password = nil
|
150
|
+
@mysql_database = nil
|
151
|
+
@embed.delete(cartridge)
|
152
|
+
persist
|
153
|
+
end
|
154
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
require 'dnsruby'
|
2
|
+
require 'rhc-rest'
|
3
|
+
|
4
|
+
module RHCHelper
|
5
|
+
#
|
6
|
+
# A class to help maintain the state from rhc calls
|
7
|
+
#
|
8
|
+
class Domain
|
9
|
+
extend Runnable
|
10
|
+
extend Commandify
|
11
|
+
include Dnsruby
|
12
|
+
|
13
|
+
def self.create_if_needed(prefix="test")
|
14
|
+
unless $namespace
|
15
|
+
loop do
|
16
|
+
# Loop until we find a unique namespace
|
17
|
+
chars = ("1".."9").to_a
|
18
|
+
namespace = prefix + Array.new(8, '').collect{chars[rand(chars.size)]}.join
|
19
|
+
|
20
|
+
# No retries on reservation check
|
21
|
+
unless reserved?(namespace)
|
22
|
+
# Set the global namespace
|
23
|
+
$namespace = namespace
|
24
|
+
|
25
|
+
# Create the domain
|
26
|
+
rhc_domain_create
|
27
|
+
|
28
|
+
# Write the new domain to a file in the temp directory
|
29
|
+
File.open(File.join(RHCHelper::TEMP_DIR, 'namespace'), 'w') do |f|
|
30
|
+
f.write(namespace)
|
31
|
+
end
|
32
|
+
|
33
|
+
break
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
def self.reserved?(namespace=$namespace)
|
40
|
+
# If we get a response, then the namespace is reserved
|
41
|
+
# An exception means that it is available
|
42
|
+
begin
|
43
|
+
Dnsruby::Resolver.new.query("#{namespace}.#{$domain}", Dnsruby::Types::TXT)
|
44
|
+
return true
|
45
|
+
rescue
|
46
|
+
return false
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
@@ -0,0 +1,107 @@
|
|
1
|
+
require 'uri'
|
2
|
+
require 'net/https'
|
3
|
+
require 'ostruct'
|
4
|
+
|
5
|
+
module RHCHelper
|
6
|
+
module Httpify
|
7
|
+
include Loggable
|
8
|
+
|
9
|
+
# attributes that contain statistics based on calls to connect
|
10
|
+
attr_accessor :response_code, :response_time
|
11
|
+
|
12
|
+
def http_instance(uri, timeout=30)
|
13
|
+
proxy = ENV['http_proxy'] ? URI.parse(ENV['http_proxy']) : OpenStruct.new
|
14
|
+
http = Net::HTTP.new(uri.host, uri.port, proxy.host, proxy.port)
|
15
|
+
http.open_timeout = timeout
|
16
|
+
http.read_timeout = timeout
|
17
|
+
if (uri.scheme == "https")
|
18
|
+
http.use_ssl = true
|
19
|
+
http.verify_mode = OpenSSL::SSL::VERIFY_NONE
|
20
|
+
end
|
21
|
+
return http.start
|
22
|
+
end
|
23
|
+
|
24
|
+
def http_get(url, timeout=30)
|
25
|
+
uri = URI.parse(url)
|
26
|
+
http = http_instance(uri, timeout)
|
27
|
+
request = Net::HTTP::Get.new(uri.request_uri)
|
28
|
+
http.request(request)
|
29
|
+
end
|
30
|
+
|
31
|
+
def http_head(url, host=nil, follow_redirects=true)
|
32
|
+
uri = URI.parse(url)
|
33
|
+
http = http_instance(uri)
|
34
|
+
request = Net::HTTP::Head.new(uri.request_uri)
|
35
|
+
request["Host"] = host if host
|
36
|
+
response = http.request(request)
|
37
|
+
|
38
|
+
if follow_redirects and response.is_a?(Net::HTTPRedirection)
|
39
|
+
return http_head(response.header['location'])
|
40
|
+
else
|
41
|
+
return response
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def is_inaccessible?(max_retries=120)
|
46
|
+
max_retries.times do |i|
|
47
|
+
begin
|
48
|
+
if http_head("http://#{hostname}").is_a? Net::HTTPServerError
|
49
|
+
return true
|
50
|
+
else
|
51
|
+
logger.info("Connection still accessible / retry #{i} / #{hostname}")
|
52
|
+
sleep 1
|
53
|
+
end
|
54
|
+
rescue
|
55
|
+
return true
|
56
|
+
end
|
57
|
+
end
|
58
|
+
return false
|
59
|
+
end
|
60
|
+
|
61
|
+
def is_accessible?(use_https=false, max_retries=120, host=nil)
|
62
|
+
prefix = use_https ? "https://" : "http://"
|
63
|
+
url = prefix + hostname
|
64
|
+
|
65
|
+
max_retries.times do |i|
|
66
|
+
begin
|
67
|
+
if http_head(url, host).is_a? Net::HTTPSuccess
|
68
|
+
return true
|
69
|
+
else
|
70
|
+
logger.info("Connection still inaccessible / retry #{i} / #{url}")
|
71
|
+
sleep 1
|
72
|
+
end
|
73
|
+
rescue SocketError
|
74
|
+
logger.info("Connection still inaccessible / retry #{i} / #{url}")
|
75
|
+
sleep 1
|
76
|
+
end
|
77
|
+
end
|
78
|
+
|
79
|
+
return false
|
80
|
+
end
|
81
|
+
|
82
|
+
def connect(use_https=false, max_retries=30)
|
83
|
+
prefix = use_https ? "https://" : "http://"
|
84
|
+
url = prefix + hostname
|
85
|
+
|
86
|
+
logger.info("Connecting to #{url}")
|
87
|
+
beginning_time = Time.now
|
88
|
+
|
89
|
+
max_retries.times do |i|
|
90
|
+
response = http_get(url, 1)
|
91
|
+
|
92
|
+
if response.is_a? Net::HTTPSuccess
|
93
|
+
@response_code = response.code
|
94
|
+
@response_time = Time.now - beginning_time
|
95
|
+
logger.info("Connection result = #{@response_code} / #{url}")
|
96
|
+
logger.info("Connection response time = #{@response_time} / #{url}")
|
97
|
+
return response.body
|
98
|
+
else
|
99
|
+
logger.info("Connection failed / retry #{i} / #{url}")
|
100
|
+
sleep 1
|
101
|
+
end
|
102
|
+
end
|
103
|
+
|
104
|
+
return nil
|
105
|
+
end
|
106
|
+
end
|
107
|
+
end
|
@@ -0,0 +1,39 @@
|
|
1
|
+
require 'logger'
|
2
|
+
|
3
|
+
module RHCHelper
|
4
|
+
module Loggable
|
5
|
+
PASSWORD_REGEX = / -p [^\s]* /
|
6
|
+
|
7
|
+
def logger
|
8
|
+
Loggable.logger
|
9
|
+
end
|
10
|
+
|
11
|
+
def perf_logger
|
12
|
+
Loggable.perf_logger
|
13
|
+
end
|
14
|
+
|
15
|
+
def self.logger
|
16
|
+
@logger ||= Logger.new($stdout)
|
17
|
+
end
|
18
|
+
|
19
|
+
def self.logger=(logger)
|
20
|
+
@logger = logger
|
21
|
+
original_formatter = Logger::Formatter.new
|
22
|
+
@logger.formatter = proc { |severity, datetime, progname, msg|
|
23
|
+
# Filter out any passwords
|
24
|
+
filter_msg = msg.gsub(PASSWORD_REGEX, " -p ***** ")
|
25
|
+
|
26
|
+
# Format with the original formatter
|
27
|
+
original_formatter.call(severity, datetime, progname, filter_msg)
|
28
|
+
}
|
29
|
+
end
|
30
|
+
|
31
|
+
def self.perf_logger
|
32
|
+
@perf_logger ||= Logger.new($stdout)
|
33
|
+
end
|
34
|
+
|
35
|
+
def self.perf_logger=(logger)
|
36
|
+
@perf_logger = logger
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
@@ -0,0 +1,38 @@
|
|
1
|
+
require 'active_support/json'
|
2
|
+
require 'active_support/core_ext/object/to_json'
|
3
|
+
|
4
|
+
module RHCHelper
|
5
|
+
module Persistable
|
6
|
+
include ActiveSupport::JSON
|
7
|
+
include Loggable
|
8
|
+
|
9
|
+
def find_on_fs
|
10
|
+
Dir.glob("#{RHCHelper::TEMP_DIR}/*.json").collect {|f| App.from_file(f)}
|
11
|
+
end
|
12
|
+
|
13
|
+
def from_file(filename)
|
14
|
+
App.from_json(ActiveSupport::JSON.decode(File.open(filename, "r") {|f| f.readlines}[0]))
|
15
|
+
end
|
16
|
+
|
17
|
+
def from_json(json)
|
18
|
+
app = App.new(json['type'], json['name'])
|
19
|
+
app.embed = json['embed']
|
20
|
+
app.mysql_user = json['mysql_user']
|
21
|
+
app.mysql_password = json['mysql_password']
|
22
|
+
app.mysql_hostname = json['mysql_hostname']
|
23
|
+
app.uid = json['uid']
|
24
|
+
return app
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
module Persistify
|
29
|
+
include ActiveSupport::JSON
|
30
|
+
|
31
|
+
attr_accessor :file
|
32
|
+
|
33
|
+
def persist
|
34
|
+
json = self.to_json(:except => [:logger, :perf_logger])
|
35
|
+
File.open(@file, "w") {|f| f.puts json}
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
@@ -0,0 +1,41 @@
|
|
1
|
+
require 'open4'
|
2
|
+
require 'timeout'
|
3
|
+
|
4
|
+
module RHCHelper
|
5
|
+
module Runnable
|
6
|
+
include Loggable
|
7
|
+
|
8
|
+
def run(cmd, arg=nil, input=[])
|
9
|
+
logger.info("Running: #{cmd}")
|
10
|
+
|
11
|
+
exit_code = -1
|
12
|
+
output = nil
|
13
|
+
|
14
|
+
# Don't let a command run more than 5 minutes
|
15
|
+
Timeout::timeout(500) do
|
16
|
+
pid, stdin, stdout, stderr = Open4::popen4 cmd
|
17
|
+
input.each {|line| stdin.puts line}
|
18
|
+
stdin.close
|
19
|
+
|
20
|
+
# Block until the command finishes
|
21
|
+
ignored, status = Process::waitpid2 pid
|
22
|
+
out = stdout.read.strip
|
23
|
+
err = stderr.read.strip
|
24
|
+
stdout.close
|
25
|
+
stderr.close
|
26
|
+
logger.debug("Standard Output:\n#{out}")
|
27
|
+
logger.debug("Standard Error:\n#{err}")
|
28
|
+
|
29
|
+
# Allow a caller to pass in a block to process the output
|
30
|
+
yield status.exitstatus, out, err, arg if block_given?
|
31
|
+
exit_code = status.exitstatus
|
32
|
+
end
|
33
|
+
|
34
|
+
if exit_code != 0
|
35
|
+
logger.error("(#{$$}): Execution failed #{cmd} with exit_code: #{exit_code.to_s}")
|
36
|
+
end
|
37
|
+
|
38
|
+
return exit_code
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
@@ -0,0 +1,99 @@
|
|
1
|
+
require 'fileutils'
|
2
|
+
require 'rhc/config'
|
3
|
+
|
4
|
+
include RHCHelper
|
5
|
+
|
6
|
+
Given /^an existing (.+) application with an embedded (.*) cartridge$/ do |type, embed|
|
7
|
+
App.find_on_fs.each do |app|
|
8
|
+
if app.type == type and app.embed.include?(embed)
|
9
|
+
@app = app
|
10
|
+
break
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
@app.should_not be_nil, 'No existing applications w/cartridges found. Check the creation scenarios for failures.'
|
15
|
+
end
|
16
|
+
|
17
|
+
Given /^an existing (.+) application with embedded (.*) and (.*) cartridges$/ do |type, embed_1, embed_2|
|
18
|
+
App.find_on_fs.each do |app|
|
19
|
+
if app.type == type and app.embed.include?(embed_1) and app.embed.include?(embed_2)
|
20
|
+
@app = app
|
21
|
+
break
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
@app.should_not be_nil, 'No existing applications w/cartridges found. Check the creation scenarios for failures.'
|
26
|
+
end
|
27
|
+
|
28
|
+
Given /^an existing (.+) application( without an embedded cartridge)?$/ do |type, ignore|
|
29
|
+
App.find_on_fs.each do |app|
|
30
|
+
if app.type == type and app.embed.empty?
|
31
|
+
@app = app
|
32
|
+
break
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
@app.should_not be_nil, 'No existing applications found. Check the creation scenarios for failures.'
|
37
|
+
end
|
38
|
+
|
39
|
+
When /^(\d+) (.+) applications are created$/ do |app_count, type|
|
40
|
+
@apps = app_count.to_i.times.collect do
|
41
|
+
app = App.create_unique(type)
|
42
|
+
app.rhc_app_create
|
43
|
+
app
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
When /^the application is stopped$/ do
|
48
|
+
@app.rhc_app_stop
|
49
|
+
end
|
50
|
+
|
51
|
+
When /^the application is started$/ do
|
52
|
+
@app.rhc_app_start
|
53
|
+
end
|
54
|
+
|
55
|
+
When /^the application is restarted$/ do
|
56
|
+
@app.rhc_app_restart
|
57
|
+
end
|
58
|
+
|
59
|
+
When /^the application is destroyed$/ do
|
60
|
+
@app.rhc_app_destroy
|
61
|
+
end
|
62
|
+
|
63
|
+
When /^the application is snapshot$/ do
|
64
|
+
@snapshot = File.join(RHCHelper::TEMP_DIR, "snapshot.tar.gz")
|
65
|
+
@app.snapshot = @snapshot
|
66
|
+
@app.rhc_app_snapshot_save
|
67
|
+
end
|
68
|
+
|
69
|
+
When /^the application is shown$/ do
|
70
|
+
@app.rhc_app_show
|
71
|
+
end
|
72
|
+
|
73
|
+
When /^the application is tidied$/ do
|
74
|
+
@app.rhc_app_tidy
|
75
|
+
end
|
76
|
+
|
77
|
+
Then /^the snapshot should be found$/ do
|
78
|
+
File.exist?(@snapshot).should be_true
|
79
|
+
(File.size(@snapshot) > 0).should be_true
|
80
|
+
end
|
81
|
+
|
82
|
+
Then /^the applications should be accessible?$/ do
|
83
|
+
@apps.each do |app|
|
84
|
+
app.is_accessible?.should be_true
|
85
|
+
app.is_accessible?(true).should be_true
|
86
|
+
end
|
87
|
+
end
|
88
|
+
|
89
|
+
Then /^the application should be accessible$/ do
|
90
|
+
@app.is_accessible?.should be_true
|
91
|
+
@app.is_accessible?(true).should be_true, "Application was not accessible and should be"
|
92
|
+
end
|
93
|
+
|
94
|
+
Then /^the application should not be accessible$/ do
|
95
|
+
@app.is_inaccessible?.should be_true, "Application was still accessible when it shouldn't be"
|
96
|
+
end
|
97
|
+
|
98
|
+
Then /^it should succeed$/ do
|
99
|
+
end
|
@@ -0,0 +1,42 @@
|
|
1
|
+
require 'fileutils'
|
2
|
+
require 'rhc/config'
|
3
|
+
|
4
|
+
include RHCHelper
|
5
|
+
|
6
|
+
When /^the (.+) cartridge is added$/ do |name|
|
7
|
+
@app.add_cartridge name
|
8
|
+
end
|
9
|
+
|
10
|
+
When /^the (.+) cartridge is stopped$/ do |name|
|
11
|
+
@app.cartridge(name).stop
|
12
|
+
end
|
13
|
+
|
14
|
+
When /^the (.+) cartridge is restarted$/ do |name|
|
15
|
+
@app.cartridge(name).restart
|
16
|
+
end
|
17
|
+
|
18
|
+
When /^the (.+) cartridge is started$/ do |name|
|
19
|
+
@app.cartridge(name).start
|
20
|
+
end
|
21
|
+
|
22
|
+
When /^the (.+) cartridge is removed$/ do |name|
|
23
|
+
@app.remove_cartridge name
|
24
|
+
end
|
25
|
+
|
26
|
+
Then /^the (.+) cartridge should be running$/ do |name|
|
27
|
+
@app.cartridge(name).status.should match("RESULT:\n(.+) is running|RESULT:\n(\n|.)+Uptime:")
|
28
|
+
end
|
29
|
+
|
30
|
+
Then /^the (.+) cartridge should be stopped$/ do |name|
|
31
|
+
@app.cartridge(name).status.should match("RESULT:\n(.+) stopped")
|
32
|
+
end
|
33
|
+
|
34
|
+
Then /^the (.+) cartridge should be removed$/ do |name|
|
35
|
+
# for some reason the server returns Success when cart does not exist
|
36
|
+
@app.cartridge(name).status.should match("RESULT:\n(.*)Success")
|
37
|
+
end
|
38
|
+
|
39
|
+
|
40
|
+
Then /^adding the (.+) cartridge should fail$/ do |name|
|
41
|
+
@app.add_cartridge(name).should == 1
|
42
|
+
end
|
@@ -0,0 +1,32 @@
|
|
1
|
+
# Cross-platform way of finding an executable in the $PATH.
|
2
|
+
#
|
3
|
+
# which('ruby') #=> /usr/bin/ruby
|
4
|
+
#
|
5
|
+
# Solution found at: http://bit.ly/8dKQsa
|
6
|
+
#
|
7
|
+
def which(cmd)
|
8
|
+
exts = ENV['PATHEXT'] ? ENV['PATHEXT'].split(';') : ['']
|
9
|
+
ENV['PATH'].split(File::PATH_SEPARATOR).each do |path|
|
10
|
+
exts.each { |ext|
|
11
|
+
exe = "#{path}/#{cmd}#{ext}"
|
12
|
+
return exe if File.executable? exe
|
13
|
+
}
|
14
|
+
end
|
15
|
+
return nil
|
16
|
+
end
|
17
|
+
|
18
|
+
Given /^the libra client tools$/ do
|
19
|
+
which('rhc').should_not be_nil
|
20
|
+
end
|
21
|
+
|
22
|
+
When /^the setup wizard is run$/ do
|
23
|
+
RHCHelper::App.rhc_setup
|
24
|
+
|
25
|
+
# Force a refresh of the loaded RHC state
|
26
|
+
RHC::Config.initialize
|
27
|
+
end
|
28
|
+
|
29
|
+
Then /^the client tools should be setup$/ do
|
30
|
+
RHC::Config.should_run_wizard?.should be_false, "Wizard still thinks it needs to be run"
|
31
|
+
end
|
32
|
+
|
@@ -0,0 +1,19 @@
|
|
1
|
+
include RHCHelper
|
2
|
+
When /^a new domain is needed and created$/ do
|
3
|
+
Domain.create_if_needed
|
4
|
+
end
|
5
|
+
|
6
|
+
Then /^the domain should be reserved?$/ do
|
7
|
+
# Sleep to allow DNS to propogate
|
8
|
+
sleep 5
|
9
|
+
|
10
|
+
# Check for up to a minute
|
11
|
+
resolved = false
|
12
|
+
120.times do
|
13
|
+
resolved = Domain.reserved?
|
14
|
+
break if resolved
|
15
|
+
sleep 1
|
16
|
+
end
|
17
|
+
|
18
|
+
resolved.should be_true, 'Not able to lookup DNS TXT record in time.'
|
19
|
+
end
|