dtk-node-agent 0.5.10

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (62) hide show
  1. checksums.yaml +15 -0
  2. data/Gemfile +4 -0
  3. data/Gemfile.lock +18 -0
  4. data/README.md +42 -0
  5. data/bin/dtk-node-agent +16 -0
  6. data/dtk-node-agent.gemspec +38 -0
  7. data/lib/config/install.config +12 -0
  8. data/lib/dtk-node-agent/installer.rb +142 -0
  9. data/lib/dtk-node-agent/version.rb +3 -0
  10. data/mcollective_additions/plugins/README.md +1 -0
  11. data/mcollective_additions/plugins/v1.2/agent/discovery.rb +39 -0
  12. data/mcollective_additions/plugins/v1.2/agent/get_log_fragment.ddl +15 -0
  13. data/mcollective_additions/plugins/v1.2/agent/get_log_fragment.rb +79 -0
  14. data/mcollective_additions/plugins/v1.2/agent/git_access.ddl +9 -0
  15. data/mcollective_additions/plugins/v1.2/agent/git_access.rb +79 -0
  16. data/mcollective_additions/plugins/v1.2/agent/netstat.ddl +9 -0
  17. data/mcollective_additions/plugins/v1.2/agent/netstat.rb +34 -0
  18. data/mcollective_additions/plugins/v1.2/agent/puppet_apply.ddl +9 -0
  19. data/mcollective_additions/plugins/v1.2/agent/puppet_apply.rb +630 -0
  20. data/mcollective_additions/plugins/v1.2/agent/rpcutil.ddl +204 -0
  21. data/mcollective_additions/plugins/v1.2/agent/rpcutil.rb +101 -0
  22. data/mcollective_additions/plugins/v1.2/facts/pbuilder_facts.rb +35 -0
  23. data/mcollective_additions/plugins/v2.2/agent/dev_manager.ddl +9 -0
  24. data/mcollective_additions/plugins/v2.2/agent/dev_manager.rb +69 -0
  25. data/mcollective_additions/plugins/v2.2/agent/discovery.rb +39 -0
  26. data/mcollective_additions/plugins/v2.2/agent/dtk_node_agent_git_client.rb +94 -0
  27. data/mcollective_additions/plugins/v2.2/agent/execute_tests.ddl +9 -0
  28. data/mcollective_additions/plugins/v2.2/agent/execute_tests.rb +64 -0
  29. data/mcollective_additions/plugins/v2.2/agent/get_log_fragment.ddl +15 -0
  30. data/mcollective_additions/plugins/v2.2/agent/get_log_fragment.rb +79 -0
  31. data/mcollective_additions/plugins/v2.2/agent/git_access.ddl +9 -0
  32. data/mcollective_additions/plugins/v2.2/agent/git_access.rb +72 -0
  33. data/mcollective_additions/plugins/v2.2/agent/netstat.ddl +9 -0
  34. data/mcollective_additions/plugins/v2.2/agent/netstat.rb +34 -0
  35. data/mcollective_additions/plugins/v2.2/agent/ps.ddl +9 -0
  36. data/mcollective_additions/plugins/v2.2/agent/ps.rb +37 -0
  37. data/mcollective_additions/plugins/v2.2/agent/puppet_apply.ddl +9 -0
  38. data/mcollective_additions/plugins/v2.2/agent/puppet_apply.rb +633 -0
  39. data/mcollective_additions/plugins/v2.2/agent/puppet_cancel.ddl +10 -0
  40. data/mcollective_additions/plugins/v2.2/agent/puppet_cancel.rb +78 -0
  41. data/mcollective_additions/plugins/v2.2/agent/rpcutil.ddl +204 -0
  42. data/mcollective_additions/plugins/v2.2/agent/rpcutil.rb +101 -0
  43. data/mcollective_additions/plugins/v2.2/agent/sync_agent_code.ddl +10 -0
  44. data/mcollective_additions/plugins/v2.2/agent/sync_agent_code.rb +85 -0
  45. data/mcollective_additions/plugins/v2.2/agent/tail.ddl +11 -0
  46. data/mcollective_additions/plugins/v2.2/agent/tail.rb +67 -0
  47. data/mcollective_additions/plugins/v2.2/connector/r8stomp.rb +238 -0
  48. data/mcollective_additions/plugins/v2.2/connector/stomp.rb +349 -0
  49. data/mcollective_additions/plugins/v2.2/connector/stomp_em.rb +191 -0
  50. data/mcollective_additions/plugins/v2.2/facts/pbuilder_facts.rb +35 -0
  51. data/mcollective_additions/plugins/v2.2/security/sshkey.ddl +9 -0
  52. data/mcollective_additions/plugins/v2.2/security/sshkey.rb +362 -0
  53. data/mcollective_additions/server.cfg +22 -0
  54. data/puppet_additions/modules/r8/lib/puppet/type/r8_export_file.rb +53 -0
  55. data/puppet_additions/modules/r8/manifests/export_variable.rb +10 -0
  56. data/puppet_additions/puppet_lib_base/puppet/indirector/catalog/r8_storeconfig_backend.rb +48 -0
  57. data/puppet_additions/puppet_lib_base/puppet/indirector/r8_storeconfig_backend.rb +4 -0
  58. data/puppet_additions/puppet_lib_base/puppet/indirector/resource/r8_storeconfig_backend.rb +72 -0
  59. data/src/etc/init.d/ec2-run-user-data +95 -0
  60. data/src/etc/logrotate.d/mcollective +10 -0
  61. data/src/etc/logrotate.d/puppet +7 -0
  62. metadata +189 -0
@@ -0,0 +1,10 @@
1
+ metadata :name => "run puppet cancel",
2
+ :description => "Agent to cancel Puppet apply runs",
3
+ :author => "Reactor8",
4
+ :license => "",
5
+ :version => "",
6
+ :url => "",
7
+ :timeout => 600
8
+ action "run", :description => "puppet cancel" do
9
+ end
10
+
@@ -0,0 +1,78 @@
1
+ require 'rubygems'
2
+ require 'puppet'
3
+ require 'grit'
4
+ require 'tempfile'
5
+ require 'fileutils'
6
+
7
+ #TODO: move to be shared by agents
8
+ PuppetApplyLogDir = "/var/log/puppet"
9
+ ModulePath = "/etc/puppet/modules"
10
+
11
+ module MCollective
12
+ module Agent
13
+ class Puppet_cancel < RPC::Agent
14
+ def initialize()
15
+ super()
16
+ @log = Log.instance
17
+ @reply_data = nil
18
+ end
19
+
20
+ #
21
+ # Amar:
22
+ # puppet_cancel agent gets 'task_id' in request
23
+ # And goes through list of live threads inside stomp/mcollective process.
24
+ # If thread with matching 'task_id' is found that thread is killed
25
+ # If thread with matching 'task_id' is not found, error is returned in response
26
+ #
27
+ def run_action
28
+ task_id = request[:top_task_id]
29
+ @log.info("Terminating puppet apply thread for task_id=#{task_id}")
30
+
31
+ ret ||= Response.new()
32
+
33
+ Thread.list.each do |t|
34
+ if t[:task_id] == task_id
35
+ t[:is_canceled] = true
36
+ t.kill
37
+ @log.info("Puppet apply thread for task_id=#{task_id} terminated.")
38
+ ret.set_status_succeeded!()
39
+ return ret
40
+ end
41
+ end
42
+
43
+ @log.info("Puppet apply thread for task_id=#{task_id} is not running on this node.")
44
+ ret.set_status_failed!()
45
+ error_info = { :error => { :message => "Puppet apply thread for task_id=#{task_id} is not running on the node." } }
46
+ ret.merge!(error_info)
47
+ end
48
+
49
+ end
50
+ #TODO: this should be common accross Agents
51
+ class Response < Hash
52
+ def initialize(hash={})
53
+ super()
54
+ self.merge!(hash)
55
+ self[:status] = :unknown unless hash.has_key?(:status)
56
+ end
57
+
58
+ def to_hash()
59
+ Hash.new.merge(self)
60
+ end
61
+
62
+ def failed?()
63
+ self[:status] == :failed
64
+ end
65
+
66
+ def set_status_failed!()
67
+ self[:status] = :failed
68
+ end
69
+ def set_status_succeeded!()
70
+ self[:status] = :succeeded
71
+ end
72
+ def set_dynamic_attributes!(dynamic_attributes)
73
+ self[:dynamic_attributes] = dynamic_attributes
74
+ end
75
+ end
76
+ end
77
+ end
78
+
@@ -0,0 +1,204 @@
1
+ metadata :name => "rpcutil",
2
+ :description => "General helpful actions that expose stats and internals to SimpleRPC clients",
3
+ :author => "R.I.Pienaar <rip@devco.net>",
4
+ :license => "Apache License, Version 2.0",
5
+ :version => "1.0",
6
+ :url => "http://marionette-collective.org/",
7
+ :timeout => 10
8
+
9
+ action "collective_info", :description => "Info about the main and sub collectives" do
10
+ display :always
11
+
12
+ output :main_collective,
13
+ :description => "The main Collective",
14
+ :display_as => "Main Collective"
15
+
16
+ output :collectives,
17
+ :description => "All Collectives",
18
+ :display_as => "All Collectives"
19
+
20
+ summarize do
21
+ aggregate summary(:collectives)
22
+ end
23
+ end
24
+
25
+ action "inventory", :description => "System Inventory" do
26
+ display :always
27
+
28
+ output :agents,
29
+ :description => "List of agent names",
30
+ :display_as => "Agents"
31
+
32
+ output :facts,
33
+ :description => "List of facts and values",
34
+ :display_as => "Facts"
35
+
36
+ output :classes,
37
+ :description => "List of classes on the system",
38
+ :display_as => "Classes"
39
+
40
+ output :version,
41
+ :description => "MCollective Version",
42
+ :display_as => "Version"
43
+
44
+ output :main_collective,
45
+ :description => "The main Collective",
46
+ :display_as => "Main Collective"
47
+
48
+ output :collectives,
49
+ :description => "All Collectives",
50
+ :display_as => "All Collectives"
51
+
52
+ output :data_plugins,
53
+ :description => "List of data plugin names",
54
+ :display_as => "Data Plugins"
55
+ end
56
+
57
+ action "get_fact", :description => "Retrieve a single fact from the fact store" do
58
+ display :always
59
+
60
+ input :fact,
61
+ :prompt => "The name of the fact",
62
+ :description => "The fact to retrieve",
63
+ :type => :string,
64
+ :validation => '^[\w\-\.]+$',
65
+ :optional => false,
66
+ :maxlength => 40
67
+
68
+ output :fact,
69
+ :description => "The name of the fact being returned",
70
+ :display_as => "Fact"
71
+
72
+ output :value,
73
+ :description => "The value of the fact",
74
+ :display_as => "Value"
75
+
76
+ summarize do
77
+ aggregate summary(:value)
78
+ end
79
+ end
80
+
81
+ action "daemon_stats", :description => "Get statistics from the running daemon" do
82
+ display :always
83
+
84
+ output :threads,
85
+ :description => "List of threads active in the daemon",
86
+ :display_as => "Threads"
87
+
88
+ output :agents,
89
+ :description => "List of agents loaded",
90
+ :display_as => "Agents"
91
+
92
+ output :pid,
93
+ :description => "Process ID of the daemon",
94
+ :display_as => "PID"
95
+
96
+ output :times,
97
+ :description => "Processor time consumed by the daemon",
98
+ :display_as => "Times"
99
+
100
+ output :validated,
101
+ :description => "Messages that passed security validation",
102
+ :display_as => "Security Validated"
103
+
104
+ output :unvalidated,
105
+ :description => "Messages that failed security validation",
106
+ :display_as => "Failed Security"
107
+
108
+ output :passed,
109
+ :description => "Passed filter checks",
110
+ :display_as => "Passed Filter"
111
+
112
+ output :filtered,
113
+ :description => "Didn't pass filter checks",
114
+ :display_as => "Failed Filter"
115
+
116
+ output :starttime,
117
+ :description => "Time the server started",
118
+ :display_as => "Start Time"
119
+
120
+ output :total,
121
+ :description => "Total messages received",
122
+ :display_as => "Total Messages"
123
+
124
+ output :replies,
125
+ :description => "Replies sent back to clients",
126
+ :display_as => "Replies"
127
+
128
+ output :configfile,
129
+ :description => "Config file used to start the daemon",
130
+ :display_as => "Config File"
131
+
132
+ output :version,
133
+ :description => "MCollective Version",
134
+ :display_as => "Version"
135
+
136
+ output :ttlexpired,
137
+ :description => "Messages that did pass TTL checks",
138
+ :display_as => "TTL Expired"
139
+
140
+ summarize do
141
+ aggregate summary(:version)
142
+ aggregate summary(:agents)
143
+ end
144
+ end
145
+
146
+ action "agent_inventory", :description => "Inventory of all agents on the server" do
147
+ display :always
148
+
149
+ output :agents,
150
+ :description => "List of agents on the server",
151
+ :display_as => "Agents"
152
+ end
153
+
154
+ action "get_config_item", :description => "Get the active value of a specific config property" do
155
+ display :always
156
+
157
+ input :item,
158
+ :prompt => "Configuration Item",
159
+ :description => "The item to retrieve from the server",
160
+ :type => :string,
161
+ :validation => '^.+$',
162
+ :optional => false,
163
+ :maxlength => 50
164
+
165
+ output :item,
166
+ :description => "The config property being retrieved",
167
+ :display_as => "Property"
168
+
169
+ output :value,
170
+ :description => "The value that is in use",
171
+ :display_as => "Value"
172
+
173
+ summarize do
174
+ aggregate summary(:value)
175
+ end
176
+ end
177
+
178
+ action "get_data", :description => "Get data from a data plugin" do
179
+ display :always
180
+
181
+ input :source,
182
+ :prompt => "Data Source",
183
+ :description => "The data plugin to retrieve information from",
184
+ :type => :string,
185
+ :validation => '^\w+$',
186
+ :optional => false,
187
+ :maxlength => 50
188
+
189
+ input :query,
190
+ :prompt => "Query",
191
+ :description => "The query argument to supply to the data plugin",
192
+ :type => :string,
193
+ :validation => '^.+$',
194
+ :optional => true,
195
+ :maxlength => 50
196
+ end
197
+
198
+ action "ping", :description => "Responds to requests for PING with PONG" do
199
+ display :always
200
+
201
+ output :pong,
202
+ :description => "The local timestamp",
203
+ :display_as => "Timestamp"
204
+ end
@@ -0,0 +1,101 @@
1
+ module MCollective
2
+ module Agent
3
+ class Rpcutil<RPC::Agent
4
+ # Basic system inventory, same as the basic discovery agent
5
+ action "inventory" do
6
+ reply[:agents] = Agents.agentlist
7
+ reply[:facts] = PluginManager["facts_plugin"].get_facts
8
+ reply[:version] = MCollective.version
9
+ reply[:classes] = []
10
+ reply[:main_collective] = config.main_collective
11
+ reply[:collectives] = config.collectives
12
+ reply[:data_plugins] = PluginManager.grep(/_data$/)
13
+
14
+ cfile = Config.instance.classesfile
15
+ if File.exist?(cfile)
16
+ reply[:classes] = File.readlines(cfile).map {|i| i.chomp}
17
+ end
18
+ end
19
+
20
+ # Retrieve a single fact from the node
21
+ action "get_fact" do
22
+ validate :fact, String
23
+
24
+ reply[:fact] = request[:fact]
25
+ reply[:value] = Facts[request[:fact]]
26
+ end
27
+
28
+ # Get the global stats for this mcollectied
29
+ action "daemon_stats" do
30
+ stats = PluginManager["global_stats"].to_hash
31
+
32
+ reply[:threads] = stats[:threads]
33
+ reply[:agents] = stats[:agents]
34
+ reply[:pid] = stats[:pid]
35
+ reply[:times] = stats[:times]
36
+ reply[:configfile] = Config.instance.configfile
37
+ reply[:version] = MCollective.version
38
+
39
+ reply.data.merge!(stats[:stats])
40
+ end
41
+
42
+ # Builds an inventory of all agents on teh machine
43
+ # including license, version and timeout information
44
+ action "agent_inventory" do
45
+ reply[:agents] = []
46
+
47
+ Agents.agentlist.sort.each do |target_agent|
48
+ agent = PluginManager["#{target_agent}_agent"]
49
+ actions = agent.methods.grep(/_agent/)
50
+
51
+ agent_data = {:agent => target_agent,
52
+ :license => "unknown",
53
+ :timeout => agent.timeout,
54
+ :description => "unknown",
55
+ :name => target_agent,
56
+ :url => "unknown",
57
+ :version => "unknown",
58
+ :author => "unknown"}
59
+
60
+ agent_data.merge!(agent.meta)
61
+
62
+ reply[:agents] << agent_data
63
+ end
64
+ end
65
+
66
+ # Retrieves a single config property that is in effect
67
+ action "get_config_item" do
68
+ validate :item, String
69
+
70
+ reply.fail! "Unknown config property #{request[:item]}" unless config.respond_to?(request[:item])
71
+
72
+ reply[:item] = request[:item]
73
+ reply[:value] = config.send(request[:item])
74
+ end
75
+
76
+ # Responds to PING requests with the local timestamp
77
+ action "ping" do
78
+ reply[:pong] = Time.now.to_i
79
+ end
80
+
81
+ # Returns all configured collectives
82
+ action "collective_info" do
83
+ config = Config.instance
84
+ reply[:main_collective] = config.main_collective
85
+ reply[:collectives] = config.collectives
86
+ end
87
+
88
+ action "get_data" do
89
+ validate :source, String
90
+
91
+ query = Data.ddl_transform_input(Data.ddl(request[:source]), request[:query].to_s)
92
+
93
+ data = Data[ request[:source] ].lookup(query)
94
+
95
+ data.keys.each do |key|
96
+ reply[key] = data[key]
97
+ end
98
+ end
99
+ end
100
+ end
101
+ end
@@ -0,0 +1,10 @@
1
+ metadata :name => "sync agents code",
2
+ :description => "Agent to sync agent's code from git repo",
3
+ :author => "Reactor8",
4
+ :license => "",
5
+ :version => "",
6
+ :url => "",
7
+ :timeout => 600
8
+ action "run", :description => "sync agents code" do
9
+ end
10
+
@@ -0,0 +1,85 @@
1
+ require 'rubygems'
2
+ require 'puppet'
3
+ require 'grit'
4
+ require 'tempfile'
5
+ require 'fileutils'
6
+
7
+ AGENT_MCOLLECTIVE_LOCATION = "#{::MCollective::Config.instance.libdir}/mcollective/agent/"
8
+
9
+ module MCollective
10
+ module Agent
11
+ class Sync_agent_code < RPC::Agent
12
+ def initialize()
13
+ super()
14
+ @log = Log.instance
15
+ @reply_data = nil
16
+ end
17
+
18
+ def old_run_action
19
+ ret ||= Response.new()
20
+ #git_server_url = request[:git_server_url]
21
+ raise "git server is not set in facts" unless git_server_url = Facts["git-server"]
22
+ branch = request[:branch]
23
+ cmd_opts = {:raise => true, :timeout => 60}
24
+
25
+ begin
26
+ # Amar: if git repo dir exists pull code, otherwise (first converge case) clone agent's project from git
27
+ if File.directory?(AgentGitPath)
28
+ grit_repo = ::Grit::Repo.new(AgentGitPath)
29
+ grit_repo.git.send(:pull, cmd_opts)
30
+ @log.info("Latest agent code pulled from GIT Repositoy.")
31
+ else
32
+ clone_args = [git_server_url, AgentGitPath]
33
+ clone_args += ["-b", branch] if branch
34
+ ::Grit::Git.new("").clone(cmd_opts, *clone_args)
35
+ @log.info("Agent project successfully cloned from GIT Repository.")
36
+ end
37
+ # Copy latest agents to mcollective agent's directory
38
+ agents = Dir.glob("#{AgentGitPath}/mcollective_additions/plugins/v2.2/agent/*")
39
+ FileUtils.cp_r(agents, AgentMcollectivePath)
40
+ @log.info("Agent files copied to mcollective destination.")
41
+ # System call to restart mcollective
42
+ system("sudo /etc/init.d/mcollective restart")
43
+ @log.info("mcollective system restart completed.")
44
+
45
+ ret.set_status_succeeded!()
46
+ rescue Exception => e
47
+ @log.error("Error in syncing agent's code with GIT Repository: '#{git_server_url}'. Error: #{e}")
48
+ ret.set_status_failed!()
49
+ error_info = { :errors => { :message => "Error in syncing agent's code with GIT Repository: '#{git_server_url}'." } }
50
+ ret.merge!(error_info)
51
+ end
52
+
53
+ return ret
54
+ end
55
+
56
+ end
57
+ #TODO: this should be common accross Agents
58
+ class Response < Hash
59
+ def initialize(hash={})
60
+ super()
61
+ self.merge!(hash)
62
+ self[:status] = :unknown unless hash.has_key?(:status)
63
+ end
64
+
65
+ def to_hash()
66
+ Hash.new.merge(self)
67
+ end
68
+
69
+ def failed?()
70
+ self[:status] == :failed
71
+ end
72
+
73
+ def set_status_failed!()
74
+ self[:status] = :failed
75
+ end
76
+ def set_status_succeeded!()
77
+ self[:status] = :succeeded
78
+ end
79
+ def set_dynamic_attributes!(dynamic_attributes)
80
+ self[:dynamic_attributes] = dynamic_attributes
81
+ end
82
+ end
83
+ end
84
+ end
85
+