forj 0.0.34 → 0.0.35

Sign up to get free protection for your applications and to get access to all the features.
data/lib/forj-config.rb CHANGED
@@ -21,8 +21,8 @@
21
21
  require 'rubygems'
22
22
  require 'yaml'
23
23
 
24
- require_relative 'log.rb'
25
- include Logging
24
+ #require_relative 'log.rb'
25
+ #include Logging
26
26
 
27
27
  class ForjDefault
28
28
 
@@ -38,6 +38,8 @@ class ForjDefault
38
38
  if not $LIB_PATH
39
39
  raise 'Internal $LIB_PATH was not set.'
40
40
  end
41
+
42
+ Logging.info ('Reading default configuration...')
41
43
 
42
44
  @sDefaultsName=File.join($LIB_PATH,'defaults.yaml')
43
45
 
@@ -50,10 +52,10 @@ class ForjConfig
50
52
 
51
53
  # Internal variables:
52
54
  # @sConfigName='config.yaml'
55
+ # @yRuntime = data in memory.
53
56
  # @yLocal = config.yaml file data hash.
54
57
  # @yConfig = defaults.yaml + local_config data hash
55
58
 
56
-
57
59
  attr_reader :yLocal
58
60
  attr_reader :yConfig
59
61
  attr_reader :sConfigName
@@ -69,14 +71,13 @@ class ForjConfig
69
71
 
70
72
  sConfigDefaultName='config.yaml'
71
73
 
72
- # binding.pry
73
74
  if sConfigName
74
75
  if File.dirname(sConfigName) == '.'
75
76
  sConfigName= File.join($FORJ_DATA_PATH,sConfigName)
76
77
  end
77
78
  sConfigName = File.expand_path(sConfigName)
78
79
  if not File.exists?(sConfigName)
79
- Logging.error('Config file %s doesn\'t exists. Using default one.')
80
+ Logging.warning("Config file '%s' doesn't exists. Using default one." % [sConfigName] )
80
81
  @sConfigName=File.join($FORJ_DATA_PATH,sConfigDefaultName)
81
82
  else
82
83
  @sConfigName=sConfigName
@@ -98,12 +99,14 @@ class ForjConfig
98
99
  if not File.exists?($FORJ_DATA_PATH)
99
100
  Dir.mkdir($FORJ_DATA_PATH)
100
101
  end
101
- puts ('INFO: Creating your default configuration file ...')
102
+ Logging.info ('Creating your default configuration file ...')
102
103
  self.SaveConfig()
103
104
  end
104
105
  end
105
106
 
106
107
  BuildConfig()
108
+
109
+ @yRuntime={}
107
110
  end
108
111
 
109
112
 
@@ -113,14 +116,14 @@ class ForjConfig
113
116
  YAML.dump(@yLocal, out)
114
117
  end
115
118
  rescue => e
116
- Logging.error(e.message)
119
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
117
120
  return false
118
121
  end
119
- # puts ('INFO: Configuration file "%s" updated.' % @sConfigName)
122
+ Logging.info ('Configuration file "%s" updated.' % @sConfigName)
120
123
  return true
121
124
  end
122
125
 
123
- def ConfigSet(key, value, section = 'default')
126
+ def LocalSet(key, value, section = 'default')
124
127
  if not key or not value
125
128
  return false
126
129
  end
@@ -136,7 +139,7 @@ class ForjConfig
136
139
  return true
137
140
  end
138
141
 
139
- def ConfigDel(key,section = 'default')
142
+ def LocalDel(key,section = 'default')
140
143
  if not key
141
144
  return false
142
145
  end
@@ -148,6 +151,35 @@ class ForjConfig
148
151
  return true
149
152
  end
150
153
 
154
+ def setDefault(key, value)
155
+ if not key
156
+ return false
157
+ end
158
+ if not @yRuntime[key]
159
+ @yRuntime[key] = value
160
+ end
161
+ return true
162
+ end
163
+
164
+ def set(key, value)
165
+ if not key
166
+ return false
167
+ end
168
+ if value
169
+ @yRuntime[key] = value
170
+ else
171
+ @yRuntime.delete(key)
172
+ end
173
+ return true
174
+ end
175
+
176
+ def get(key, default = @yConfig['default'][key])
177
+ if @yRuntime.has_key?(key)
178
+ @yRuntime[key]
179
+ else
180
+ default
181
+ end
182
+ end
151
183
 
152
184
  def BuildConfig()
153
185
  # This function implements the logic to get defaults, superseed by local config.
data/lib/log.rb CHANGED
@@ -26,41 +26,140 @@ require 'require_relative'
26
26
  require_relative 'helpers.rb'
27
27
  include Helpers
28
28
 
29
+
29
30
  #
30
31
  # Logging module
31
32
  #
32
33
  module Logging
33
- def info(message)
34
- home = Helpers.get_home_path
35
- d = '%s/.forj/' % [home]
36
- Helpers.create_directory(d)
37
-
38
- log = '%s/.forj/forj.log' % [home]
39
- log = Logger.new(log)
40
- log.level = Logger::DEBUG
41
34
 
42
- log.formatter = proc do |severity, datetime, progname, msg|
43
- "#{progname} : #{datetime}: #{severity}: #{msg} \n"
35
+ class SSLErrorMgt
36
+
37
+ def initialize()
38
+ @iRetry=0
39
+ end
40
+
41
+ def ErrorDetected(message,backtrace)
42
+ if message.match('SSLv2/v3 read server hello A: unknown protocol')
43
+ if @iRetry <5
44
+ sleep(2)
45
+ @iRetry+=1
46
+ print "%s/5 try...\r" % @iRetry if $FORJ_LOGGER.level == 0
47
+ return false
48
+ else
49
+ Logging.error('Too many retry. %s' % message)
50
+ return true
51
+ end
52
+ else
53
+ Logging.error("%s\n%s" % [message,backtrace.join("\n")])
54
+ return true
55
+ end
44
56
  end
45
57
 
46
- log.info(message)
58
+ end
59
+
60
+ class ForjLog
61
+ # Class used to create 2 log object, in order to keep track of error in a log file and change log output to OUTPUT on needs (option flags).
62
+
63
+ attr_reader :level
64
+
65
+ def initialize(sLogFile = 'forj.log', level = Logger::WARN)
66
+ if not $FORJ_DATA_PATH
67
+ raise "Internal Error: Unable to initialize ForjLog - global FORJ_DATA_PATH not set"
68
+ end
69
+ @oFileLogger = Logger.new(File.join($FORJ_DATA_PATH, sLogFile), 'weekly')
70
+ @oFileLogger.level = Logger::DEBUG
71
+ @oFileLogger.formatter = proc do |severity, datetime, progname, msg|
72
+ "#{progname} : #{datetime}: #{severity}: #{msg} \n"
73
+ end
74
+
75
+ @oOutLogger = Logger.new(STDOUT)
76
+ @level = level
77
+ @oOutLogger.level = @level
78
+ @oOutLogger.formatter = proc do |severity, datetime, progname, msg|
79
+ severity == 'ANY'?"#{msg} \n":"#{severity}: #{msg} \n"
80
+ end
81
+ end
82
+
83
+ def info?
84
+ return(@oOutLogger.info?)
85
+ end
86
+ def debug?
87
+ return(@oOutLogger.debug?)
88
+ end
89
+ def error?
90
+ return(@oOutLogger.error?)
91
+ end
92
+ def fatal?
93
+ return(@oOutLogger.fatal?)
94
+ end
95
+
96
+ def info(message)
97
+ @oOutLogger.info(message + ANSI.clear_line)
98
+ @oFileLogger.info(message)
99
+ end
100
+ def debug(message)
101
+ @oOutLogger.debug(message + ANSI.clear_line)
102
+ @oFileLogger.debug(message)
103
+ end
104
+ def error(message)
105
+ @oOutLogger.error(message + ANSI.clear_line)
106
+ @oFileLogger.error(message)
107
+ end
108
+ def fatal(message)
109
+ @oOutLogger.fatal(message + ANSI.clear_line)
110
+ @oFileLogger.fatal(message)
111
+ end
112
+
113
+ def warn(message)
114
+ @oOutLogger.warn(message + ANSI.clear_line)
115
+ @oFileLogger.warn(message)
116
+ end
117
+
118
+ def set_level(level)
119
+ @level = level
120
+ @oOutLogger.level = level
121
+ end
122
+
123
+ def unknown(message)
124
+ @oOutLogger.unknown(message + ANSI.clear_line)
125
+ end
126
+
127
+ end
128
+
129
+ def message(message)
130
+ $FORJ_LOGGER.unknown(message)
131
+ end
132
+
133
+ def info(message)
134
+ $FORJ_LOGGER.info(message)
135
+ end
136
+
137
+ def debug(message)
138
+ $FORJ_LOGGER.debug(message)
139
+ end
140
+
141
+ def warning(message)
142
+ $FORJ_LOGGER.warn(message)
47
143
  end
48
144
 
49
145
  def error(message)
50
- home = Helpers.get_home_path
51
- d = '%s/.forj/' % [home]
52
- Helpers.create_directory(d)
53
-
54
- log = '%s/.forj/forj.log' % [home]
55
- log = Logger.new(log)
56
- log.level = Logger::ERROR
57
-
58
- log.formatter = proc do |severity, datetime, progname, msg|
59
- "#{progname} : #{datetime}: #{severity}: #{msg} \n"
60
- end
146
+ $FORJ_LOGGER.error(message)
147
+ end
148
+
149
+ def fatal(rc, message)
150
+ $FORJ_LOGGER.fatal(message)
151
+ puts 'Issues found. Please fix it and retry. Process aborted.'
152
+ exit rc
153
+ end
61
154
 
62
- log.error(message)
155
+ def set_level(level)
156
+ $FORJ_LOGGER.set_level(level)
63
157
  end
64
- end
158
+
159
+ def state(message)
160
+ print("%s%s ...\r" % [message, ANSI.clear_line]) if $FORJ_LOGGER.level == Logger::INFO
161
+ end
162
+
65
163
 
66
164
 
165
+ end
data/lib/network.rb CHANGED
@@ -19,149 +19,311 @@ require 'rubygems'
19
19
  require 'require_relative'
20
20
 
21
21
  require_relative 'connection.rb'
22
- include Connection
23
- require_relative 'log.rb'
24
- include Logging
22
+
25
23
 
26
24
  #
27
25
  # Network module
28
26
  #
29
27
  module Network
30
- def get_or_create_network(name)
31
- network = get_network(name)
32
- if network == nil
33
- network = create_network(name)
28
+
29
+ # Network management
30
+ def get_or_create_network(oFC, name)
31
+ Logging.state("Searching for network '%s'" % [name])
32
+ network = get_network(oFC, name)
33
+ if not network
34
+ network = create_network(oFC, name)
34
35
  end
35
36
  network
36
37
  end
37
38
 
38
- def get_network(name)
39
+ def get_network(oFC, name)
39
40
  begin
40
- info = 'getting network %s' % [name]
41
- Logging.info(info)
42
- Connection.network.networks.all(:name => name)[0]
41
+ networks = oFC.oNetwork.networks.all(:name => name)
42
+ case networks.length()
43
+ when 0
44
+ Logging.debug("No network found")
45
+ nil
46
+ when 1
47
+ Logging.debug("Found network '%s'" % [networks[0].name])
48
+ networks[0]
49
+ else
50
+ Logging.warning("Several network was found with '%s'. Selecting the first one '%s'." % [name, networks[0].name])
51
+ networks[0]
52
+ end
43
53
  rescue => e
44
- puts e.message
45
- Logging.error(e.message)
54
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
46
55
  end
47
56
  end
48
57
 
49
- def create_network(name)
58
+ def create_network(oFC, name)
50
59
  begin
51
- info = 'creating network %s' % [name]
52
- Logging.info(info)
53
- Connection.network.networks.create(:name => name)
60
+ Logging.debug('creating network %s' % [name])
61
+ oFC.oNetwork.networks.create(:name => name)
54
62
  rescue => e
55
- Logging.error(e.message)
63
+ Logging.fatal(1, "%s\n%s" % [e.inspect, e.message])
56
64
  end
57
65
  end
58
66
 
59
- def delete_network(network_name)
67
+ def delete_network(oFC, network_name)
60
68
  begin
61
- network = get_network(network_name)
62
- Connection.network.networks.get(network.id).destroy
69
+ network = get_network(oFC, network_name)
70
+ oFC.oNetwork.networks.get(network.id).destroy
63
71
  rescue => e
64
- Logging.error(e.message)
72
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
65
73
  end
66
74
  end
67
75
 
68
- def get_or_create_subnet(network_id, name)
76
+
77
+ # Subnet management
78
+ def get_or_create_subnet(oFC, network_id, name)
79
+ Logging.state("Searching for sub-network attached '%s'." % [name])
69
80
  begin
70
- subnet = get_subnet(name)
71
- if subnet == nil
72
- subnet = create_subnet(network_id, name)
73
- end
74
- subnet
81
+ subnets = oFC.oNetwork.subnets.all(:network_id => network_id)
75
82
  rescue => e
76
- Logging.error(e.message)
83
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
84
+ end
85
+ if subnets
86
+ case subnets.length()
87
+ when 0
88
+ Logging.debug("No subnet found from '%s' network" % [name])
89
+ subnet = nil
90
+ when 1
91
+ Logging.debug("Found '%s' subnet from '%s' network" % [subnets[0].name, name])
92
+ subnet = subnets[0]
93
+ else
94
+ Logging.warning("Several subnet was found on '%s'. Choosing the first one = '%s'" % [name, subnets[0].name])
95
+ subnet = subnets[0]
96
+ end
97
+ end
98
+ if not subnet
99
+ # Create the subnet with 'sub-' prefixing the network name.
100
+ begin
101
+ subnet = create_subnet(oFC, network_id, 'sub-%s' % [name])
102
+ rescue => e
103
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
104
+ end
77
105
  end
106
+ return subnet
78
107
  end
79
108
 
80
- def create_subnet(network_id, name)
109
+ def create_subnet(oFC, network_id, name)
110
+ Logging.debug("Creating subnet '%s'" % [name])
81
111
  begin
82
- Connection.network.subnets.create(
112
+ oFC.oNetwork.subnets.create(
83
113
  :network_id => network_id,
84
114
  :name => name,
85
- :cidr => get_next_subnet,
115
+ :cidr => get_next_subnet(oFC),
86
116
  :ip_version => '4'
87
117
  )
88
118
  rescue => e
89
- Logging.error(e.message)
119
+ Logging.fatal(1, "%s\n%s" % [e.class.name, e.message])
90
120
  end
91
121
  end
92
122
 
93
- def delete_subnet(subnet_id)
123
+ def delete_subnet(oFC, subnet)
124
+ Logging.debug("Deleting subnet '%s'" % [subnet.name])
94
125
  begin
95
- Connection.network.subnets.get(subnet_id).destroy
126
+ oFC.oNetwork.subnets.get(subnet.id).destroy
96
127
  rescue => e
97
- Logging.error(e.message)
128
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
98
129
  end
99
130
  end
100
131
 
101
- def get_subnet(name)
132
+ def get_subnet(oFC, name)
102
133
  begin
103
- Connection.network.subnets.all(:name => name)[0]
134
+ oFC.oNetwork.subnets.all(:name => name)[0]
104
135
  rescue => e
105
- Logging.error(e.message)
136
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
106
137
  end
107
138
  end
108
139
 
109
- def get_router(name)
110
- begin
111
- routers = Connection.network.routers.all({:name => name})
112
- router = nil
113
140
 
114
- routers.each do|r|
115
- router = r
141
+ # Router management
142
+ def get_or_create_router(oFC, network, subnet)
143
+ port = get_router_interface_attached(oFC, network)
144
+ if not port
145
+ # Trying to get router
146
+ router = get_router(oFC, 'router-%s' % network.name)
147
+ router = create_router(oFC, 'router-%s' % network.name) if not router
148
+ create_router_interface(subnet, router) if router
149
+ else
150
+ routers = oFC.oNetwork.routers.all({:id => port.device_id})
151
+ if routers.length() == 1
152
+ if routers[0].external_gateway_info
153
+ Logging.debug("Found router '%s' attached to an external gateway." % [ routers[0].name ] )
154
+ else
155
+ Logging.debug("Found router '%s' but need to be attached to an external gateway. Attaching..." % [ routers[0].name ] )
156
+ netty=search_gateway(oFC)
157
+ if netty
158
+ routers[0].external_gateway_info = { 'network_id' => netty.id }
159
+ routers[0].save
160
+ Logging.debug("Router '%s' attached to the external network '%s'." % [ routers[0].name, netty.name ] )
161
+ else
162
+ Logging.fatal(1, "Unable to attach router '%s' to an external gateway. Required for boxes to get internet access. " % [ routers[0].name ] )
163
+ end
164
+ end
165
+ router = routers[0]
166
+ else
167
+ Logging.warning("Unable to found the router id '%s'" % [ port.device_id ])
168
+ router = nil
169
+ end
170
+ end
171
+ router
172
+ end
173
+
174
+ def get_router(oFC, name)
175
+ Logging.state("Searching for router '%s'..." % [name] )
176
+ begin
177
+ routers = oFC.oNetwork.routers.all({:name => name})
178
+ if routers.length() == 1
179
+ if routers[0].external_gateway_info.has_key?('id')
180
+ Logging.debug("Found router '%s' attached to an external gateway." % [ routers[0].name ] )
181
+ else
182
+ Logging.warning("Found router '%s' but not attached to an external." % [ routers[0].name ] )
183
+ end
184
+ routers[0]
185
+ else
186
+ Logging.debug("Router '%s' not found." % [ name ] )
187
+ nil
116
188
  end
189
+ rescue => e
190
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
191
+ end
192
+ end
117
193
 
118
- router
194
+ def create_router(oFC, name)
195
+
196
+ netty = search_gateway(oFC)
197
+
198
+ begin
199
+ if netty
200
+ Logging.debug("Creating router '%s' attached to the external Network '%s'." % [name, netty.name])
201
+ oFC.oNetwork.routers.create(
202
+ :name => name,
203
+ :admin_state_up => true,
204
+ :external_gateway_info => { 'network_id' => netty.id }
205
+ )
206
+ else
207
+ Logging.debug("Creating router '%s' without external Network." % [name])
208
+ oFC.oNetwork.routers.create(
209
+ :name => name,
210
+ :admin_state_up => true
211
+ )
212
+ end
119
213
  rescue => e
120
- Logging.error(e.message)
214
+ Logging.fatal(1, "%s\n%s" % [e.inspect, e.message])
121
215
  end
122
216
  end
123
217
 
124
- def create_router_interface(subnet_id, router)
218
+ def delete_router(oFC, router_id)
219
+ Logging.debug("Deleting router '%s'" % [router.name])
125
220
  begin
126
- router.add_interface(subnet_id, nil)
221
+ oFC.oNetwork.routers.get(router.id).destroy
127
222
  rescue => e
128
- Logging.error(e.message)
223
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
224
+ end
225
+ end
226
+
227
+
228
+ # Router interface to connect to the network
229
+ def create_router_interface(subnet, router)
230
+ raise "Internal Error: subnet/router object not passed." if not subnet or not router
231
+
232
+ Logging.debug("Attaching subnet '%s' to router '%s'" % [subnet.name, router.name])
233
+ begin
234
+ router.add_interface(subnet.id, nil)
235
+ rescue => e
236
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
129
237
  end
130
238
  end
131
239
 
132
240
  def delete_router_interface(subnet_id, router)
241
+ Logging.debug("Removing subnet '%s' from router '%s'" % [subnet.name, router.name])
133
242
  begin
134
243
  router.remove_interface(subnet_id)
135
244
  rescue => e
136
- Logging.error(e.message)
245
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
137
246
  end
138
247
  end
139
-
140
- def create_router(name)
248
+
249
+ def get_router_interface(oFC, network_id, device_id)
141
250
  begin
142
- Connection.network.routers.create(
143
- :name => name,
144
- :admin_state_up => true
145
- )
251
+ # Searching for router port attached
252
+ ports=oFC.oNetwork.ports.all({:network_id => network_id, :device_id => device_id})
253
+ case ports.length()
254
+ when 0
255
+ nil
256
+ else
257
+ port[0]
258
+ end
146
259
  rescue => e
147
- Logging.error(e.message)
260
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
148
261
  end
149
262
  end
150
263
 
151
- def delete_router(router_id)
264
+ def get_router_interface_attached(oFC, network)
265
+ Logging.state("Searching for router port attached to the network '%s'" % [network.name] )
152
266
  begin
153
- Connection.network.routers.get(router_id).destroy
267
+ # Searching for router port attached
268
+ ports=oFC.oNetwork.ports.all({:network_id => network.id, :device_type => 'network:router_interface'})
269
+ case ports.length()
270
+ when 0
271
+ Logging.debug("No router port attached to the network '%s'" % [network.name] )
272
+ nil
273
+ else
274
+ Logging.debug("Found a router port attached to the network '%s' " % [network.name] )
275
+ ports[0]
276
+ end
154
277
  rescue => e
155
- Logging.error(e.message)
278
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
156
279
  end
157
280
  end
281
+
282
+ # Gateway management
283
+ def get_gateway(oFC, name)
284
+
285
+ return nil if not name or not oFC
286
+
287
+ Logging.state("Getting gateway '%s'" % [name])
288
+ networks = oFC.oNetwork
289
+ begin
290
+ netty = networks.get(name)
291
+ rescue => e
292
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
293
+ end
294
+ Logging.state("Found gateway '%s'" % [name]) if netty
295
+ Logging.state("Unable to found gateway '%s'" % [name]) if not netty
296
+ return netty
297
+ end
298
+
299
+ def search_gateway(oFC)
300
+ Logging.state("Identifying External gateway ...")
301
+ begin
302
+ # Searching for router port attached
303
+ networks=oFC.oNetwork.networks.all({ :router_external => true })
304
+ case networks.length()
305
+ when 0
306
+ Logging.debug("No external network")
307
+ nil
308
+ when 1
309
+ Logging.debug("Found external network '%s'." % [networks[0].name] )
310
+ networks[0]
311
+ else
312
+ Logging.debug("Found several external networks. Selecting the first one '%s'" % [networks[0].name] )
313
+ networks[0]
314
+ end
315
+ rescue => e
316
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
317
+ end
318
+ end
319
+
158
320
  end
159
321
 
160
322
 
161
- def get_next_subnet
323
+ def get_next_subnet(oFC)
162
324
  begin
163
325
  subnet_values = Array.new
164
- subnets = Connection.network.subnets.all
326
+ subnets = oFC.oNetwork.subnets.all
165
327
 
166
328
  subnets.each do|s|
167
329
  subnet_values.push(s.cidr)
@@ -198,6 +360,6 @@ def get_next_subnet
198
360
  end
199
361
  new_cidr
200
362
  rescue => e
201
- Logging.error(e.message)
363
+ Logging.error("%s\n%s" % [e.message, e.backtrace.join("\n")])
202
364
  end
203
365
  end