corl 0.5.15 → 0.5.16

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: c360e505e5eaa8bdea103dad27a7868f06655153
4
- data.tar.gz: 8cf2016ccc74e060bfa91372e7b54481b1a06a83
3
+ metadata.gz: 6525066ff89087597683642d763aaf33dc8d4f30
4
+ data.tar.gz: 4d6ffa51014c3f8316a118ef6f5b8476da2e0b0b
5
5
  SHA512:
6
- metadata.gz: f16e3bfa746c95710bd6e6b5aa0374e0de28ff8fe98374d76f237b74dbc9fdc341cc7880fbf5e4a5504122f739a7b337b19224340377e5f25d130acb01606ee3
7
- data.tar.gz: f4e9f8fe0ca6e9478ae96018b346fcbb5ae509d10de97146cae1520b18787ec16ec673fa0f4ab46de9c795b0b3354abd4fff4a4ce36dc719b040e938382b6214
6
+ metadata.gz: 668c3569ee4d16da744d12da994f72565fa0b01b90c254359b5315fe28c7d5d313d351b8d3e061d45b5cfd3e316aed13522da50812aab605ba2774c6de72dee2
7
+ data.tar.gz: b4b76ae9c30d0993a305ce6f872159861bdbd898763f66bb614a20d16def26556e1feb717050834fa13bf63d4cc01f080794f6c3a45acc53b27aafc213ccf636
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.5.15
1
+ 0.5.16
@@ -2,16 +2,16 @@
2
2
  # DO NOT EDIT THIS FILE DIRECTLY
3
3
  # Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
4
4
  # -*- encoding: utf-8 -*-
5
- # stub: corl 0.5.15 ruby lib
5
+ # stub: corl 0.5.16 ruby lib
6
6
 
7
7
  Gem::Specification.new do |s|
8
8
  s.name = "corl"
9
- s.version = "0.5.15"
9
+ s.version = "0.5.16"
10
10
 
11
11
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
12
12
  s.require_paths = ["lib"]
13
13
  s.authors = ["Adrian Webb"]
14
- s.date = "2015-02-19"
14
+ s.date = "2015-02-26"
15
15
  s.description = "Framework that provides a simple foundation for growing organically in the cloud"
16
16
  s.email = "adrian.webb@coralnexus.com"
17
17
  s.executables = ["corl"]
@@ -78,8 +78,10 @@ Gem::Specification.new do |s|
78
78
  "lib/core/mod/fog_rackspace_server.rb",
79
79
  "lib/core/mod/hiera_backend.rb",
80
80
  "lib/core/plugin/agent.rb",
81
+ "lib/core/plugin/agent_wrapper.rb",
81
82
  "lib/core/plugin/builder.rb",
82
83
  "lib/core/plugin/cloud_action.rb",
84
+ "lib/core/plugin/cloud_action_wrapper.rb",
83
85
  "lib/core/plugin/configuration.rb",
84
86
  "lib/core/plugin/fog_machine.rb",
85
87
  "lib/core/plugin/fog_node.rb",
@@ -106,6 +108,7 @@ Gem::Specification.new do |s|
106
108
  "lib/facter/custom_facts.rb",
107
109
  "lib/facter/vagrant_exists.rb",
108
110
  "lib/hiera/corl_logger.rb",
111
+ "lib/nucleon/action/agent/manager.rb",
109
112
  "lib/nucleon/action/network/config.rb",
110
113
  "lib/nucleon/action/network/create.rb",
111
114
  "lib/nucleon/action/network/images.rb",
@@ -117,11 +120,15 @@ Gem::Specification.new do |s|
117
120
  "lib/nucleon/action/network/vagrantfile.rb",
118
121
  "lib/nucleon/action/node/IP.rb",
119
122
  "lib/nucleon/action/node/SSH.rb",
123
+ "lib/nucleon/action/node/agent/status.rb",
124
+ "lib/nucleon/action/node/agent/stop.rb",
125
+ "lib/nucleon/action/node/agents.rb",
120
126
  "lib/nucleon/action/node/authorize.rb",
121
127
  "lib/nucleon/action/node/bootstrap.rb",
122
128
  "lib/nucleon/action/node/build.rb",
123
129
  "lib/nucleon/action/node/cache.rb",
124
130
  "lib/nucleon/action/node/destroy.rb",
131
+ "lib/nucleon/action/node/download.rb",
125
132
  "lib/nucleon/action/node/exec.rb",
126
133
  "lib/nucleon/action/node/fact.rb",
127
134
  "lib/nucleon/action/node/facts.rb",
@@ -139,6 +146,7 @@ Gem::Specification.new do |s|
139
146
  "lib/nucleon/action/node/start.rb",
140
147
  "lib/nucleon/action/node/status.rb",
141
148
  "lib/nucleon/action/node/stop.rb",
149
+ "lib/nucleon/action/node/upload.rb",
142
150
  "lib/nucleon/action/plugin/create.rb",
143
151
  "lib/nucleon/action/plugin/list.rb",
144
152
  "lib/nucleon/action/plugins.rb",
@@ -59,12 +59,11 @@ class Agent < Nucleon.plugin_class(:nucleon, :cloud_action)
59
59
  def execute(use_network = true, &block)
60
60
  super do |node|
61
61
  ensure_network do
62
- add_agent(node)
63
-
64
62
  trap(:INT) do
65
63
  safe_exit
66
64
  end
67
65
 
66
+ add_agent(node)
68
67
  block.call(node)
69
68
  remove_agent(node) if myself.status == code.success
70
69
  end
@@ -75,12 +74,19 @@ class Agent < Nucleon.plugin_class(:nucleon, :cloud_action)
75
74
  # Utilities
76
75
 
77
76
  def add_agent(node)
78
- settings[:pid] = Process.pid
77
+ args = []
78
+
79
+ ARGV.each do |arg|
80
+ args << ( arg =~ /^\-/ ? arg : "'#{arg}'" )
81
+ end
79
82
 
80
- stored_config = Util::Data.clean(settings.export)
81
- stored_config = Util::Data.rm_keys(stored_config, [ :node_provider, :nodes, :color, :version ])
83
+ agent_config = Config.new({
84
+ :pid => Process.pid,
85
+ :args => args.join(' ')
86
+ }).import(Util::Data.clean(settings.export))
82
87
 
83
- node.add_agent(plugin_provider, stored_config)
88
+ agent_config = Util::Data.rm_keys(agent_config.export, [ :node_provider, :nodes, :color, :version ])
89
+ node.add_agent(plugin_provider, agent_config)
84
90
  end
85
91
  protected :add_agent
86
92
 
@@ -0,0 +1,26 @@
1
+
2
+ nucleon_require(File.dirname(__FILE__), :agent)
3
+
4
+ #---
5
+
6
+ module Nucleon
7
+ module Plugin
8
+ class AgentWrapper < Nucleon.plugin_class(:nucleon, :agent)
9
+
10
+ #-----------------------------------------------------------------------------
11
+ # Operations
12
+
13
+ def execute(use_network = true, &block)
14
+ super do |node|
15
+ bin_dir = File.join(network.directory, 'bin')
16
+ bin_dir = ( File.directory?(bin_dir) ? bin_dir : network.directory )
17
+
18
+ Dir.chdir(bin_dir) do
19
+ result = node.exec({ :commands => [ block.call(node) ] }).first
20
+ myself.status = result.status
21
+ end
22
+ end
23
+ end
24
+ end
25
+ end
26
+ end
@@ -0,0 +1,26 @@
1
+
2
+ nucleon_require(File.dirname(__FILE__), :cloud_action)
3
+
4
+ #---
5
+
6
+ module Nucleon
7
+ module Plugin
8
+ class CloudActionWrapper < Nucleon.plugin_class(:nucleon, :cloud_action)
9
+
10
+ #-----------------------------------------------------------------------------
11
+ # Operations
12
+
13
+ def execute(use_network = true, &block)
14
+ super do |node|
15
+ bin_dir = File.join(network.directory, 'bin')
16
+ bin_dir = ( File.directory?(bin_dir) ? bin_dir : network.directory )
17
+
18
+ Dir.chdir(bin_dir) do
19
+ result = node.exec({ :commands => [ block.call(node) ] }).first
20
+ myself.status = result.status
21
+ end
22
+ end
23
+ end
24
+ end
25
+ end
26
+ end
@@ -176,6 +176,7 @@ class Configuration < Nucleon.plugin_class(:nucleon, :base)
176
176
  config.import(properties, method_config)
177
177
  end
178
178
  end
179
+ success = cache.load if success
179
180
  else
180
181
  logger.warn("Loading of source configuration failed")
181
182
  end
@@ -195,6 +196,7 @@ class Configuration < Nucleon.plugin_class(:nucleon, :base)
195
196
 
196
197
  success = yield(method_config) if block_given?
197
198
  end
199
+ success = cache.save if success
198
200
  else
199
201
  logger.warn("Can not save source configuration")
200
202
  end
@@ -377,31 +377,63 @@ class Node < Nucleon.plugin_class(:nucleon, :base)
377
377
  #---
378
378
 
379
379
  def agents
380
- hash(myself[:agents])
380
+ if local?
381
+ agents = cache_setting([ :agents ], {}, :hash)
382
+ else
383
+ agents = remote_cache_setting([ :agents ], {}, :hash)
384
+ end
385
+ Util::Data.symbol_map(agents)
381
386
  end
382
387
 
383
388
  def agent(provider)
384
- search([ :agents, provider ], {}, :hash)
389
+ if local?
390
+ agent = cache_setting([ :agents, provider ], {}, :hash)
391
+ else
392
+ agent = remote_cache_setting([ :agents, provider ], {}, :hash)
393
+ end
394
+ Util::Data.symbol_map(agent)
385
395
  end
386
396
 
387
- def add_agent(provider, settings)
388
- set_setting([ :agents, provider ], Config.new(settings).export)
397
+ def agent_running(provider)
398
+ if local?
399
+ agent_options = agent(provider)
400
+ return false unless agent_options.has_key?(:pid)
389
401
 
390
- save({
391
- :message => "Agent #{provider} starting up on #{plugin_provider} #{plugin_name}",
392
- :remote => extension_set(:add_agent_remote, :edit),
393
- :push => true
394
- })
402
+ Process.kill(0, agent_options[:pid].to_i)
403
+ true
404
+ else
405
+ result = run.node_agents
406
+
407
+ if result.status == code.success
408
+ result_data = Util::Data.parse_json(result.errors)
409
+ running = Util::Data.value(result_data[provider.to_s]["running"], false)
410
+ end
411
+ return running
412
+ end
413
+ rescue Errno::ESRCH # No process (local)
414
+ false
415
+ rescue Errno::EPERM # The process exists, but no permission to send signal to it (local)
416
+ true
395
417
  end
396
418
 
397
- def remove_agent(provider)
398
- delete_setting([ :agents, provider ])
419
+ def add_agent(provider, options)
420
+ if local?
421
+ set_cache_setting([ :agents, provider ], Config.new(options).export)
422
+ else
423
+ remote_set_cache_setting([ :agents, provider ], Config.new(options).export)
424
+ end
425
+ end
399
426
 
400
- save({
401
- :message => "Agent #{provider} shutting down on #{plugin_provider} #{plugin_name}",
402
- :remote => extension_set(:remove_agent_remote, :edit),
403
- :push => true
404
- })
427
+ def remove_agent(provider)
428
+ if local?
429
+ agent_options = agent(provider)
430
+ if agent_options && agent_running(provider)
431
+ Process.kill("SIGINT", agent_options[:pid].to_i)
432
+ end
433
+ delete_cache_setting([ :agents, provider ])
434
+ else
435
+ remote_delete_cache_setting([ :agents, provider ])
436
+ end
405
437
  end
406
438
 
407
439
  #-----------------------------------------------------------------------------
@@ -715,6 +747,7 @@ class Node < Nucleon.plugin_class(:nucleon, :base)
715
747
  config = Config.ensure(options)
716
748
  hook_config = Config.new({ :local_path => local_path, :remote_path => remote_path, :config => config }, {}, true, false)
717
749
  quiet = config.get(:quiet, false)
750
+ progress = config.get(:progress, true)
718
751
 
719
752
  if extension_check(:download, hook_config)
720
753
  logger.info("Downloading from #{plugin_name}")
@@ -725,7 +758,7 @@ class Node < Nucleon.plugin_class(:nucleon, :base)
725
758
  active_machine = local? ? local_machine : machine
726
759
 
727
760
  success = active_machine.download(remote_path, local_path, config.export) do |name, received, total|
728
- info("#{name}: Sent #{received} of #{total}", { :i18n => false }) unless quiet
761
+ info("#{name}: Sent #{received} of #{total}", { :i18n => false }) if progress && ! quiet
729
762
  yield(:progress, { :name => name, :received => received, :total => total })
730
763
  end
731
764
 
@@ -754,6 +787,7 @@ class Node < Nucleon.plugin_class(:nucleon, :base)
754
787
  config = Config.ensure(options)
755
788
  hook_config = Config.new({ :local_path => local_path, :remote_path => remote_path, :config => config }, {}, true, false)
756
789
  quiet = config.get(:quiet, false)
790
+ progress = config.get(:progress, true)
757
791
 
758
792
  if extension_check(:upload, hook_config)
759
793
  logger.info("Uploading to #{plugin_name}")
@@ -764,7 +798,7 @@ class Node < Nucleon.plugin_class(:nucleon, :base)
764
798
  active_machine = local? ? local_machine : machine
765
799
 
766
800
  success = active_machine.upload(local_path, remote_path, config.export) do |name, sent, total|
767
- info("#{name}: Sent #{sent} of #{total}", { :i18n => false }) unless quiet
801
+ info("#{name}: Sent #{sent} of #{total}", { :i18n => false }) if progress && ! quiet
768
802
  yield(:progress, { :name => name, :sent => sent, :total => total })
769
803
  end
770
804
 
@@ -788,7 +822,7 @@ class Node < Nucleon.plugin_class(:nucleon, :base)
788
822
 
789
823
  def send_files(local_path, remote_path, files = nil, permission = '0644', options = {}, &code)
790
824
  local_path = File.expand_path(local_path)
791
- return false unless File.directory?(local_path)
825
+ return false unless File.directory?(local_path) || File.exists?(local_path)
792
826
 
793
827
  success = true
794
828
 
@@ -42,59 +42,61 @@ vagrant_exists = defined?(Vagrant) == 'constant' && Vagrant.class == Module
42
42
  #
43
43
  # For agent options processed here, see lib/core/plugin/agent.rb
44
44
  #
45
- action_start_index = vagrant_exists ? 1 : 0
46
-
47
- if ARGV[action_start_index].to_sym == :agent
48
- remote_exec = false
49
-
50
- log = true
51
- truncate_log = true
52
-
53
- log_file = nil
54
- agent_provider = []
55
- process_log_file_value = false
56
-
57
- first_option_found = false
58
-
59
- # Argument processing
60
- ARGV[(action_start_index + 1)..-1].each do |arg|
61
- first_option_found = true if arg[0] == '-'
62
-
63
- if arg =~ /^\-\-nodes\=?/
64
- remote_exec = true
65
- elsif arg == "--no-log"
66
- log = false
67
- elsif arg == "--no-truncate_log"
68
- truncate_log = false
69
- elsif arg =~ /^\-\-log_file(?=\=(.*))?/
70
- if $1
71
- log_file = $1
72
- else
73
- process_log_file_value = true
45
+ unless vagrant_exists
46
+ action_start_index = 0
47
+
48
+ if ARGV[action_start_index].to_sym == :agent
49
+ remote_exec = false
50
+
51
+ log = true
52
+ truncate_log = true
53
+
54
+ log_file = nil
55
+ agent_provider = []
56
+ process_log_file_value = false
57
+
58
+ first_option_found = false
59
+
60
+ # Argument processing
61
+ ARGV[(action_start_index + 1)..-1].each do |arg|
62
+ first_option_found = true if arg[0] == '-'
63
+
64
+ if arg =~ /^\-\-nodes\=?/
65
+ remote_exec = true
66
+ elsif arg == "--no-log"
67
+ log = false
68
+ elsif arg == "--no-truncate_log"
69
+ truncate_log = false
70
+ elsif arg =~ /^\-\-log_file(?=\=(.*))?/
71
+ if $1
72
+ log_file = $1
73
+ else
74
+ process_log_file_value = true
75
+ end
76
+ elsif process_log_file_value
77
+ log_file = arg
78
+ process_log_file_value = false
79
+ elsif ! first_option_found
80
+ agent_provider << arg
74
81
  end
75
- elsif process_log_file_value
76
- log_file = arg
77
- process_log_file_value = false
78
- elsif ! first_option_found
79
- agent_provider << arg
80
82
  end
81
- end
82
83
 
83
- # TODO: Need better way to share with base agent default log file. (mixin?)
84
- log_file = "/var/log/corl/agent_#{agent_provider.join('_')}.log" unless log_file
84
+ # TODO: Need better way to share with base agent default log file. (mixin?)
85
+ log_file = "/var/log/corl/agent_#{agent_provider.join('_')}.log" unless log_file
85
86
 
86
- unless remote_exec || vagrant_exists
87
- # Daemonize process
88
- Process.daemon
87
+ unless remote_exec
88
+ # Daemonize process
89
+ Process.daemon
89
90
 
90
- # Log all output, or not
91
- if log
92
- FileUtils.mkdir_p('/var/log/corl')
93
- File.write(log_file, '') if truncate_log
91
+ # Log all output, or not
92
+ if log
93
+ FileUtils.mkdir_p('/var/log/corl')
94
+ File.write(log_file, '') if truncate_log
94
95
 
95
- $stderr.reopen(log_file, 'a')
96
- $stdout.reopen($stderr)
97
- $stdout.sync = $stderr.sync = true
96
+ $stderr.reopen(log_file, 'a')
97
+ $stdout.reopen($stderr)
98
+ $stdout.sync = $stderr.sync = true
99
+ end
98
100
  end
99
101
  end
100
102
  end
@@ -0,0 +1,75 @@
1
+
2
+ module Nucleon
3
+ module Action
4
+ module Agent
5
+ class Manager < Nucleon.plugin_class(:nucleon, :agent)
6
+
7
+ #-----------------------------------------------------------------------------
8
+ # Info
9
+
10
+ def self.describe
11
+ super(nil, :manager, 1100)
12
+ end
13
+
14
+ #-----------------------------------------------------------------------------
15
+ # Settings
16
+
17
+ def configure
18
+ super do
19
+ codes :network_failure
20
+
21
+ register_int :sleep_interval, 15
22
+ register_int :network_retries, 3
23
+ register_int :agent_restart_retries, 2
24
+ end
25
+ end
26
+
27
+ #---
28
+
29
+ def arguments
30
+ [ :sleep_interval ]
31
+ end
32
+
33
+ #-----------------------------------------------------------------------------
34
+ # Operations
35
+
36
+ def execute
37
+ super do |node|
38
+ ensure_node(node) do
39
+ network_retry = 0
40
+ agent_restart_retry = {}
41
+
42
+ while status == code.success
43
+ if network.load({ :remote => settings[:net_remote], :pull => true })
44
+ network_retry = 0
45
+
46
+ node.agents.each do |provider, agent_options|
47
+ agent_restart_retry[provider] = 0 unless agent_restart_retry.has_key?(provider)
48
+
49
+ unless provider == :agent_manager || node.agent_running(provider)
50
+ if agent_restart_retry[provider] < settings[:agent_restart_retries]
51
+ command = "corl #{agent_options[:args]} --log_level=warn"
52
+ result = node.exec({ :commands => [ command ] }).first
53
+
54
+ if result.status == code.success
55
+ agent_restart_retry[provider] = 0
56
+ else
57
+ agent_restart_retry[provider] += 1
58
+ end
59
+ end
60
+ end
61
+ end
62
+ elsif network_retry < settings[:network_retries]
63
+ network_retry += 1
64
+ else
65
+ myself.status = code.network_failure
66
+ end
67
+ sleep settings[:sleep_interval]
68
+ end
69
+ end
70
+ end
71
+ end
72
+ end
73
+ end
74
+ end
75
+ end
@@ -0,0 +1,53 @@
1
+
2
+ module Nucleon
3
+ module Action
4
+ module Node
5
+ module Agent
6
+ class Status < Nucleon.plugin_class(:nucleon, :cloud_action)
7
+
8
+ #-----------------------------------------------------------------------------
9
+ # Info
10
+
11
+ def self.describe
12
+ super([ :node, :agent ], :status, 650)
13
+ end
14
+
15
+ #-----------------------------------------------------------------------------
16
+ # Settings
17
+
18
+ def configure
19
+ super do
20
+ register_array :provider, nil
21
+ register_translator :format, :json
22
+ end
23
+ end
24
+
25
+ #---
26
+
27
+ def arguments
28
+ [ :provider ]
29
+ end
30
+
31
+ #-----------------------------------------------------------------------------
32
+ # Operations
33
+
34
+ def execute
35
+ super do |node|
36
+ ensure_node(node) do
37
+ translator = CORL.translator({}, settings[:format])
38
+
39
+ agent_provider = "agent_#{settings[:provider].join('_')}"
40
+ agent_record = node.agent(agent_provider)
41
+
42
+ agent_record[:running] = node.agent_running(agent_provider) unless agent_record.empty?
43
+
44
+ myself.result = agent_record
45
+ $stderr.puts translator.generate(result) unless result.empty?
46
+ end
47
+ end
48
+ end
49
+ end
50
+ end
51
+ end
52
+ end
53
+ end
@@ -0,0 +1,44 @@
1
+
2
+ module Nucleon
3
+ module Action
4
+ module Node
5
+ module Agent
6
+ class Stop < Nucleon.plugin_class(:nucleon, :cloud_action)
7
+
8
+ #-----------------------------------------------------------------------------
9
+ # Info
10
+
11
+ def self.describe
12
+ super([ :node, :agent ], :stop, 640)
13
+ end
14
+
15
+ #-----------------------------------------------------------------------------
16
+ # Settings
17
+
18
+ def configure
19
+ super do
20
+ register_array :provider, nil
21
+ end
22
+ end
23
+
24
+ #---
25
+
26
+ def arguments
27
+ [ :provider ]
28
+ end
29
+
30
+ #-----------------------------------------------------------------------------
31
+ # Operations
32
+
33
+ def execute
34
+ super do |node|
35
+ ensure_node(node) do
36
+ node.remove_agent("agent_#{settings[:provider].join('_')}")
37
+ end
38
+ end
39
+ end
40
+ end
41
+ end
42
+ end
43
+ end
44
+ end
@@ -0,0 +1,44 @@
1
+
2
+ module Nucleon
3
+ module Action
4
+ module Node
5
+ class Agents < Nucleon.plugin_class(:nucleon, :cloud_action)
6
+
7
+ #-----------------------------------------------------------------------------
8
+ # Info
9
+
10
+ def self.describe
11
+ super(:node, :agents, 800)
12
+ end
13
+
14
+ #-----------------------------------------------------------------------------
15
+ # Settings
16
+
17
+ def configure
18
+ super do
19
+ register_translator :format, :json
20
+ end
21
+ end
22
+
23
+ #-----------------------------------------------------------------------------
24
+ # Operations
25
+
26
+ def execute
27
+ super do |node|
28
+ ensure_node(node) do
29
+ translator = CORL.translator({}, settings[:format])
30
+ agent_records = node.agents
31
+
32
+ agent_records.each do |provider, agent_options|
33
+ agent_records[provider][:running] = node.agent_running(provider)
34
+ end
35
+
36
+ myself.result = agent_records
37
+ $stderr.puts translator.generate(result) unless result.empty?
38
+ end
39
+ end
40
+ end
41
+ end
42
+ end
43
+ end
44
+ end
@@ -0,0 +1,82 @@
1
+
2
+ module Nucleon
3
+ module Action
4
+ module Node
5
+ class Download < Nucleon.plugin_class(:nucleon, :cloud_action)
6
+
7
+ #-----------------------------------------------------------------------------
8
+ # Info
9
+
10
+ def self.describe
11
+ super(:node, :download, 500)
12
+ end
13
+
14
+ #-----------------------------------------------------------------------------
15
+ # Settings
16
+
17
+ def configure
18
+ super do
19
+ register_str :remote_path, nil
20
+ register_str :local_path, nil
21
+
22
+ register_bool :progress, true
23
+
24
+ register_array :download_nodes, nil do |values|
25
+ if values.nil?
26
+ warn('download_nodes_empty')
27
+ next false
28
+ end
29
+
30
+ node_plugins = CORL.loaded_plugins(:CORL, :node)
31
+ success = true
32
+
33
+ values.each do |value|
34
+ if info = CORL.plugin_class(:CORL, :node).translate_reference(value)
35
+ if ! node_plugins.keys.include?(info[:provider].to_sym) || info[:name].empty?
36
+ warn('download_nodes', { :value => value, :node_provider => info[:provider], :name => info[:name] })
37
+ success = false
38
+ end
39
+ end
40
+ end
41
+ success
42
+ end
43
+ end
44
+ end
45
+
46
+ #---
47
+
48
+ def ignore
49
+ [ :nodes, :parallel ]
50
+ end
51
+
52
+ def arguments
53
+ [ :remote_path, :local_path, :upload_nodes ]
54
+ end
55
+
56
+ #-----------------------------------------------------------------------------
57
+ # Operations
58
+
59
+ def execute
60
+ super do |local_node|
61
+ ensure_network do
62
+ batch_success = network.batch(settings[:download_nodes], settings[:node_provider], false) do |node|
63
+ render_options = { :id => node.id, :hostname => node.hostname, :remote_path => settings[:remote_path], :local_path => settings[:local_path] }
64
+
65
+ info('start', render_options)
66
+ success = node.download(settings[:remote_path], settings[:local_path], { :progress => settings[:progress] })
67
+
68
+ if success
69
+ success('complete', render_options)
70
+ else
71
+ error('failure', render_options)
72
+ end
73
+ success
74
+ end
75
+ myself.status = code.batch_error unless batch_success
76
+ end
77
+ end
78
+ end
79
+ end
80
+ end
81
+ end
82
+ end
@@ -0,0 +1,83 @@
1
+
2
+ module Nucleon
3
+ module Action
4
+ module Node
5
+ class Upload < Nucleon.plugin_class(:nucleon, :cloud_action)
6
+
7
+ #-----------------------------------------------------------------------------
8
+ # Info
9
+
10
+ def self.describe
11
+ super(:node, :upload, 500)
12
+ end
13
+
14
+ #-----------------------------------------------------------------------------
15
+ # Settings
16
+
17
+ def configure
18
+ super do
19
+ register_str :local_path, nil
20
+ register_str :remote_path, nil
21
+ register_str :file_mode, '0755'
22
+
23
+ register_bool :progress, true
24
+
25
+ register_array :upload_nodes, nil do |values|
26
+ if values.nil?
27
+ warn('upload_nodes_empty')
28
+ next false
29
+ end
30
+
31
+ node_plugins = CORL.loaded_plugins(:CORL, :node)
32
+ success = true
33
+
34
+ values.each do |value|
35
+ if info = CORL.plugin_class(:CORL, :node).translate_reference(value)
36
+ if ! node_plugins.keys.include?(info[:provider].to_sym) || info[:name].empty?
37
+ warn('upload_nodes', { :value => value, :node_provider => info[:provider], :name => info[:name] })
38
+ success = false
39
+ end
40
+ end
41
+ end
42
+ success
43
+ end
44
+ end
45
+ end
46
+
47
+ #---
48
+
49
+ def ignore
50
+ [ :nodes ]
51
+ end
52
+
53
+ def arguments
54
+ [ :local_path, :remote_path, :upload_nodes ]
55
+ end
56
+
57
+ #-----------------------------------------------------------------------------
58
+ # Operations
59
+
60
+ def execute
61
+ super do |local_node|
62
+ ensure_network do
63
+ batch_success = network.batch(settings[:upload_nodes], settings[:node_provider], settings[:parallel]) do |node|
64
+ render_options = { :id => node.id, :hostname => node.hostname, :local_path => settings[:local_path], :remote_path => settings[:remote_path] }
65
+
66
+ info('start', render_options)
67
+ success = node.send_files(settings[:local_path], settings[:remote_path], nil, settings[:file_mode], { :progress => settings[:progress] })
68
+
69
+ if success
70
+ success('complete', render_options)
71
+ else
72
+ error('failure', render_options)
73
+ end
74
+ success
75
+ end
76
+ myself.status = code.batch_error unless batch_success
77
+ end
78
+ end
79
+ end
80
+ end
81
+ end
82
+ end
83
+ end
@@ -667,6 +667,36 @@ en:
667
667
  info:
668
668
  start: |-
669
669
  Destroying %{provider} machine %{name}
670
+ upload:
671
+ description: |-
672
+ Upload a file or directory to a specified location on remote nodes
673
+ help: |-
674
+ Upload a file or directory to a specified location on remote nodes
675
+ options:
676
+ upload_nodes: |-
677
+ Nodes to upload file or directory to
678
+ local_path: |-
679
+ Local file or directory to upload to nodes (default %{default_value})
680
+ remote_path: |-
681
+ Remote path to upload local file or directory to (default %{default_value})
682
+ file_mode: |-
683
+ File mode to set for remote file or directory uploaded (default %{default_value})
684
+ progress: |-
685
+ Show upload progress (default %{default_value})
686
+ info:
687
+ start: |-
688
+ Starting upload of %{local_path} to %{remote_path} on %{hostname} (id %{id})
689
+ success:
690
+ complete: |-
691
+ Upload completed
692
+ warn:
693
+ upload_nodes_empty: |-
694
+ Nodes must be specified in order to run the upload action
695
+ upload_nodes: |-
696
+ Provider %{node_provider} node %{name} is not a valid node to upload (%{value} given)
697
+ error:
698
+ failure: |-
699
+ Upload failed
670
700
  ip:
671
701
  description: |-
672
702
  Return the public IP address for nodes
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: corl
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.15
4
+ version: 0.5.16
5
5
  platform: ruby
6
6
  authors:
7
7
  - Adrian Webb
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2015-02-19 00:00:00.000000000 Z
11
+ date: 2015-02-26 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: nucleon
@@ -238,8 +238,10 @@ files:
238
238
  - lib/core/mod/fog_rackspace_server.rb
239
239
  - lib/core/mod/hiera_backend.rb
240
240
  - lib/core/plugin/agent.rb
241
+ - lib/core/plugin/agent_wrapper.rb
241
242
  - lib/core/plugin/builder.rb
242
243
  - lib/core/plugin/cloud_action.rb
244
+ - lib/core/plugin/cloud_action_wrapper.rb
243
245
  - lib/core/plugin/configuration.rb
244
246
  - lib/core/plugin/fog_machine.rb
245
247
  - lib/core/plugin/fog_node.rb
@@ -266,6 +268,7 @@ files:
266
268
  - lib/facter/custom_facts.rb
267
269
  - lib/facter/vagrant_exists.rb
268
270
  - lib/hiera/corl_logger.rb
271
+ - lib/nucleon/action/agent/manager.rb
269
272
  - lib/nucleon/action/network/config.rb
270
273
  - lib/nucleon/action/network/create.rb
271
274
  - lib/nucleon/action/network/images.rb
@@ -277,11 +280,15 @@ files:
277
280
  - lib/nucleon/action/network/vagrantfile.rb
278
281
  - lib/nucleon/action/node/IP.rb
279
282
  - lib/nucleon/action/node/SSH.rb
283
+ - lib/nucleon/action/node/agent/status.rb
284
+ - lib/nucleon/action/node/agent/stop.rb
285
+ - lib/nucleon/action/node/agents.rb
280
286
  - lib/nucleon/action/node/authorize.rb
281
287
  - lib/nucleon/action/node/bootstrap.rb
282
288
  - lib/nucleon/action/node/build.rb
283
289
  - lib/nucleon/action/node/cache.rb
284
290
  - lib/nucleon/action/node/destroy.rb
291
+ - lib/nucleon/action/node/download.rb
285
292
  - lib/nucleon/action/node/exec.rb
286
293
  - lib/nucleon/action/node/fact.rb
287
294
  - lib/nucleon/action/node/facts.rb
@@ -299,6 +306,7 @@ files:
299
306
  - lib/nucleon/action/node/start.rb
300
307
  - lib/nucleon/action/node/status.rb
301
308
  - lib/nucleon/action/node/stop.rb
309
+ - lib/nucleon/action/node/upload.rb
302
310
  - lib/nucleon/action/plugin/create.rb
303
311
  - lib/nucleon/action/plugin/list.rb
304
312
  - lib/nucleon/action/plugins.rb