CloudyScripts 1.10.44 → 2.11.45
Sign up to get free protection for your applications and to get access to all the features.
- data/Rakefile +1 -1
- data/lib/help/script_execution_state.rb +2 -1
- data/lib/help/state_transition_helper.rb +4 -4
- data/lib/help/v_cloud_api_handler.rb +155 -0
- data/lib/help/v_cloud_transition_helper.rb +58 -0
- data/lib/scripts/ec2/ami2_ebs_conversion.rb +3 -0
- data/lib/scripts/ec2/audit_via_ssh.rb +20 -11
- data/lib/scripts/ec2/copy_ami.rb +3 -0
- data/lib/scripts/ec2/download_snapshot.rb +3 -0
- data/lib/scripts/ec2/ec2_script.rb +1 -1
- data/lib/scripts/vCloud/open_port_checker_vm.rb +82 -0
- data/lib/scripts/vCloud/v_cloud_script.rb +110 -0
- metadata +10 -6
data/Rakefile
CHANGED
@@ -12,7 +12,7 @@ require 'rake/testtask'
|
|
12
12
|
|
13
13
|
spec = Gem::Specification.new do |s|
|
14
14
|
s.name = 'CloudyScripts'
|
15
|
-
s.version = '
|
15
|
+
s.version = '2.11.45'
|
16
16
|
s.has_rdoc = true
|
17
17
|
s.extra_rdoc_files = ['README.rdoc', 'LICENSE']
|
18
18
|
s.summary = 'Scripts to facilitate programming for infrastructure clouds.'
|
@@ -1,11 +1,12 @@
|
|
1
1
|
require "help/state_transition_helper"
|
2
|
+
require "help/v_cloud_transition_helper"
|
2
3
|
|
3
4
|
# Implements a little state-machine.
|
4
5
|
# Usage: for every state you need, extend this class.
|
5
6
|
# The method enter() must be implemented for every state you code and
|
6
7
|
# return another state.
|
7
8
|
class ScriptExecutionState
|
8
|
-
include StateTransitionHelper
|
9
|
+
include StateTransitionHelper, VCloudTransitionHelper
|
9
10
|
|
10
11
|
# context information for the state (hash)
|
11
12
|
attr_reader :context, :logger
|
@@ -637,7 +637,7 @@ module StateTransitionHelper
|
|
637
637
|
# Get root filesytem type
|
638
638
|
def get_root_partition_fs_type()
|
639
639
|
post_message("Retrieving '/' root partition filesystem type...")
|
640
|
-
@logger.debug "get root partition
|
640
|
+
@logger.debug "get root partition filesystem type"
|
641
641
|
# get root device and then its fs type
|
642
642
|
root_fs_type = remote_handler().get_root_fs_type()
|
643
643
|
@logger.debug "Found '#{root_fs_type}' as root filesystem type"
|
@@ -652,7 +652,7 @@ module StateTransitionHelper
|
|
652
652
|
# Get root filesytem type and label
|
653
653
|
def get_root_partition_fs_type_and_label()
|
654
654
|
post_message("Retrieving '/' root partition filesystem type and label...")
|
655
|
-
@logger.debug "get root partition
|
655
|
+
@logger.debug "get root partition filesystem type"
|
656
656
|
# get root device and then its fs type
|
657
657
|
root_fs_type = remote_handler().get_root_fs_type()
|
658
658
|
@logger.debug "Found '#{root_fs_type}' as root filesystem type"
|
@@ -681,7 +681,7 @@ module StateTransitionHelper
|
|
681
681
|
# Get partition filesytem type
|
682
682
|
def get_partition_fs_type(part)
|
683
683
|
post_message("Retrieving '#{part}' partition filesystem type...")
|
684
|
-
@logger.debug "get #{part} partition
|
684
|
+
@logger.debug "get #{part} partition filesystem type"
|
685
685
|
# get partition device and then its fs type
|
686
686
|
part_fs_type = remote_handler().get_partition_fs_type(part)
|
687
687
|
@logger.debug "Found '#{part_fs_type}' as filesystem type"
|
@@ -696,7 +696,7 @@ module StateTransitionHelper
|
|
696
696
|
# Get partition filesytem type and label
|
697
697
|
def get_partition_fs_type_and_label(part)
|
698
698
|
post_message("Retrieving '#{part}' partition filesystem type...")
|
699
|
-
@logger.debug "get #{part} partition
|
699
|
+
@logger.debug "get #{part} partition filesystem type"
|
700
700
|
# get partition device and then its fs type
|
701
701
|
part_fs_type = remote_handler().get_partition_fs_type(part)
|
702
702
|
@logger.debug "Found '#{part_fs_type}' as filesystem type"
|
@@ -0,0 +1,155 @@
|
|
1
|
+
require "base64"
|
2
|
+
require "xmlsimple"
|
3
|
+
|
4
|
+
class VCloudApiHandler
|
5
|
+
def initialize(username, password, url_endpoint, logger = Logger.new(STDOUT))
|
6
|
+
@username = username
|
7
|
+
@password = password
|
8
|
+
@url_endpoint = url_endpoint
|
9
|
+
@logger = logger
|
10
|
+
end
|
11
|
+
|
12
|
+
def versions
|
13
|
+
res = Net::HTTP.get "#{@url_endpoint}", '/api/versions'
|
14
|
+
return XmlSimple.xml_in(res)
|
15
|
+
end
|
16
|
+
|
17
|
+
def login
|
18
|
+
url = URI.parse("https://services.vcloudexpress.terremark.com/api/v0.8a-ext1.6/login")
|
19
|
+
req = Net::HTTP::Post.new(url.path)
|
20
|
+
req.basic_auth("#{@username}", "#{@password}")
|
21
|
+
req.add_field('Content-Length','0')
|
22
|
+
req.add_field('Content-Type', 'application/vdn.vmware.vCloud.orgList+xml')
|
23
|
+
@logger.debug "--- Request-Header:"
|
24
|
+
req.each_header do |key, name|
|
25
|
+
@logger.debug "#{key}: #{name}"
|
26
|
+
end
|
27
|
+
res = http_request(url, req)
|
28
|
+
@vcloud_token = res.get_fields("Set-Cookie")
|
29
|
+
xmlbody = XmlSimple.xml_in(res.body)
|
30
|
+
@organization_link = xmlbody["Org"].first["href"]
|
31
|
+
return xmlbody
|
32
|
+
end
|
33
|
+
|
34
|
+
def org
|
35
|
+
res = generic_get_request(@organization_link)
|
36
|
+
xmlbody = XmlSimple.xml_in(res.body)
|
37
|
+
xmlbody["Link"].each() {|info|
|
38
|
+
@logger.info "org: found info on #{info.inspect}"
|
39
|
+
case info['type']
|
40
|
+
when "application/vnd.vmware.vcloud.vdc+xml"
|
41
|
+
@vdc_link = info['href']
|
42
|
+
when "application/vnd.vmware.vcloud.catalog+xml"
|
43
|
+
@catalog_link = info['href']
|
44
|
+
when "application/vnd.vmware.vcloud.tasksList+xml"
|
45
|
+
@taskslist_link = info['href']
|
46
|
+
when "application/vnd.tmrk.vcloudExpress.keysList+xml"
|
47
|
+
@keyslist_link = info['href']
|
48
|
+
else
|
49
|
+
@logger.info "could not identify #{info['type']} for org"
|
50
|
+
end
|
51
|
+
}
|
52
|
+
return xmlbody
|
53
|
+
end
|
54
|
+
|
55
|
+
def vdc
|
56
|
+
@server_links = []
|
57
|
+
@network_links = []
|
58
|
+
res = generic_get_request(@vdc_link)
|
59
|
+
xmlbody = XmlSimple.xml_in(res.body)
|
60
|
+
xmlbody['ResourceEntities'].first['ResourceEntity'].each() do |info|
|
61
|
+
@logger.info "vdc: found info on #{info.inspect}"
|
62
|
+
case info['type']
|
63
|
+
when "application/vnd.vmware.vcloud.vApp+xml"
|
64
|
+
@server_links << info['href']
|
65
|
+
else
|
66
|
+
@logger.info "could not identify #{info['type']} for vdc"
|
67
|
+
end
|
68
|
+
end
|
69
|
+
@logger.debug "@server_links = #{@server_links.inspect}"
|
70
|
+
xmlbody['AvailableNetworks'].first['Network'].each() do |info|
|
71
|
+
@logger.debug "vdc: found info on #{info.inspect}"
|
72
|
+
case info['type']
|
73
|
+
when "application/vnd.vmware.vcloud.network+xml"
|
74
|
+
@network_links << info['href']
|
75
|
+
else
|
76
|
+
@logger.info "could not identify #{info['type']} for vdc"
|
77
|
+
end
|
78
|
+
end
|
79
|
+
@logger.debug "@network_links = #{@network_links.inspect}"
|
80
|
+
end
|
81
|
+
|
82
|
+
def v_apps
|
83
|
+
@server_links.each() {|server_link|
|
84
|
+
generic_get_request(server_link)
|
85
|
+
}
|
86
|
+
end
|
87
|
+
|
88
|
+
def networks
|
89
|
+
@network_links.each() {|network_link|
|
90
|
+
generic_get_request(network_link)
|
91
|
+
}
|
92
|
+
end
|
93
|
+
|
94
|
+
def internet_services
|
95
|
+
@internet_services_link = "#{@vdc_link}/internetServices"
|
96
|
+
@internet_services_link.gsub!("api/v0.8a-ext1.6","api/extensions/v1.6")
|
97
|
+
res = generic_get_request(@internet_services_link)
|
98
|
+
xmlbody = XmlSimple.xml_in(res.body)
|
99
|
+
return xmlbody
|
100
|
+
end
|
101
|
+
|
102
|
+
def server_ip_address(server_ip)
|
103
|
+
server_link = "https://services.vcloudexpress.terremark.com/api/v0.8a-ext1.6/vapp/#{server_ip}"
|
104
|
+
res = generic_get_request(server_link)
|
105
|
+
xmlbody = XmlSimple.xml_in(res.body)
|
106
|
+
ip_address = xmlbody["NetworkConnectionSection"].first["NetworkConnection"].first["IpAddress"]
|
107
|
+
@logger.debug "Ip: #{ip_address}"
|
108
|
+
#"NetworkConnectionSection"=>[{"NetworkConnection"=>[{"IpAddress"=>["10.114.117.11"],
|
109
|
+
ip_address
|
110
|
+
end
|
111
|
+
|
112
|
+
def firewall_rules
|
113
|
+
|
114
|
+
end
|
115
|
+
|
116
|
+
#private
|
117
|
+
|
118
|
+
def generic_get_request(full_url)
|
119
|
+
raise Exception.new("no url") if full_url == nil
|
120
|
+
@logger.debug "generic request: url = #{full_url.inspect}"
|
121
|
+
url = URI.parse(full_url)
|
122
|
+
req = Net::HTTP::Get.new(url.path)
|
123
|
+
prepare_request(req)
|
124
|
+
return http_request(url, req)
|
125
|
+
end
|
126
|
+
|
127
|
+
def prepare_request(request)
|
128
|
+
raise Exception.new("no vcloud-token") if @vcloud_token == nil
|
129
|
+
request.add_field('Content-Length','0')
|
130
|
+
request.add_field('Content-Type', 'application/vdn.vmware.vCloud.orgList+xml')
|
131
|
+
request.add_field('Cookie', @vcloud_token)
|
132
|
+
|
133
|
+
@logger.debug "--- Request-Header:"
|
134
|
+
request.each_header do |key, name|
|
135
|
+
@logger.debug "#{key}: #{name}"
|
136
|
+
end
|
137
|
+
end
|
138
|
+
|
139
|
+
def http_request(url, request)
|
140
|
+
http_session = Net::HTTP.new(url.host, url.port)
|
141
|
+
http_session.verify_mode = OpenSSL::SSL::VERIFY_NONE
|
142
|
+
http_session.use_ssl = true
|
143
|
+
res = http_session.start {|http|
|
144
|
+
http.request(request)
|
145
|
+
}
|
146
|
+
|
147
|
+
@logger.debug "--- Response-Header:"
|
148
|
+
res.each_header do |key, name|
|
149
|
+
@logger.debug "#{key}: #{name}"
|
150
|
+
end
|
151
|
+
xmlbody = XmlSimple.xml_in(res.body)
|
152
|
+
@logger.debug "response-body: #{xmlbody.inspect}"
|
153
|
+
return res
|
154
|
+
end
|
155
|
+
end
|
@@ -0,0 +1,58 @@
|
|
1
|
+
require 'net/scp'
|
2
|
+
|
3
|
+
# Contains methods that are used by the scripts in the state-machines. Since
|
4
|
+
# they are reused by different scripts, they are factored into this module
|
5
|
+
module VCloudTransitionHelper
|
6
|
+
|
7
|
+
def retrieve_ip_services
|
8
|
+
@context[:vcloud_internet_services] = []
|
9
|
+
vcloud_api_handler.login
|
10
|
+
vcloud_api_handler.org
|
11
|
+
vcloud_api_handler.vdc
|
12
|
+
res = vcloud_api_handler.internet_services
|
13
|
+
puts "retrieved: #{res.inspect}"
|
14
|
+
res['InternetService'].each() {|is|
|
15
|
+
port = is['Port'].first.to_i
|
16
|
+
ip = is['PublicIpAddress'].first['Name'].first #TODO: several IPs may be defined here?
|
17
|
+
id = is['PublicIpAddress'].first['Id'].first
|
18
|
+
@context[:vcloud_internet_services] << {:port => port, :ip => ip, :id => id}
|
19
|
+
}
|
20
|
+
end
|
21
|
+
|
22
|
+
protected
|
23
|
+
|
24
|
+
#setting/retrieving handlers
|
25
|
+
|
26
|
+
def remote_handler()
|
27
|
+
if @remote_handler == nil
|
28
|
+
if @context[:remote_command_handler] == nil
|
29
|
+
@context[:remote_command_handler] = RemoteCommandHandler.new
|
30
|
+
else
|
31
|
+
@remote_handler = @context[:remote_command_handler]
|
32
|
+
end
|
33
|
+
end
|
34
|
+
@remote_handler
|
35
|
+
end
|
36
|
+
|
37
|
+
def remote_handler=(remote_handler)
|
38
|
+
@remote_handler = remote_handler
|
39
|
+
end
|
40
|
+
|
41
|
+
def vcloud_api_handler()
|
42
|
+
if @vcloud_api_handler == nil
|
43
|
+
@vcloud_api_handler = @context[:vcloud_api_handler]
|
44
|
+
end
|
45
|
+
@vcloud_api_handler
|
46
|
+
end
|
47
|
+
|
48
|
+
def vcloud_api_handler=(vcloud_api_handler)
|
49
|
+
@vcloud_api_handler = vcloud_api_handler
|
50
|
+
end
|
51
|
+
|
52
|
+
def post_message(msg)
|
53
|
+
if @context[:script] != nil
|
54
|
+
@context[:script].post_message(msg)
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
end
|
@@ -34,6 +34,9 @@ class Ami2EbsConversion < Ec2Script
|
|
34
34
|
if @input_params[:security_group_name] == nil
|
35
35
|
@input_params[:security_group_name] = "default"
|
36
36
|
end
|
37
|
+
if @input_params[:ami_id] == nil && !(@input_params[:ami_id] =~ /^ami-.*$/)
|
38
|
+
raise Exception.new("Invalid AMI ID specified: #{@input_params[:ami_id]}")
|
39
|
+
end
|
37
40
|
ec2_helper = Ec2Helper.new(@input_params[:ec2_api_handler])
|
38
41
|
if !ec2_helper.check_open_port(@input_params[:security_group_name], 22)
|
39
42
|
raise Exception.new("Port 22 must be opened for security group #{@input_params[:security_group_name]} to connect via SSH")
|
@@ -4,7 +4,6 @@ require "help/remote_command_handler"
|
|
4
4
|
require "help/ec2_helper"
|
5
5
|
require "audit/lib/audit"
|
6
6
|
require "AWS"
|
7
|
-
require 'pp'
|
8
7
|
|
9
8
|
# Audit an AMI or an instance via an SSH connection using a specific benchmark
|
10
9
|
#
|
@@ -42,6 +41,7 @@ class AuditViaSsh < Ec2Script
|
|
42
41
|
else
|
43
42
|
raise Exception.new("Invalid Audit '#{@input_params[:audit_type]}' specified")
|
44
43
|
end
|
44
|
+
|
45
45
|
ec2_helper = Ec2Helper.new(@input_params[:ec2_api_handler])
|
46
46
|
if !ec2_helper.check_open_port(@input_params[:sec_grp_name], 22)
|
47
47
|
raise Exception.new("Port 22 must be opened for security group 'default' to connect via SSH")
|
@@ -81,13 +81,21 @@ class AuditViaSsh < Ec2Script
|
|
81
81
|
@context[:instance_id] = instance_infos[0]
|
82
82
|
@context[:public_dns_name] = instance_infos[1]
|
83
83
|
@context[:tmp_dir] = tmp_dir
|
84
|
-
#puts "DEBUG: Audit Scripts"
|
85
|
-
#pp @context
|
86
84
|
|
87
85
|
Dir::mkdir(tmp_dir)
|
88
86
|
if FileTest::directory?(tmp_dir)
|
89
87
|
post_message("local temporary directory created")
|
90
88
|
end
|
89
|
+
|
90
|
+
if @context[:audit] == nil
|
91
|
+
@context[:audit] = Audit.new(:benchmark => @context[:benchmark_file], :attachment_dir => @context[:tmp_dir],
|
92
|
+
:connection_type => :ssh,
|
93
|
+
:connection_params => {:user => @context[:ssh_user],
|
94
|
+
:keys => @context[:ssh_key_file],
|
95
|
+
:host => @context[:public_dns_name],
|
96
|
+
:paranoid => false},
|
97
|
+
:logger => nil)
|
98
|
+
end
|
91
99
|
|
92
100
|
LaunchAuditViaSsh.new(@context)
|
93
101
|
end
|
@@ -96,20 +104,21 @@ class AuditViaSsh < Ec2Script
|
|
96
104
|
# Launch the audit via SSH
|
97
105
|
class LaunchAuditViaSsh < AuditViaSshState
|
98
106
|
def enter
|
99
|
-
audit =
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
107
|
+
audit = @context[:audit]
|
108
|
+
#audit = Audit.new(:benchmark => @context[:benchmark_file], :attachment_dir => @context[:tmp_dir],
|
109
|
+
# :connection_type => :ssh,
|
110
|
+
# :connection_params => {:user => @context[:ssh_user],
|
111
|
+
# :keys => @context[:ssh_key_file],
|
112
|
+
# :host => @context[:public_dns_name],
|
113
|
+
# :paranoid => false},
|
105
114
|
#:timeout => 120,
|
106
115
|
#:verbose => :warn},
|
107
|
-
|
116
|
+
# :logger => nil)
|
108
117
|
audit.start(false)
|
109
118
|
@context[:result][:audit_test] = []
|
110
119
|
audit.results.each() {|key, value|
|
111
120
|
if key =~ /^SSH_.*$/ || key =~ /^APACHE2_.*$/
|
112
|
-
|
121
|
+
puts "DEBUG: Key: #{key}, Result: #{value.result}, Desc: #{value.rule.description}"
|
113
122
|
@context[:result][:audit_test] << {:name => key, :desc => value.rule.description, :status => value.result}
|
114
123
|
post_message("== > Test #{key}: Status: #{value.result.eql?("pass") ? "OK" : "NOK"}\n Desc: #{value.rule.description}")
|
115
124
|
end
|
data/lib/scripts/ec2/copy_ami.rb
CHANGED
@@ -38,6 +38,9 @@ class CopyAmi < Ec2Script
|
|
38
38
|
end
|
39
39
|
|
40
40
|
def check_input_parameters()
|
41
|
+
if @input_params[:ami_id] == nil && !(@input_params[:ami_id] =~ /^ami-.*$/)
|
42
|
+
raise Exception.new("Invalid AMI ID specified: #{@input_params[:ami_id]}")
|
43
|
+
end
|
41
44
|
ec2_helper = Ec2Helper.new(@input_params[:ec2_api_handler])
|
42
45
|
if ec2_helper.ami_prop(@input_params[:ami_id], 'rootDeviceType') != "ebs"
|
43
46
|
raise Exception.new("must be an EBS type image")
|
@@ -41,6 +41,9 @@ class DownloadSnapshot < Ec2Script
|
|
41
41
|
if !ec2_helper.check_open_port(@input_params[:security_group_name], 22)
|
42
42
|
raise Exception.new("Port 22 must be opened for security group #{@input_params[:security_group_name]} to connect via SSH")
|
43
43
|
end
|
44
|
+
if !ec2_helper.check_open_port(@input_params[:security_group_name], 80)
|
45
|
+
raise Exception.new("Port 80 must be opened for security group #{@input_params[:security_group_name]} to make the download link work")
|
46
|
+
end
|
44
47
|
if @input_params[:source_device] == nil
|
45
48
|
@input_params[:source_device] = "/dev/sdj1"
|
46
49
|
end
|
@@ -21,7 +21,7 @@ class Ec2Script
|
|
21
21
|
@input_params[:result] = @result
|
22
22
|
@input_params.each() do |param_key, param_value|
|
23
23
|
if [:logger, :ec2_api_handler, :target_ec2_handler, :remote_command_handler,
|
24
|
-
:source_ssh_keydata, :target_ssh_keydata
|
24
|
+
:source_ssh_keydata, :target_ssh_keydata, :ssh_keydata
|
25
25
|
].include?(param_key.to_s.to_sym)
|
26
26
|
@logger.debug("INPUT PARAM #{param_key} is set [but not logged]")
|
27
27
|
else
|
@@ -0,0 +1,82 @@
|
|
1
|
+
require "help/script_execution_state"
|
2
|
+
require "help/remote_command_handler"
|
3
|
+
require "scripts/vcloud/v_cloud_script"
|
4
|
+
|
5
|
+
# Identifies all open internet services and checks if
|
6
|
+
# there are actually used by a service. Note: this script depends
|
7
|
+
# on a propriatary version of the vCloud API implemented by Terremark.
|
8
|
+
#
|
9
|
+
|
10
|
+
class OpenPortCheckerVm < VCloudScript
|
11
|
+
# Input parameters
|
12
|
+
# * vcloud_api_handler => object that allows to access the vCloud service
|
13
|
+
def initialize(input_params)
|
14
|
+
super(input_params)
|
15
|
+
end
|
16
|
+
|
17
|
+
def check_input_parameters()
|
18
|
+
if @input_params[:vcloud_api_handler] == nil
|
19
|
+
raise Exception.new("no vCloud handler specified")
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
def load_initial_state()
|
24
|
+
OpenPortCheckerState.load_state(@input_params)
|
25
|
+
end
|
26
|
+
|
27
|
+
private
|
28
|
+
|
29
|
+
# Here begins the state machine implementation
|
30
|
+
class OpenPortCheckerState < ScriptExecutionState
|
31
|
+
def self.load_state(context)
|
32
|
+
state = context[:initial_state] == nil ? RetrievingInternetServices.new(context) : context[:initial_state]
|
33
|
+
state
|
34
|
+
end
|
35
|
+
|
36
|
+
end
|
37
|
+
|
38
|
+
# Nothing done yet. Retrieve all internet services.
|
39
|
+
class RetrievingInternetServices < OpenPortCheckerState
|
40
|
+
def enter
|
41
|
+
retrieve_ip_services()
|
42
|
+
CheckingInternetServices.new(@context)
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
# Got all internet services. Go through them and check the ports.
|
47
|
+
class CheckingInternetServices < OpenPortCheckerState
|
48
|
+
def enter
|
49
|
+
@context[:result][:port_checks] = []
|
50
|
+
@context[:vcloud_internet_services].each() do |is|
|
51
|
+
port = is[:port]
|
52
|
+
ip = is[:ip]
|
53
|
+
identifier = is[:id]
|
54
|
+
begin
|
55
|
+
result = @context[:remote_command_handler].is_port_open?(ip, port)
|
56
|
+
post_message("check port #{port} on IP #{ip} => #{result ? "successful" : "failed"}")
|
57
|
+
rescue Exception => e
|
58
|
+
@logger.warn("exception during executing port check: #{e}")
|
59
|
+
end
|
60
|
+
@context[:result][:port_checks] << {:ip => ip, :id => identifier,
|
61
|
+
:port => port, :success => result
|
62
|
+
}
|
63
|
+
end
|
64
|
+
AnalysisDone.new(@context)
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
# Nothing done yet. Retrieve all security groups
|
69
|
+
class AnalysisDone < OpenPortCheckerState
|
70
|
+
def enter
|
71
|
+
Done.new(@context)
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
# Script done.
|
76
|
+
class Done < OpenPortCheckerState
|
77
|
+
def done?
|
78
|
+
true
|
79
|
+
end
|
80
|
+
end
|
81
|
+
|
82
|
+
end
|
@@ -0,0 +1,110 @@
|
|
1
|
+
# Base class for any script for vCloud.
|
2
|
+
class VCloudScript
|
3
|
+
# Initialization. Common Input parameters:
|
4
|
+
# * vcloud_api_handler => used to connect to the API (needs user/password/api-url)
|
5
|
+
# * logger => allows to pass a ruby logger object used for logging (optional, default is a stdout logger with level WARN)
|
6
|
+
# Scripts may add specific key/value pairs.
|
7
|
+
def initialize(input_params)
|
8
|
+
@input_params = input_params
|
9
|
+
@state_change_listeners = []
|
10
|
+
@progress_message_listeners = []
|
11
|
+
if input_params[:logger] == nil
|
12
|
+
@logger = Logger.new(STDOUT)
|
13
|
+
@logger.level = Logger::WARN
|
14
|
+
input_params[:logger] = @logger
|
15
|
+
else
|
16
|
+
@logger = input_params[:logger]
|
17
|
+
end
|
18
|
+
@result = {:done => false, :failed => false}
|
19
|
+
@input_params[:result] = @result
|
20
|
+
@input_params.each() do |param_key, param_value|
|
21
|
+
if [:logger, :vcloud_api_handler, :target_ec2_handler, :remote_command_handler,
|
22
|
+
:source_ssh_keydata, :target_ssh_keydata, :ssh_keydata
|
23
|
+
].include?(param_key.to_s.to_sym)
|
24
|
+
@logger.debug("INPUT PARAM #{param_key} is set [but not logged]")
|
25
|
+
else
|
26
|
+
@logger.debug("INPUT PARAM #{param_key} = #{param_value.inspect}")
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
def register_state_change_listener(listener)
|
32
|
+
@state_change_listeners << listener
|
33
|
+
end
|
34
|
+
|
35
|
+
def register_progress_message_listener(listener)
|
36
|
+
@progress_message_listeners << listener
|
37
|
+
end
|
38
|
+
|
39
|
+
# Check input parameters (in @input_parameters object variable)
|
40
|
+
# and set default values.
|
41
|
+
# Abstract method to be implemented by extending classes.
|
42
|
+
def check_input_parameters()
|
43
|
+
raise Exception.new("check_input_parameters must be implemented")
|
44
|
+
end
|
45
|
+
|
46
|
+
# Load the initial state for the script.
|
47
|
+
# Abstract method to be implemented by extending classes.
|
48
|
+
def load_initial_state()
|
49
|
+
raise Exception.new("load_initial_state must be implemented")
|
50
|
+
end
|
51
|
+
|
52
|
+
# Executes the script.
|
53
|
+
def start_script()
|
54
|
+
# optional parameters and initialization
|
55
|
+
check_input_parameters()
|
56
|
+
@input_params[:script] = self
|
57
|
+
begin
|
58
|
+
current_state = load_initial_state()
|
59
|
+
@state_change_listeners.each() {|listener|
|
60
|
+
current_state.register_state_change_listener(listener)
|
61
|
+
}
|
62
|
+
end_state = current_state.start_state_machine()
|
63
|
+
if end_state.failed?
|
64
|
+
@result[:failed] = true
|
65
|
+
@result[:failure_reason] = current_state.end_state.failure_reason
|
66
|
+
@result[:end_state] = current_state.end_state
|
67
|
+
else
|
68
|
+
@result[:failed] = false
|
69
|
+
end
|
70
|
+
rescue Exception => e
|
71
|
+
@logger.warn "exception during execution: #{e}"
|
72
|
+
@logger.warn e.backtrace.join("\n")
|
73
|
+
err = e.to_s
|
74
|
+
err += " (in #{current_state.end_state.to_s})" unless current_state == nil
|
75
|
+
@result[:failed] = true
|
76
|
+
@result[:failure_reason] = err
|
77
|
+
@result[:end_state] = current_state.end_state unless current_state == nil
|
78
|
+
ensure
|
79
|
+
begin
|
80
|
+
@input_params[:remote_command_handler].disconnect
|
81
|
+
rescue Exception => e2
|
82
|
+
end
|
83
|
+
end
|
84
|
+
#
|
85
|
+
@result[:done] = true
|
86
|
+
end
|
87
|
+
|
88
|
+
|
89
|
+
# Return a hash of results. Common values are:
|
90
|
+
# * :done => is true when the script has terminated, otherwise false
|
91
|
+
# * :failed => is false when the script succeeded
|
92
|
+
# * :failure_reason => returns a failure reason (string)
|
93
|
+
# * :end_state => returns the state, in which the script terminated (#Help::ScriptExecutionState)
|
94
|
+
# Scripts may add specific key/value pairs.
|
95
|
+
# *
|
96
|
+
# Returns a hash with the following information:
|
97
|
+
# :done => if execution is done
|
98
|
+
#
|
99
|
+
def get_execution_result
|
100
|
+
@result
|
101
|
+
end
|
102
|
+
|
103
|
+
def post_message(message, level = Logger::DEBUG)
|
104
|
+
@progress_message_listeners.each() {|listener|
|
105
|
+
listener.new_message(message, level)
|
106
|
+
}
|
107
|
+
end
|
108
|
+
|
109
|
+
end
|
110
|
+
|
metadata
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: CloudyScripts
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
hash:
|
4
|
+
hash: 121
|
5
5
|
prerelease: false
|
6
6
|
segments:
|
7
|
-
-
|
8
|
-
-
|
9
|
-
-
|
10
|
-
version:
|
7
|
+
- 2
|
8
|
+
- 11
|
9
|
+
- 45
|
10
|
+
version: 2.11.45
|
11
11
|
platform: ruby
|
12
12
|
authors:
|
13
13
|
- Matthias Jung
|
@@ -15,7 +15,7 @@ autorequire:
|
|
15
15
|
bindir: bin
|
16
16
|
cert_chain: []
|
17
17
|
|
18
|
-
date: 2011-09-
|
18
|
+
date: 2011-09-16 00:00:00 +02:00
|
19
19
|
default_executable:
|
20
20
|
dependencies:
|
21
21
|
- !ruby/object:Gem::Dependency
|
@@ -257,6 +257,8 @@ files:
|
|
257
257
|
- lib/help/script_execution_state.rb
|
258
258
|
- lib/help/state_change_listener.rb
|
259
259
|
- lib/help/state_transition_helper.rb
|
260
|
+
- lib/help/v_cloud_api_handler.rb
|
261
|
+
- lib/help/v_cloud_transition_helper.rb
|
260
262
|
- lib/scripts/ec2/ami2_ebs_conversion.rb
|
261
263
|
- lib/scripts/ec2/audit_via_ssh.rb
|
262
264
|
- lib/scripts/ec2/copy_ami.rb
|
@@ -268,6 +270,8 @@ files:
|
|
268
270
|
- lib/scripts/ec2/open_port_checker.rb
|
269
271
|
- lib/scripts/ec2/port_range_detector.rb
|
270
272
|
- lib/scripts/ec2/snapshot_optimization.rb
|
273
|
+
- lib/scripts/vCloud/open_port_checker_vm.rb
|
274
|
+
- lib/scripts/vCloud/v_cloud_script.rb
|
271
275
|
has_rdoc: true
|
272
276
|
homepage: http://elastic-security.com
|
273
277
|
licenses: []
|