lorj 1.0.3 → 1.0.4

Sign up to get free protection for your applications and to get access to all the features.
Files changed (72) hide show
  1. checksums.yaml +4 -4
  2. data/example/students_1/students.rb +5 -6
  3. data/example/students_2/students.rb +4 -5
  4. data/example/students_3/students.rb +4 -5
  5. data/example/students_4/students.rb +4 -5
  6. data/example/students_5/students.rb +5 -5
  7. data/lib/core/core.rb +6 -1
  8. data/lib/core/core_controller.rb +1 -9
  9. data/lib/core/core_internal.rb +2 -1
  10. data/lib/core/core_model.rb +2 -10
  11. data/lib/core/core_object_data.rb +18 -0
  12. data/lib/core/core_object_params.rb +43 -4
  13. data/lib/core/core_process.rb +1 -9
  14. data/lib/core/core_process_setup.rb +32 -6
  15. data/lib/core/core_setup_ask.rb +41 -33
  16. data/lib/core/core_setup_encrypt.rb +29 -6
  17. data/lib/core/core_setup_init.rb +2 -2
  18. data/lib/core/definition.rb +33 -10
  19. data/lib/core/definition_internal.rb +10 -14
  20. data/lib/core/lorj_basedefinition.rb +16 -24
  21. data/lib/core/lorj_baseprocess.rb +113 -44
  22. data/lib/core/lorj_data.rb +2 -9
  23. data/lib/core/lorj_keypath.rb +5 -2
  24. data/lib/core_process/cloud/process/common.rb +4 -7
  25. data/lib/core_process/cloud/process/connection.rb +44 -45
  26. data/lib/core_process/cloud/process/external_network.rb +24 -28
  27. data/lib/core_process/cloud/process/flavor.rb +31 -34
  28. data/lib/core_process/cloud/process/images.rb +12 -15
  29. data/lib/core_process/cloud/process/internet_network.rb +13 -14
  30. data/lib/core_process/cloud/process/internet_server.rb +9 -10
  31. data/lib/core_process/cloud/process/keypairs.rb +34 -27
  32. data/lib/core_process/cloud/process/network.rb +21 -23
  33. data/lib/core_process/cloud/process/public_ip.rb +17 -18
  34. data/lib/core_process/cloud/process/router.rb +86 -92
  35. data/lib/core_process/cloud/process/rules.rb +30 -31
  36. data/lib/core_process/cloud/process/security_groups.rb +21 -22
  37. data/lib/core_process/cloud/process/server.rb +30 -31
  38. data/lib/core_process/cloud/process/server_log.rb +13 -14
  39. data/lib/core_process/cloud/process/subnetwork.rb +25 -40
  40. data/lib/logging.rb +4 -17
  41. data/lib/lorj/version.rb +1 -1
  42. data/lib/lorj.rb +2 -1
  43. data/lib/lorj_account.rb +137 -90
  44. data/lib/lorj_config.rb +13 -19
  45. data/lib/lorj_defaults.rb +46 -292
  46. data/lib/lorj_meta.rb +729 -0
  47. data/lib/prc.rb +119 -30
  48. data/lib/prc_base_config.rb +53 -47
  49. data/lib/prc_core_config.rb +837 -565
  50. data/lib/prc_section_config.rb +44 -16
  51. data/lib/providers/hpcloud/hpcloud.rb +1 -1
  52. data/lib/providers/openstack/openstack.rb +278 -21
  53. data/lib/providers/openstack/openstack_create.rb +205 -0
  54. data/lib/providers/openstack/openstack_delete.rb +28 -0
  55. data/lib/providers/openstack/openstack_get.rb +39 -0
  56. data/lib/providers/openstack/openstack_process.rb +26 -0
  57. data/lib/providers/openstack/openstack_query.rb +96 -0
  58. data/lib/providers/openstack/openstack_update.rb +35 -0
  59. data/lib/rh.rb +91 -6
  60. data/lorj-spec/defaults.yaml +18 -12
  61. data/lorj.gemspec +1 -0
  62. data/spec/01_hash_rh_spec.rb +41 -2
  63. data/spec/02_prc_base_config_spec.rb +1 -1
  64. data/spec/03_prc_section_config_spec.rb +1 -1
  65. data/spec/04_prc_core_config_spec.rb +148 -4
  66. data/spec/09_prc_spec.rb +104 -0
  67. data/spec/{00_lorj_log_spec.rb → 10_lorj_log_spec.rb} +23 -2
  68. data/spec/11_lorj_config_spec.rb +9 -27
  69. data/spec/12_lorj_account_spec.rb +36 -20
  70. data/spec/20_lorj_meta_spec.rb +271 -0
  71. data/spec/21_lorj_defaults_spec.rb +85 -0
  72. metadata +31 -4
@@ -18,45 +18,73 @@ require 'rubygems'
18
18
  require 'yaml'
19
19
 
20
20
  module PRC
21
- # SectionConfig class layer
21
+ # SectionConfig class layer based on BaseConfig.
22
+ #
23
+ # It supports a data_options :section for #[], #[]=, etc...
24
+ #
22
25
  class SectionConfig < PRC::BaseConfig
23
26
  # Get the value of a specific key under a section.
27
+ # You have to call #data_options(:section => 'MySection')
24
28
  #
25
29
  # * *Args* :
26
30
  # - +keys+ : keys to get values from a section set by data_options.
27
- # If section is set, it will use :default
31
+ # If section is not set, it will use :default
28
32
  # * *Returns* :
29
33
  # - key value.
30
34
  # * *Raises* :
31
35
  # Nothing
32
36
  def [](*keys)
33
37
  return nil if keys.length == 0
34
- return _get(:default, *keys) if @data_options[:section].nil?
35
- _get(@data_options[:section], *keys)
38
+ return p_get(:default, *keys) if @data_options[:section].nil?
39
+ p_get(@data_options[:section], *keys)
36
40
  end
37
41
 
42
+ # Set the value of a specific key under a section.
43
+ # You have to call #data_options(:section => 'MySection')
44
+ #
45
+ # * *Args* :
46
+ # - +keys+ : keys to get values from a section set by data_options.
47
+ # If section is not set, it will use :default
48
+ # * *Returns* :
49
+ # - key value.
50
+ # * *Raises* :
51
+ # Nothing
38
52
  def []=(*keys, value)
39
53
  return nil if keys.length == 0
40
- return _set(:default, *keys, value) if @data_options[:section].nil?
41
- _set(@data_options[:section], *keys, value)
54
+ return p_set(:default, *keys, value) if @data_options[:section].nil?
55
+ p_set(@data_options[:section], *keys, value)
42
56
  end
43
57
 
58
+ # Check key existence under a section.
59
+ # You have to call #data_options(:section => 'MySection')
60
+ #
61
+ # * *Args* :
62
+ # - +keys+ : keys to get values from a section set by data_options.
63
+ # If section is not set, it will use :default
64
+ # * *Returns* :
65
+ # - key value.
66
+ # * *Raises* :
67
+ # Nothing
44
68
  def exist?(*keys)
45
69
  return nil if keys.length == 0
46
- return _exist?(:default, *keys) if @data_options[:section].nil?
47
- _exist?(@data_options[:section], *keys)
48
- end
49
-
50
- def where?(*keys)
51
- return nil if keys.length == 0
52
- return _exist?(:default, *keys) if @data_options[:section].nil?
53
- _where?(@data_options[:section], *keys)
70
+ return p_exist?(:default, *keys) if @data_options[:section].nil?
71
+ p_exist?(@data_options[:section], *keys)
54
72
  end
55
73
 
74
+ # remove the key under a section.
75
+ # You have to call #data_options(:section => 'MySection')
76
+ #
77
+ # * *Args* :
78
+ # - +keys+ : keys to get values from a section set by data_options.
79
+ # If section is not set, it will use :default
80
+ # * *Returns* :
81
+ # - key value.
82
+ # * *Raises* :
83
+ # Nothing
56
84
  def del(*keys)
57
85
  return nil if keys.length == 0
58
- return _del(:default, *keys) if @data_options[:section].nil?
59
- _del(@data_options[:section], *keys)
86
+ return p_del(:default, *keys) if @data_options[:section].nil?
87
+ p_del(@data_options[:section], *keys)
60
88
  end
61
89
  end
62
90
  end
@@ -61,7 +61,7 @@ class Hpcloud
61
61
  # If the query is not push through and Hash object, the Provider
62
62
  # will needs to create his own mapping function.
63
63
  define_obj :network
64
- query_mapping :external, :router_external
64
+ def_attr_mapping :external, :router_external
65
65
 
66
66
  define_obj :rule
67
67
  obj_needs :data, :dir, :mapping => :direction
@@ -16,30 +16,287 @@
16
16
 
17
17
  # This class describes how to process some actions, and will do everything prior
18
18
  # this task to make it to work.
19
- class Openstack < BaseDefinition
20
- def initialize
21
- superclass.provides([:compute, :network])
19
+ require 'fog'
20
+ require 'uri'
21
+
22
+ hpcloud_path = File.expand_path(File.dirname(__FILE__))
23
+
24
+ require File.join(hpcloud_path, 'openstack_query.rb')
25
+ require File.join(hpcloud_path, 'openstack_get.rb')
26
+ require File.join(hpcloud_path, 'openstack_delete.rb')
27
+ require File.join(hpcloud_path, 'openstack_create.rb')
28
+ require File.join(hpcloud_path, 'openstack_update.rb')
29
+
30
+ # Defines Meta Openstack object
31
+ class Openstack
32
+ process_default :use_controller => true
33
+
34
+ define_obj :services
35
+ # Define Data used by service
36
+
37
+ obj_needs :data, :account_id, :mapping => :openstack_username
38
+ obj_needs :data, :account_key, :mapping => :openstack_api_key
39
+ obj_needs :data, :auth_uri, :mapping => :openstack_auth_uri
40
+ obj_needs :data, :tenant, :mapping => :openstack_tenant
41
+ obj_needs :data, ':excon_opts/:connect_timeout', :default_value => 30
42
+ obj_needs :data, ':excon_opts/:read_timeout', :default_value => 240
43
+ obj_needs :data, ':excon_opts/:write_timeout', :default_value => 240
44
+
45
+ define_obj :compute_connection
46
+ # Defines Data used by compute.
47
+
48
+ obj_needs :data, :account_id, :mapping => :openstack_username
49
+ obj_needs :data, :account_key, :mapping => :openstack_api_key,
50
+ :decrypt => true
51
+ obj_needs :data, :auth_uri, :mapping => :openstack_auth_url
52
+ obj_needs :data, :tenant, :mapping => :openstack_tenant
53
+ obj_needs :data, :compute, :mapping => :openstack_region
54
+
55
+ define_obj :network_connection
56
+ obj_needs :data, :account_id, :mapping => :openstack_username
57
+ obj_needs :data, :account_key, :mapping => :openstack_api_key,
58
+ :decrypt => true
59
+ obj_needs :data, :auth_uri, :mapping => :openstack_auth_url
60
+ obj_needs :data, :tenant, :mapping => :openstack_tenant
61
+ obj_needs :data, :network, :mapping => :openstack_region
62
+
63
+ # Openstack tenants object
64
+ define_obj(:tenants, :create_e => :openstack_get_tenant)
65
+ obj_needs :CloudObject, :compute_connection
66
+ obj_needs :data, :tenant
67
+
68
+ # Openstack Network
69
+ define_obj :network
70
+ def_hdata :network_name, :mapping => :name
71
+ def_attr_mapping :external, :router_external
72
+
73
+ define_obj :keypairs
74
+
75
+ undefine_attribute :id # Do not return any predefined ID
76
+
77
+ define_obj :server_log
78
+
79
+ # Excon::Response object type
80
+ def_attr_mapping :output, 'output'
81
+
82
+ define_obj :security_groups
83
+ # Added tenant data to add in queries.
84
+ obj_needs :CloudObject, :tenants
85
+
86
+ define_obj :rule
87
+ obj_needs :data, :dir, :mapping => :direction
88
+ attr_value_mapping :IN, 'ingress'
89
+ attr_value_mapping :OUT, 'egress'
90
+
91
+ obj_needs :data, :proto, :mapping => :protocol
92
+ obj_needs :data, :port_min, :mapping => :port_range_min
93
+ obj_needs :data, :port_max, :mapping => :port_range_max
94
+ obj_needs :data, :addr_map, :mapping => :remote_ip_prefix
95
+ obj_needs :data, :sg_id, :mapping => :security_group_id
96
+
97
+ def_attr_mapping :dir, :direction
98
+ def_attr_mapping :proto, :protocol
99
+ def_attr_mapping :port_min, :port_range_min
100
+ def_attr_mapping :port_max, :port_range_max
101
+ def_attr_mapping :addr_map, :remote_ip_prefix
102
+ def_attr_mapping :sg_id, :security_group_id
103
+
104
+ define_data(:account_id,
105
+ :account => true,
106
+ :desc => 'Openstack Username',
107
+ :validate => /^.+/
108
+ )
109
+
110
+ define_data(:account_key,
111
+ :account => true,
112
+ :desc => 'Openstack Password',
113
+ :validate => /^.+/
114
+ )
115
+ define_data(:auth_uri,
116
+ :account => true,
117
+ :explanation => "The authentication service is identified as '"\
118
+ "identity' under your horizon UI - Project/Compute then "\
119
+ 'Access & security.',
120
+ :desc => 'Openstack Authentication service URL. '\
121
+ 'Ex: https://mycloud:5000/v2.0/tokens',
122
+ :validate => %r{^http(s)?:\/\/.*\/tokens$}
123
+ )
124
+ define_data(:tenant,
125
+ :account => true,
126
+ :explanation => 'The Project name is shown from your horizon UI'\
127
+ ', on top left, close to the logo',
128
+ :desc => 'Openstack Tenant Name',
129
+ :validate => /^.+/
130
+ )
131
+
132
+ define_data(:compute,
133
+ :account => true,
134
+ :explanation => 'Depending on your installation, you may need to'\
135
+ ' provide a Region name. This information shown under your '\
136
+ 'horizon UI - close right to the project name (top left).'\
137
+ "\nIf there is no region shown, you can ignore it.",
138
+ :desc => 'Openstack Compute Region (Ex: regionOne)'
139
+ )
140
+
141
+ define_data(:network,
142
+ :account => true,
143
+ :desc => 'Openstack Network Region (Ex: regionOne)',
144
+ :explanation => 'Depending on your installation, you may need to'\
145
+ ' provide a Region name. This information shown under your '\
146
+ 'horizon UI - close right to the project name (top left).'\
147
+ "\nIf there is no region shown, you can ignore it."
148
+ )
149
+
150
+ define_obj :server
151
+ def_attr_mapping :status, :state
152
+ attr_value_mapping :create, 'BUILD'
153
+ attr_value_mapping :boot, :boot
154
+ attr_value_mapping :active, 'ACTIVE'
155
+ attr_value_mapping :active, 'ACTIVE'
156
+
157
+ def_attr_mapping :private_ip_address, :accessIPv4
158
+ def_attr_mapping :public_ip_address, :accessIPv4
159
+ def_attr_mapping :image_id, [:image, 'id']
160
+
161
+ define_obj :router
162
+ obj_needs_optional
163
+ obj_needs :data, :router_name, :mapping => :name
164
+
165
+ # The FORJ gateway_network_id is extracted
166
+ # from Fog::HP::Network::Router[:external_gateway_info][:network_id]
167
+
168
+ obj_needs :data,
169
+ :external_gateway_id,
170
+ :mapping => [:external_gateway_info, 'network_id']
171
+
172
+ def_attr_mapping :gateway_network_id, [:external_gateway_info, 'network_id']
173
+
174
+ # Port attributes used specifically by openstack fog API.
175
+ define_obj :port
176
+ def_attribute :device_owner
177
+ def_attribute :network_id
178
+
179
+ define_obj :public_ip
180
+ def_attr_mapping :server_id, :instance_id
181
+ def_attr_mapping :public_ip, :ip
182
+
183
+ define_obj :image
184
+ def_attr_mapping :image_name, :name
185
+ end
186
+
187
+ # Following class describe how FORJ should handle Openstack Cloud objects.
188
+ class OpenstackController
189
+ def self.def_cruds(*crud_types)
190
+ crud_types.each do |crud_type|
191
+ case crud_type
192
+ when :create, :delete
193
+ base_method(crud_type)
194
+ when :query, :get
195
+ query_method(crud_type)
196
+ when :update
197
+ update_method(crud_type)
198
+ end
199
+ end
200
+ end
201
+
202
+ def self.update_method(crud_type)
203
+ define_method(crud_type) do |sObjectType, obj, hParams|
204
+ method_name = "#{crud_type}_#{sObjectType}"
205
+ if self.class.method_defined? method_name
206
+ send(method_name, obj, hParams)
207
+ else
208
+ controller_error "'%s' is not a valid object for '%s'",
209
+ sObjectType, crud_type
210
+ end
211
+ end
22
212
  end
23
213
 
24
- def compute
25
- Fog::Compute.new(
26
- :provider => :openstack,
27
- :openstack_api_key => superclass.oForjAccount.get(:account_id),
28
- :openstack_username => superclass.oForjAccount.get(:account_key),
29
- :openstack_auth_url => superclass.oForjAccount.get(:auth_uri),
30
- :openstack_tenant => superclass.oForjAccount.get(:tenant_id),
31
- :openstack_region => superclass.oForjAccount.get(:compute)
32
- )
214
+ def self.query_method(crud_type)
215
+ define_method(crud_type) do |sObjectType, sCondition, hParams|
216
+ method_name = "#{crud_type}_#{sObjectType}"
217
+ if self.class.method_defined? method_name
218
+ send(method_name, hParams, sCondition)
219
+ else
220
+ controller_error "'%s' is not a valid object for '%s'",
221
+ sObjectType, crud_type
222
+ end
223
+ end
33
224
  end
34
225
 
35
- def network
36
- Fog::Network.new(
37
- :provider => :openstack,
38
- :openstack_api_key => superclass.oForjAccount.get(:account_id),
39
- :openstack_username => superclass.oForjAccount.get(:account_key),
40
- :openstack_auth_url => superclass.oForjAccount.get(:auth_uri),
41
- :openstack_tenant => superclass.oForjAccount.get(:tenant_id),
42
- :openstack_region => superclass.oForjAccount.get(:network)
43
- )
226
+ def self.base_method(crud_type)
227
+ define_method(crud_type) do |sObjectType, hParams|
228
+ method_name = "#{crud_type}_#{sObjectType}"
229
+ if self.class.method_defined? method_name
230
+ send(method_name, hParams)
231
+ else
232
+ controller_error "'%s' is not a valid object for '%s'",
233
+ sObjectType, crud_type
234
+ end
235
+ end
236
+ end
237
+
238
+ # Define the Openstack controller handlers
239
+ def_cruds :create, :delete, :get, :query, :update
240
+
241
+ def connect(sObjectType, hParams)
242
+ case sObjectType
243
+ when :services
244
+ # Fog use URI type for auth uri: URI.parse(:auth_uri)
245
+ # Convert openstack_auth_uri to type URI
246
+ hParams[:hdata][:openstack_auth_uri] =
247
+ URI.parse(hParams[:hdata][:openstack_auth_uri])
248
+ retrieve_result =
249
+ Fog::OpenStack.retrieve_tokens_v2(hParams[:hdata],
250
+ hParams[:excon_opts])
251
+ creds = format_retrieve_result(retrieve_result)
252
+ return creds
253
+ when :compute_connection
254
+ Fog::Compute.new(
255
+ hParams[:hdata].merge(:provider => :openstack)
256
+ )
257
+ when :network_connection
258
+ Fog::Network::OpenStack.new(hParams[:hdata])
259
+ else
260
+ controller_error "'%s' is not a valid object for 'connect'", sObjectType
261
+ end
262
+ end
263
+
264
+ def set_attr(oControlerObject, key, value)
265
+ if oControlerObject.is_a?(Excon::Response)
266
+ controller_error "No set feature for '%s'", oControlerObject.class
267
+ end
268
+
269
+ attributes = oControlerObject.attributes
270
+
271
+ controller_error "attribute '%s' is unknown in '%s'. Valid one are : '%s'",
272
+ key[0],
273
+ oControlerObject.class,
274
+ oControlerObject.class.attributes unless
275
+ oControlerObject.class.attributes.include?(key[0])
276
+
277
+ attributes.rh_set(value, key)
278
+ rescue => e
279
+ controller_error "Unable to map '%s' on '%s'. %s",
280
+ key, oControlerObject, e.message
281
+ end
282
+
283
+ def get_attr(oControlerObject, key)
284
+ if oControlerObject.is_a?(Excon::Response)
285
+ oControlerObject.data.rh_get(:body, key)
286
+ else
287
+ attributes = oControlerObject.attributes
288
+ controller_error "attribute '%s' is unknown in '%s'."\
289
+ " Valid one are : '%s'",
290
+ key[0],
291
+ oControlerObject.class,
292
+ oControlerObject.class.attributes unless
293
+ oControlerObject.class.attributes.include?(key[0])
294
+
295
+ return attributes.rh_get(key) if attributes.rh_exist?(key)
296
+ return oControlerObject.send(key[0]) if key.length == 1
297
+ oControlerObject.send(key[0]).rh_get(key[1..-1])
298
+ end
299
+ rescue => e
300
+ controller_error "==>Unable to map '%s'. %s", key, e.message
44
301
  end
45
302
  end
@@ -0,0 +1,205 @@
1
+ # encoding: UTF-8
2
+
3
+ # (c) Copyright 2014 Hewlett-Packard Development Company, L.P.
4
+ #
5
+ # Licensed under the Apache License, Version 2.0 (the "License");
6
+ # you may not use this file except in compliance with the License.
7
+ # You may obtain a copy of the License at
8
+ #
9
+ # http://www.apache.org/licenses/LICENSE-2.0
10
+ #
11
+ # Unless required by applicable law or agreed to in writing, software
12
+ # distributed under the License is distributed on an "AS IS" BASIS,
13
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
+ # See the License for the specific language governing permissions and
15
+ # limitations under the License.
16
+
17
+ # Defined Openstack object create.
18
+ class OpenstackController
19
+ def create_security_groups(hParams)
20
+ required?(hParams, :network_connection)
21
+ required?(hParams, :tenants)
22
+ required?(hParams, :security_group)
23
+
24
+ service = hParams[:network_connection]
25
+
26
+ service.security_groups.create(:name => hParams[:security_group],
27
+ :tenant_id => hParams[:tenants].id)
28
+ end
29
+
30
+ def create_network(hParams)
31
+ required?(hParams, :network_connection)
32
+ required?(hParams, :network_name)
33
+
34
+ hParams[:network_connection].networks.create(hParams[:hdata])
35
+ end
36
+
37
+ def create_subnetwork(hParams)
38
+ required?(hParams, :network_connection)
39
+ required?(hParams, :network)
40
+
41
+ netconn = hParams[:network_connection]
42
+ netconn.subnets.create(
43
+ :network_id => hParams[:network].id,
44
+ :name => hParams[:subnetwork_name],
45
+ :cidr => get_next_subnet(netconn),
46
+ :ip_version => '4'
47
+ )
48
+ end
49
+
50
+ def create_rule(hParams)
51
+ required?(hParams, :network_connection)
52
+ required?(hParams, :security_groups)
53
+ hParams[:network_connection].security_group_rules.create(hParams[:hdata])
54
+ end
55
+
56
+ def create_router(hParams)
57
+ required?(hParams, :network_connection)
58
+ required?(hParams, :router_name)
59
+
60
+ # Forcelly used admin_status_up to true. Coming from HPCloud.
61
+ # But not sure if we need it or not.
62
+ # hParams[:hdata] = hParams[:hdata].merge(:admin_state_up => true)
63
+
64
+ hParams[:network_connection].routers.create(hParams[:hdata])
65
+ end
66
+
67
+ def create_router_interface(hParams)
68
+ required?(hParams, :network_connection)
69
+ required?(hParams, :router)
70
+ required?(hParams, :subnetwork)
71
+
72
+ service = hParams[:network_connection]
73
+ router = hParams[:router]
74
+ result = service.add_router_interface(router.id, hParams[:subnetwork].id)
75
+ fail if result.status != 200
76
+ result
77
+ end
78
+
79
+ def create_keypairs(hParams)
80
+ required?(hParams, :compute_connection)
81
+ required?(hParams, :keypair_name)
82
+ required?(hParams, :public_key)
83
+
84
+ # API:
85
+ # https://github.com/fog/fog/blob/master/lib/fog/openstack/docs/compute.md
86
+ service = hParams[:compute_connection]
87
+ service.key_pairs.create(:name => hParams[:keypair_name],
88
+ :public_key => hParams[:public_key])
89
+ end
90
+
91
+ def create_server(hParams)
92
+ [:compute_connection, :image,
93
+ :network, :flavor, :keypairs,
94
+ :security_groups, :server_name].each do |required_param|
95
+ required?(hParams, required_param)
96
+ end
97
+
98
+ options = {
99
+ :name => hParams[:server_name],
100
+ :flavor_ref => hParams[:flavor].id,
101
+ :image_ref => hParams[:image].id,
102
+ :key_name => hParams[:keypairs].name,
103
+ :security_groups => [hParams[:security_groups].name],
104
+ :nics => [{ :net_id => hParams[:network].id }]
105
+ }
106
+
107
+ if hParams[:user_data]
108
+ options[:user_data_encoded] =
109
+ Base64.strict_encode64(hParams[:user_data])
110
+ end
111
+ options[:metadata] = hParams[:meta_data] if hParams[:meta_data]
112
+
113
+ compute_connect = hParams[:compute_connection]
114
+
115
+ server = compute_connect.servers.create(options)
116
+ compute_connect.servers.get(server.id) if server
117
+ end
118
+
119
+ def create_public_ip(hParams)
120
+ required?(hParams, :compute_connection)
121
+ required?(hParams, :server)
122
+
123
+ compute_connect = hParams[:compute_connection]
124
+ server = hParams[:server]
125
+
126
+ while server.state != 'ACTIVE'
127
+ sleep(5)
128
+ server = compute_connect.servers.get(server.id)
129
+ end
130
+
131
+ addresses = compute_connect.addresses.all
132
+ address = nil
133
+ # Search for an available IP
134
+ addresses.each do |elem|
135
+ if elem.fixed_ip.nil?
136
+ address = elem
137
+ break
138
+ end
139
+ end
140
+
141
+ address = allocate_new_ip(compute_connect) if address.nil?
142
+ if address.nil?
143
+ controller_error("No Public IP to assign to server '%s'", server.name)
144
+ end
145
+
146
+ address.server = server # associate the server
147
+ address.reload
148
+ # This function needs to returns a list of object.
149
+ # This list must support the each function.
150
+ address
151
+ end
152
+
153
+ def allocate_new_ip(compute_connect)
154
+ # Create a new public IP to add in the pool.
155
+ pools = compute_connect.addresses.get_address_pools
156
+ controller_error('No IP Pool found') if pools.length == 0
157
+ # TODO: Be able to support choice of pool at setup time.
158
+ if pools.length > 1
159
+ Lorj.warning('Several pools found. Selecting the first one.')
160
+ end
161
+ compute_connect.addresses.create 'pool' => pools[0]['name']
162
+ end
163
+
164
+ def get_next_subnet(oNetworkConnect)
165
+ subnet_values = []
166
+ subnets = oNetworkConnect.subnets.all
167
+
168
+ subnets.each do|s|
169
+ subnet_values.push(s.cidr)
170
+ end
171
+
172
+ gap = false
173
+ count = 0
174
+ range_used = []
175
+ new_subnet = 0
176
+ new_cidr = ''
177
+
178
+ subnet_values = subnet_values.sort!
179
+
180
+ subnet_values.each do|value|
181
+ range_used.push(value[5])
182
+ end
183
+
184
+ range_used.each do |n|
185
+ if count.to_i == n.to_i
186
+ else
187
+ new_subnet = count
188
+ gap = true
189
+ break
190
+ end
191
+ count += 1
192
+ end
193
+
194
+ if gap
195
+ new_cidr = format('10.0.%s.0/24', count)
196
+ else
197
+ max_value = range_used.max
198
+ new_subnet = max_value.to_i + 1
199
+ new_cidr = format('10.0.%s.0/24', new_subnet)
200
+ end
201
+ new_cidr
202
+ rescue => e
203
+ Logging.error("%s\n%s", e.message, e.backtrace.join("\n"))
204
+ end
205
+ end
@@ -0,0 +1,28 @@
1
+ # encoding: UTF-8
2
+
3
+ # (c) Copyright 2014 Hewlett-Packard Development Company, L.P.
4
+ #
5
+ # Licensed under the Apache License, Version 2.0 (the "License");
6
+ # you may not use this file except in compliance with the License.
7
+ # You may obtain a copy of the License at
8
+ #
9
+ # http://www.apache.org/licenses/LICENSE-2.0
10
+ #
11
+ # Unless required by applicable law or agreed to in writing, software
12
+ # distributed under the License is distributed on an "AS IS" BASIS,
13
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
+ # See the License for the specific language governing permissions and
15
+ # limitations under the License.
16
+
17
+ # Defined Openstack object delete.
18
+ class OpenstackController
19
+ def delete_server(hParams)
20
+ required?(hParams, :compute_connection)
21
+ required?(hParams, :server)
22
+
23
+ compute_connect = hParams[:compute_connection]
24
+ server = hParams[:server]
25
+
26
+ compute_connect.servers.get(server.id).destroy
27
+ end
28
+ end
@@ -0,0 +1,39 @@
1
+ # encoding: UTF-8
2
+
3
+ # (c) Copyright 2014 Hewlett-Packard Development Company, L.P.
4
+ #
5
+ # Licensed under the Apache License, Version 2.0 (the "License");
6
+ # you may not use this file except in compliance with the License.
7
+ # You may obtain a copy of the License at
8
+ #
9
+ # http://www.apache.org/licenses/LICENSE-2.0
10
+ #
11
+ # Unless required by applicable law or agreed to in writing, software
12
+ # distributed under the License is distributed on an "AS IS" BASIS,
13
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
+ # See the License for the specific language governing permissions and
15
+ # limitations under the License.
16
+
17
+ # Defined Openstack object get.
18
+ class OpenstackController
19
+ def self.def_get(connection, name, property_name = nil)
20
+ property_name = property_name.nil? ? "#{name}s" : property_name.to_s
21
+ define_method("get_#{name}") do |hParams, sUniqId|
22
+ required?(hParams, connection)
23
+ hParams[connection].send(property_name).get(sUniqId)
24
+ end
25
+ end
26
+
27
+ def_get :compute_connection, :server
28
+
29
+ def_get :compute_connection, :image
30
+
31
+ def_get :network_connection, :network
32
+
33
+ def_get :compute_connection, :keypairs, :key_pairs
34
+
35
+ def get_server_log(hParams, sUniqId)
36
+ required?(hParams, :server)
37
+ hParams[:server].console(sUniqId)
38
+ end
39
+ end