ridley 1.7.1 → 2.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +5 -0
- data/README.md +0 -55
- data/lib/ridley.rb +0 -2
- data/lib/ridley/chef_objects/node_object.rb +0 -14
- data/lib/ridley/client.rb +0 -16
- data/lib/ridley/resources/node_resource.rb +0 -189
- data/lib/ridley/version.rb +1 -1
- data/ridley.gemspec +0 -2
- data/spec/unit/ridley/chef_objects/node_object_spec.rb +0 -16
- data/spec/unit/ridley/client_spec.rb +0 -12
- data/spec/unit/ridley/resources/node_resource_spec.rb +2 -133
- metadata +2 -46
- data/lib/ridley/host_commander.rb +0 -231
- data/lib/ridley/host_connector.rb +0 -83
- data/lib/ridley/host_connector/response.rb +0 -27
- data/lib/ridley/host_connector/ssh.rb +0 -211
- data/lib/ridley/host_connector/winrm.rb +0 -218
- data/lib/ridley/host_connector/winrm/command_uploader.rb +0 -87
- data/spec/unit/ridley/host_commander_spec.rb +0 -173
- data/spec/unit/ridley/host_connector/ssh_spec.rb +0 -57
- data/spec/unit/ridley/host_connector/winrm/command_uploader_spec.rb +0 -67
- data/spec/unit/ridley/host_connector/winrm_spec.rb +0 -145
- data/spec/unit/ridley/host_connector_spec.rb +0 -50
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: ridley
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 2.0.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Jamie Winsor
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2013-
|
12
|
+
date: 2013-11-21 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: addressable
|
@@ -207,20 +207,6 @@ dependencies:
|
|
207
207
|
- - '>='
|
208
208
|
- !ruby/object:Gem::Version
|
209
209
|
version: '2.8'
|
210
|
-
- !ruby/object:Gem::Dependency
|
211
|
-
name: net-ssh
|
212
|
-
requirement: !ruby/object:Gem::Requirement
|
213
|
-
requirements:
|
214
|
-
- - '>='
|
215
|
-
- !ruby/object:Gem::Version
|
216
|
-
version: '0'
|
217
|
-
type: :runtime
|
218
|
-
prerelease: false
|
219
|
-
version_requirements: !ruby/object:Gem::Requirement
|
220
|
-
requirements:
|
221
|
-
- - '>='
|
222
|
-
- !ruby/object:Gem::Version
|
223
|
-
version: '0'
|
224
210
|
- !ruby/object:Gem::Dependency
|
225
211
|
name: retryable
|
226
212
|
requirement: !ruby/object:Gem::Requirement
|
@@ -249,20 +235,6 @@ dependencies:
|
|
249
235
|
- - '>='
|
250
236
|
- !ruby/object:Gem::Version
|
251
237
|
version: 0.4.4
|
252
|
-
- !ruby/object:Gem::Dependency
|
253
|
-
name: winrm
|
254
|
-
requirement: !ruby/object:Gem::Requirement
|
255
|
-
requirements:
|
256
|
-
- - ~>
|
257
|
-
- !ruby/object:Gem::Version
|
258
|
-
version: 1.1.0
|
259
|
-
type: :runtime
|
260
|
-
prerelease: false
|
261
|
-
version_requirements: !ruby/object:Gem::Requirement
|
262
|
-
requirements:
|
263
|
-
- - ~>
|
264
|
-
- !ruby/object:Gem::Version
|
265
|
-
version: 1.1.0
|
266
238
|
- !ruby/object:Gem::Dependency
|
267
239
|
name: buff-ruby_engine
|
268
240
|
requirement: !ruby/object:Gem::Requirement
|
@@ -323,12 +295,6 @@ files:
|
|
323
295
|
- lib/ridley/command_context/windows_uninstall.rb
|
324
296
|
- lib/ridley/connection.rb
|
325
297
|
- lib/ridley/errors.rb
|
326
|
-
- lib/ridley/host_commander.rb
|
327
|
-
- lib/ridley/host_connector.rb
|
328
|
-
- lib/ridley/host_connector/response.rb
|
329
|
-
- lib/ridley/host_connector/ssh.rb
|
330
|
-
- lib/ridley/host_connector/winrm.rb
|
331
|
-
- lib/ridley/host_connector/winrm/command_uploader.rb
|
332
298
|
- lib/ridley/logging.rb
|
333
299
|
- lib/ridley/middleware.rb
|
334
300
|
- lib/ridley/middleware/chef_auth.rb
|
@@ -412,11 +378,6 @@ files:
|
|
412
378
|
- spec/unit/ridley/client_spec.rb
|
413
379
|
- spec/unit/ridley/connection_spec.rb
|
414
380
|
- spec/unit/ridley/errors_spec.rb
|
415
|
-
- spec/unit/ridley/host_commander_spec.rb
|
416
|
-
- spec/unit/ridley/host_connector/ssh_spec.rb
|
417
|
-
- spec/unit/ridley/host_connector/winrm/command_uploader_spec.rb
|
418
|
-
- spec/unit/ridley/host_connector/winrm_spec.rb
|
419
|
-
- spec/unit/ridley/host_connector_spec.rb
|
420
381
|
- spec/unit/ridley/middleware/chef_auth_spec.rb
|
421
382
|
- spec/unit/ridley/middleware/chef_response_spec.rb
|
422
383
|
- spec/unit/ridley/middleware/gzip_spec.rb
|
@@ -513,11 +474,6 @@ test_files:
|
|
513
474
|
- spec/unit/ridley/client_spec.rb
|
514
475
|
- spec/unit/ridley/connection_spec.rb
|
515
476
|
- spec/unit/ridley/errors_spec.rb
|
516
|
-
- spec/unit/ridley/host_commander_spec.rb
|
517
|
-
- spec/unit/ridley/host_connector/ssh_spec.rb
|
518
|
-
- spec/unit/ridley/host_connector/winrm/command_uploader_spec.rb
|
519
|
-
- spec/unit/ridley/host_connector/winrm_spec.rb
|
520
|
-
- spec/unit/ridley/host_connector_spec.rb
|
521
477
|
- spec/unit/ridley/middleware/chef_auth_spec.rb
|
522
478
|
- spec/unit/ridley/middleware/chef_response_spec.rb
|
523
479
|
- spec/unit/ridley/middleware/gzip_spec.rb
|
@@ -1,231 +0,0 @@
|
|
1
|
-
module Ridley
|
2
|
-
class ConnectorSupervisor < ::Celluloid::SupervisionGroup
|
3
|
-
# @param [Celluloid::Registry] registry
|
4
|
-
def initialize(registry)
|
5
|
-
super(registry)
|
6
|
-
supervise_as :ssh, HostConnector::SSH
|
7
|
-
supervise_as :winrm, HostConnector::WinRM
|
8
|
-
end
|
9
|
-
end
|
10
|
-
|
11
|
-
class HostCommander
|
12
|
-
include Celluloid
|
13
|
-
include Ridley::Logging
|
14
|
-
|
15
|
-
PORT_CHECK_TIMEOUT = 3
|
16
|
-
|
17
|
-
finalizer :finalize_callback
|
18
|
-
|
19
|
-
def initialize
|
20
|
-
@connector_registry = Celluloid::Registry.new
|
21
|
-
@connector_supervisor = ConnectorSupervisor.new_link(@connector_registry)
|
22
|
-
end
|
23
|
-
|
24
|
-
# Execute a shell command on a node
|
25
|
-
#
|
26
|
-
# @param [String] host
|
27
|
-
# the host to perform the action on
|
28
|
-
# @param [String] command
|
29
|
-
#
|
30
|
-
# @option options [Hash] :ssh
|
31
|
-
# * :user (String) a shell user that will login to each node and perform the bootstrap command on
|
32
|
-
# * :password (String) the password for the shell user that will perform the bootstrap
|
33
|
-
# * :keys (Array, String) an array of key(s) to authenticate the ssh user with instead of a password
|
34
|
-
# * :timeout (Float) timeout value for SSH bootstrap (5.0)
|
35
|
-
# * :sudo (Boolean) run as sudo
|
36
|
-
# @option options [Hash] :winrm
|
37
|
-
# * :user (String) a user that will login to each node and perform the bootstrap command on
|
38
|
-
# * :password (String) the password for the user that will perform the bootstrap (required)
|
39
|
-
# * :port (Fixnum) the winrm port to connect on the node the bootstrap will be performed on (5985)
|
40
|
-
#
|
41
|
-
# @return [HostConnector::Response]
|
42
|
-
def run(host, command, options = {})
|
43
|
-
execute(__method__, host, command, options)
|
44
|
-
end
|
45
|
-
|
46
|
-
# Bootstrap a node
|
47
|
-
#
|
48
|
-
# @param [String] host
|
49
|
-
# the host to perform the action on
|
50
|
-
#
|
51
|
-
# @option options [Hash] :ssh
|
52
|
-
# * :user (String) a shell user that will login to each node and perform the bootstrap command on
|
53
|
-
# * :password (String) the password for the shell user that will perform the bootstrap
|
54
|
-
# * :keys (Array, String) an array of key(s) to authenticate the ssh user with instead of a password
|
55
|
-
# * :timeout (Float) timeout value for SSH bootstrap (5.0)
|
56
|
-
# * :sudo (Boolean) run as sudo
|
57
|
-
# @option options [Hash] :winrm
|
58
|
-
# * :user (String) a user that will login to each node and perform the bootstrap command on
|
59
|
-
# * :password (String) the password for the user that will perform the bootstrap (required)
|
60
|
-
# * :port (Fixnum) the winrm port to connect on the node the bootstrap will be performed on (5985)
|
61
|
-
#
|
62
|
-
# @return [HostConnector::Response]
|
63
|
-
def bootstrap(host, options = {})
|
64
|
-
execute(__method__, host, options)
|
65
|
-
end
|
66
|
-
|
67
|
-
# Perform a chef client run on a node
|
68
|
-
#
|
69
|
-
# @param [String] host
|
70
|
-
# the host to perform the action on
|
71
|
-
#
|
72
|
-
# @option options [Hash] :ssh
|
73
|
-
# * :user (String) a shell user that will login to each node and perform the bootstrap command on
|
74
|
-
# * :password (String) the password for the shell user that will perform the bootstrap
|
75
|
-
# * :keys (Array, String) an array of key(s) to authenticate the ssh user with instead of a password
|
76
|
-
# * :timeout (Float) timeout value for SSH bootstrap (5.0)
|
77
|
-
# * :sudo (Boolean) run as sudo
|
78
|
-
# @option options [Hash] :winrm
|
79
|
-
# * :user (String) a user that will login to each node and perform the bootstrap command on
|
80
|
-
# * :password (String) the password for the user that will perform the bootstrap (required)
|
81
|
-
# * :port (Fixnum) the winrm port to connect on the node the bootstrap will be performed on (5985)
|
82
|
-
#
|
83
|
-
# @return [HostConnector::Response]
|
84
|
-
def chef_client(host, options = {})
|
85
|
-
execute(__method__, host, options)
|
86
|
-
end
|
87
|
-
|
88
|
-
# Write your encrypted data bag secret on a node
|
89
|
-
#
|
90
|
-
# @param [String] host
|
91
|
-
# the host to perform the action on
|
92
|
-
# @param [String] secret
|
93
|
-
# your organization's encrypted data bag secret
|
94
|
-
#
|
95
|
-
# @option options [Hash] :ssh
|
96
|
-
# * :user (String) a shell user that will login to each node and perform the bootstrap command on
|
97
|
-
# * :password (String) the password for the shell user that will perform the bootstrap
|
98
|
-
# * :keys (Array, String) an array of key(s) to authenticate the ssh user with instead of a password
|
99
|
-
# * :timeout (Float) timeout value for SSH bootstrap (5.0)
|
100
|
-
# * :sudo (Boolean) run as sudo
|
101
|
-
# @option options [Hash] :winrm
|
102
|
-
# * :user (String) a user that will login to each node and perform the bootstrap command on
|
103
|
-
# * :password (String) the password for the user that will perform the bootstrap (required)
|
104
|
-
# * :port (Fixnum) the winrm port to connect on the node the bootstrap will be performed on (5985)
|
105
|
-
#
|
106
|
-
# @return [HostConnector::Response]
|
107
|
-
def put_secret(host, secret, options = {})
|
108
|
-
execute(__method__, host, secret, options)
|
109
|
-
end
|
110
|
-
|
111
|
-
# Execute line(s) of Ruby code on a node using Chef's embedded Ruby
|
112
|
-
#
|
113
|
-
# @param [String] host
|
114
|
-
# the host to perform the action on
|
115
|
-
# @param [Array<String>] command_lines
|
116
|
-
# An Array of lines of the command to be executed
|
117
|
-
#
|
118
|
-
# @option options [Hash] :ssh
|
119
|
-
# * :user (String) a shell user that will login to each node and perform the bootstrap command on
|
120
|
-
# * :password (String) the password for the shell user that will perform the bootstrap
|
121
|
-
# * :keys (Array, String) an array of key(s) to authenticate the ssh user with instead of a password
|
122
|
-
# * :timeout (Float) timeout value for SSH bootstrap (5.0)
|
123
|
-
# * :sudo (Boolean) run as sudo
|
124
|
-
# @option options [Hash] :winrm
|
125
|
-
# * :user (String) a user that will login to each node and perform the bootstrap command on
|
126
|
-
# * :password (String) the password for the user that will perform the bootstrap (required)
|
127
|
-
# * :port (Fixnum) the winrm port to connect on the node the bootstrap will be performed on (5985)
|
128
|
-
#
|
129
|
-
# @return [HostConnector::Response]
|
130
|
-
def ruby_script(host, command_lines, options = {})
|
131
|
-
execute(__method__, host, command_lines, options)
|
132
|
-
end
|
133
|
-
|
134
|
-
# Uninstall Chef from a node
|
135
|
-
#
|
136
|
-
# @param [String] host
|
137
|
-
# the host to perform the action on
|
138
|
-
#
|
139
|
-
# @option options [Boolena] :skip_chef (false)
|
140
|
-
# skip removal of the Chef package and the contents of the installation
|
141
|
-
# directory. Setting this to true will only remove any data and configurations
|
142
|
-
# generated by running Chef client.
|
143
|
-
# @option options [Hash] :ssh
|
144
|
-
# * :user (String) a shell user that will login to each node and perform the bootstrap command on
|
145
|
-
# * :password (String) the password for the shell user that will perform the bootstrap
|
146
|
-
# * :keys (Array, String) an array of key(s) to authenticate the ssh user with instead of a password
|
147
|
-
# * :timeout (Float) timeout value for SSH bootstrap (5.0)
|
148
|
-
# * :sudo (Boolean) run as sudo (true)
|
149
|
-
# @option options [Hash] :winrm
|
150
|
-
# * :user (String) a user that will login to each node and perform the bootstrap command on
|
151
|
-
# * :password (String) the password for the user that will perform the bootstrap (required)
|
152
|
-
# * :port (Fixnum) the winrm port to connect on the node the bootstrap will be performed on (5985)
|
153
|
-
#
|
154
|
-
# @return [HostConnector::Response]
|
155
|
-
def uninstall_chef(host, options = {})
|
156
|
-
execute(__method__, host, options)
|
157
|
-
end
|
158
|
-
|
159
|
-
# Finds and returns the best HostConnector for a given host
|
160
|
-
#
|
161
|
-
# @param [String] host
|
162
|
-
# the host to attempt to connect to
|
163
|
-
# @option options [Hash] :ssh
|
164
|
-
# * :port (Fixnum) the ssh port to connect on the node the bootstrap will be performed on (22)
|
165
|
-
# * :timeout (Float) [5.0] timeout value for testing SSH connection
|
166
|
-
# @option options [Hash] :winrm
|
167
|
-
# * :port (Fixnum) the winrm port to connect on the node the bootstrap will be performed on (5985)
|
168
|
-
# @param block [Proc]
|
169
|
-
# an optional block that is yielded the best HostConnector
|
170
|
-
#
|
171
|
-
# @return [HostConnector::SSH, HostConnector::WinRM]
|
172
|
-
def connector_for(host, options = {})
|
173
|
-
options = options.reverse_merge(ssh: Hash.new, winrm: Hash.new)
|
174
|
-
options[:ssh][:port] ||= HostConnector::SSH::DEFAULT_PORT
|
175
|
-
options[:winrm][:port] ||= HostConnector::WinRM::DEFAULT_PORT
|
176
|
-
|
177
|
-
if connector_port_open?(host, options[:winrm][:port])
|
178
|
-
options.delete(:ssh)
|
179
|
-
winrm
|
180
|
-
elsif connector_port_open?(host, options[:ssh][:port], options[:ssh][:timeout])
|
181
|
-
options.delete(:winrm)
|
182
|
-
ssh
|
183
|
-
else
|
184
|
-
raise Errors::HostConnectionError, "No connector ports open on '#{host}'"
|
185
|
-
end
|
186
|
-
end
|
187
|
-
|
188
|
-
private
|
189
|
-
|
190
|
-
def execute(method, host, *args)
|
191
|
-
options = args.last.is_a?(Hash) ? args.pop : Hash.new
|
192
|
-
|
193
|
-
connector_for(host, options).send(method, host, *args, options)
|
194
|
-
rescue Errors::HostConnectionError => ex
|
195
|
-
abort(ex)
|
196
|
-
rescue Resolv::ResolvError => ex
|
197
|
-
abort Errors::DNSResolvError.new(ex)
|
198
|
-
end
|
199
|
-
|
200
|
-
# Checks to see if the given port is open for TCP connections
|
201
|
-
# on the given host.
|
202
|
-
#
|
203
|
-
# @param [String] host
|
204
|
-
# the host to attempt to connect to
|
205
|
-
# @param [Fixnum] port
|
206
|
-
# the port to attempt to connect on
|
207
|
-
# @param [Float] wait_time ({PORT_CHECK_TIMEOUT})
|
208
|
-
# the number of seconds to wait
|
209
|
-
#
|
210
|
-
# @return [Boolean]
|
211
|
-
def connector_port_open?(host, port, wait_time = nil)
|
212
|
-
defer {
|
213
|
-
Timeout.timeout(wait_time || PORT_CHECK_TIMEOUT) { Celluloid::IO::TCPSocket.new(host, port).close; true }
|
214
|
-
}
|
215
|
-
rescue Errno::ETIMEDOUT, Timeout::Error, SocketError, Errno::ECONNREFUSED, Errno::EHOSTUNREACH, Errno::EADDRNOTAVAIL => ex
|
216
|
-
false
|
217
|
-
end
|
218
|
-
|
219
|
-
def finalize_callback
|
220
|
-
@connector_supervisor.terminate if @connector_supervisor && @connector_supervisor.alive?
|
221
|
-
end
|
222
|
-
|
223
|
-
def ssh
|
224
|
-
@connector_registry[:ssh]
|
225
|
-
end
|
226
|
-
|
227
|
-
def winrm
|
228
|
-
@connector_registry[:winrm]
|
229
|
-
end
|
230
|
-
end
|
231
|
-
end
|
@@ -1,83 +0,0 @@
|
|
1
|
-
module Ridley
|
2
|
-
module HostConnector
|
3
|
-
class Base
|
4
|
-
include Celluloid
|
5
|
-
include Ridley::Logging
|
6
|
-
|
7
|
-
# Execute a shell command on a node
|
8
|
-
#
|
9
|
-
# @param [String] host
|
10
|
-
# the host to perform the action on
|
11
|
-
# @param [String] command
|
12
|
-
# @param [Hash] options
|
13
|
-
#
|
14
|
-
# @return [HostConnector::Response]
|
15
|
-
def run(host, command, options = {})
|
16
|
-
raise RuntimeError, "abstract function: must be implemented on includer"
|
17
|
-
end
|
18
|
-
|
19
|
-
# Bootstrap a node
|
20
|
-
#
|
21
|
-
# @param [String] host
|
22
|
-
# the host to perform the action on
|
23
|
-
# @param [Hash] options
|
24
|
-
#
|
25
|
-
# @return [HostConnector::Response]
|
26
|
-
def bootstrap(host, options = {})
|
27
|
-
raise RuntimeError, "abstract function: must be implemented on includer"
|
28
|
-
end
|
29
|
-
|
30
|
-
# Perform a chef client run on a node
|
31
|
-
#
|
32
|
-
# @param [String] host
|
33
|
-
# the host to perform the action on
|
34
|
-
# @param [Hash] options
|
35
|
-
#
|
36
|
-
# @return [HostConnector::Response]
|
37
|
-
def chef_client(host, options = {})
|
38
|
-
raise RuntimeError, "abstract function: must be implemented on includer"
|
39
|
-
end
|
40
|
-
|
41
|
-
# Write your encrypted data bag secret on a node
|
42
|
-
#
|
43
|
-
# @param [String] host
|
44
|
-
# the host to perform the action on
|
45
|
-
# @param [String] secret
|
46
|
-
# your organization's encrypted data bag secret
|
47
|
-
# @param [Hash] options
|
48
|
-
#
|
49
|
-
# @return [HostConnector::Response]
|
50
|
-
def put_secret(host, secret, options = {})
|
51
|
-
raise RuntimeError, "abstract function: must be implemented on includer"
|
52
|
-
end
|
53
|
-
|
54
|
-
# Execute line(s) of Ruby code on a node using Chef's embedded Ruby
|
55
|
-
#
|
56
|
-
# @param [String] host
|
57
|
-
# the host to perform the action on
|
58
|
-
# @param [Array<String>] command_lines
|
59
|
-
# An Array of lines of the command to be executed
|
60
|
-
# @param [Hash] options
|
61
|
-
#
|
62
|
-
# @return [HostConnector::Response]
|
63
|
-
def ruby_script(host, command_lines, options = {})
|
64
|
-
raise RuntimeError, "abstract function: must be implemented on includer"
|
65
|
-
end
|
66
|
-
|
67
|
-
# Uninstall Chef from a node
|
68
|
-
#
|
69
|
-
# @param [String] host
|
70
|
-
# the host to perform the action on
|
71
|
-
# @param [Hash] options
|
72
|
-
#
|
73
|
-
# @return [HostConnector::Response]
|
74
|
-
def uninstall_chef(host, options = {})
|
75
|
-
raise RuntimeError, "abstract function: must be implemented on includer"
|
76
|
-
end
|
77
|
-
end
|
78
|
-
|
79
|
-
require_relative 'host_connector/response'
|
80
|
-
require_relative 'host_connector/ssh'
|
81
|
-
require_relative 'host_connector/winrm'
|
82
|
-
end
|
83
|
-
end
|
@@ -1,27 +0,0 @@
|
|
1
|
-
module Ridley
|
2
|
-
module HostConnector
|
3
|
-
class Response
|
4
|
-
attr_reader :host
|
5
|
-
|
6
|
-
attr_accessor :stdout
|
7
|
-
attr_accessor :stderr
|
8
|
-
attr_accessor :exit_code
|
9
|
-
attr_accessor :exit_signal
|
10
|
-
|
11
|
-
def initialize(host, options = {})
|
12
|
-
@host = host
|
13
|
-
@stdout = options[:stdout] || String.new
|
14
|
-
@stderr = options[:stderr] || String.new
|
15
|
-
@exit_code = options[:exit_code] || -1
|
16
|
-
@exit_signal = options[:exit_signal] || nil
|
17
|
-
end
|
18
|
-
|
19
|
-
# Return true if the response was not successful
|
20
|
-
#
|
21
|
-
# @return [Boolean]
|
22
|
-
def error?
|
23
|
-
self.exit_code != 0
|
24
|
-
end
|
25
|
-
end
|
26
|
-
end
|
27
|
-
end
|
@@ -1,211 +0,0 @@
|
|
1
|
-
require 'net/ssh'
|
2
|
-
|
3
|
-
module Ridley
|
4
|
-
module HostConnector
|
5
|
-
class SSH < HostConnector::Base
|
6
|
-
DEFAULT_PORT = 22
|
7
|
-
EMBEDDED_RUBY_PATH = '/opt/chef/embedded/bin/ruby'.freeze
|
8
|
-
|
9
|
-
# Execute a shell command on a node
|
10
|
-
#
|
11
|
-
# @param [String] host
|
12
|
-
# the host to perform the action on
|
13
|
-
# @param [String] command
|
14
|
-
#
|
15
|
-
# @option options [Hash] :ssh
|
16
|
-
# * :user (String) a shell user that will login to each node and perform the bootstrap command on
|
17
|
-
# * :password (String) the password for the shell user that will perform the bootstrap
|
18
|
-
# * :keys (Array, String) an array of key(s) to authenticate the ssh user with instead of a password
|
19
|
-
# * :timeout (Float) timeout value for SSH bootstrap (5.0)
|
20
|
-
# * :sudo (Boolean) run as sudo
|
21
|
-
#
|
22
|
-
# @return [HostConnector::Response]
|
23
|
-
def run(host, command, options = {})
|
24
|
-
options = options.reverse_merge(ssh: Hash.new)
|
25
|
-
options[:ssh].reverse_merge!(port: DEFAULT_PORT, paranoid: false, sudo: false)
|
26
|
-
|
27
|
-
command = "sudo #{command}" if options[:ssh][:sudo]
|
28
|
-
|
29
|
-
Ridley::HostConnector::Response.new(host).tap do |response|
|
30
|
-
begin
|
31
|
-
log.info "Running SSH command: '#{command}' on: '#{host}' as: '#{options[:ssh][:user]}'"
|
32
|
-
|
33
|
-
defer {
|
34
|
-
Net::SSH.start(host, options[:ssh][:user], options[:ssh].slice(*Net::SSH::VALID_OPTIONS)) do |ssh|
|
35
|
-
ssh.open_channel do |channel|
|
36
|
-
if options[:sudo]
|
37
|
-
channel.request_pty do |channel, success|
|
38
|
-
unless success
|
39
|
-
raise "Could not aquire pty: A pty is required for running sudo commands."
|
40
|
-
end
|
41
|
-
|
42
|
-
channel_exec(channel, command, host, response)
|
43
|
-
end
|
44
|
-
else
|
45
|
-
channel_exec(channel, command, host, response)
|
46
|
-
end
|
47
|
-
end
|
48
|
-
ssh.loop
|
49
|
-
end
|
50
|
-
}
|
51
|
-
rescue Net::SSH::AuthenticationFailed => ex
|
52
|
-
response.exit_code = -1
|
53
|
-
response.stderr = "Authentication failure for user #{ex}"
|
54
|
-
rescue Net::SSH::ConnectionTimeout, Timeout::Error
|
55
|
-
response.exit_code = -1
|
56
|
-
response.stderr = "Connection timed out"
|
57
|
-
rescue Errno::EHOSTUNREACH
|
58
|
-
response.exit_code = -1
|
59
|
-
response.stderr = "Host unreachable"
|
60
|
-
rescue Errno::ECONNREFUSED
|
61
|
-
response.exit_code = -1
|
62
|
-
response.stderr = "Connection refused"
|
63
|
-
rescue Net::SSH::Exception => ex
|
64
|
-
response.exit_code = -1
|
65
|
-
response.stderr = ex.inspect
|
66
|
-
end
|
67
|
-
|
68
|
-
case response.exit_code
|
69
|
-
when 0
|
70
|
-
log.info "Successfully ran SSH command on: '#{host}' as: '#{options[:ssh][:user]}'"
|
71
|
-
when -1
|
72
|
-
log.info "Failed to run SSH command on: '#{host}' as: '#{options[:ssh][:user]}'"
|
73
|
-
else
|
74
|
-
log.info "Successfully ran SSH command on: '#{host}' as: '#{options[:ssh][:user]}' but it failed"
|
75
|
-
end
|
76
|
-
end
|
77
|
-
end
|
78
|
-
|
79
|
-
# Bootstrap a node
|
80
|
-
#
|
81
|
-
# @param [String] host
|
82
|
-
# the host to perform the action on
|
83
|
-
#
|
84
|
-
# @option options [Hash] :ssh
|
85
|
-
# * :user (String) a shell user that will login to each node and perform the bootstrap command on
|
86
|
-
# * :password (String) the password for the shell user that will perform the bootstrap
|
87
|
-
# * :keys (Array, String) an array of key(s) to authenticate the ssh user with instead of a password
|
88
|
-
# * :timeout (Float) timeout value for SSH bootstrap (5.0)
|
89
|
-
# * :sudo (Boolean) run as sudo
|
90
|
-
#
|
91
|
-
# @return [HostConnector::Response]
|
92
|
-
def bootstrap(host, options = {})
|
93
|
-
options = options.reverse_merge(ssh: Hash.new)
|
94
|
-
options[:ssh].reverse_merge!(sudo: true, timeout: 5.0)
|
95
|
-
context = BootstrapContext::Unix.new(options)
|
96
|
-
|
97
|
-
log.info "Bootstrapping host: #{host}"
|
98
|
-
run(host, context.boot_command, options)
|
99
|
-
end
|
100
|
-
|
101
|
-
# Perform a chef client run on a node
|
102
|
-
#
|
103
|
-
# @param [String] host
|
104
|
-
# the host to perform the action on
|
105
|
-
#
|
106
|
-
# @option options [Hash] :ssh
|
107
|
-
# * :user (String) a shell user that will login to each node and perform the bootstrap command on
|
108
|
-
# * :password (String) the password for the shell user that will perform the bootstrap
|
109
|
-
# * :keys (Array, String) an array of key(s) to authenticate the ssh user with instead of a password
|
110
|
-
# * :timeout (Float) timeout value for SSH bootstrap (5.0)
|
111
|
-
# * :sudo (Boolean) run as sudo
|
112
|
-
#
|
113
|
-
# @return [HostConnector::Response]
|
114
|
-
def chef_client(host, options = {})
|
115
|
-
run(host, "chef-client", options)
|
116
|
-
end
|
117
|
-
|
118
|
-
# Write your encrypted data bag secret on a node
|
119
|
-
#
|
120
|
-
# @param [String] host
|
121
|
-
# the host to perform the action on
|
122
|
-
# @param [String] secret
|
123
|
-
# your organization's encrypted data bag secret
|
124
|
-
#
|
125
|
-
# @option options [Hash] :ssh
|
126
|
-
# * :user (String) a shell user that will login to each node and perform the bootstrap command on
|
127
|
-
# * :password (String) the password for the shell user that will perform the bootstrap
|
128
|
-
# * :keys (Array, String) an array of key(s) to authenticate the ssh user with instead of a password
|
129
|
-
# * :timeout (Float) timeout value for SSH bootstrap (5.0)
|
130
|
-
# * :sudo (Boolean) run as sudo
|
131
|
-
#
|
132
|
-
# @return [HostConnector::Response]
|
133
|
-
def put_secret(host, secret, options = {})
|
134
|
-
cmd = "echo '#{secret}' > /etc/chef/encrypted_data_bag_secret; chmod 0600 /etc/chef/encrypted_data_bag_secret"
|
135
|
-
run(host, cmd, options)
|
136
|
-
end
|
137
|
-
|
138
|
-
# Execute line(s) of Ruby code on a node using Chef's embedded Ruby
|
139
|
-
#
|
140
|
-
# @param [String] host
|
141
|
-
# the host to perform the action on
|
142
|
-
# @param [Array<String>] command_lines
|
143
|
-
# An Array of lines of the command to be executed
|
144
|
-
#
|
145
|
-
# @option options [Hash] :ssh
|
146
|
-
# * :user (String) a shell user that will login to each node and perform the bootstrap command on
|
147
|
-
# * :password (String) the password for the shell user that will perform the bootstrap
|
148
|
-
# * :keys (Array, String) an array of key(s) to authenticate the ssh user with instead of a password
|
149
|
-
# * :timeout (Float) timeout value for SSH bootstrap (5.0)
|
150
|
-
# * :sudo (Boolean) run as sudo
|
151
|
-
#
|
152
|
-
# @return [HostConnector::Response]
|
153
|
-
def ruby_script(host, command_lines, options = {})
|
154
|
-
run(host, "#{EMBEDDED_RUBY_PATH} -e \"#{command_lines.join(';')}\"", options)
|
155
|
-
end
|
156
|
-
|
157
|
-
# Uninstall Chef from a node
|
158
|
-
#
|
159
|
-
# @param [String] host
|
160
|
-
# the host to perform the action on
|
161
|
-
#
|
162
|
-
# @option options [Boolena] :skip_chef (false)
|
163
|
-
# skip removal of the Chef package and the contents of the installation
|
164
|
-
# directory. Setting this to true will only remove any data and configurations
|
165
|
-
# generated by running Chef client.
|
166
|
-
# @option options [Hash] :ssh
|
167
|
-
# * :user (String) a shell user that will login to each node and perform the bootstrap command on
|
168
|
-
# * :password (String) the password for the shell user that will perform the bootstrap
|
169
|
-
# * :keys (Array, String) an array of key(s) to authenticate the ssh user with instead of a password
|
170
|
-
# * :timeout (Float) timeout value for SSH bootstrap (5.0)
|
171
|
-
# * :sudo (Boolean) run as sudo (true)
|
172
|
-
#
|
173
|
-
# @return [HostConnector::Response]
|
174
|
-
def uninstall_chef(host, options = {})
|
175
|
-
options = options.reverse_merge(ssh: Hash.new)
|
176
|
-
options[:ssh].reverse_merge!(sudo: true, timeout: 5.0)
|
177
|
-
|
178
|
-
log.info "Uninstalling Chef from host: #{host}"
|
179
|
-
run(host, CommandContext::UnixUninstall.command(options), options)
|
180
|
-
end
|
181
|
-
|
182
|
-
private
|
183
|
-
|
184
|
-
def channel_exec(channel, command, host, response)
|
185
|
-
channel.exec(command) do |ch, success|
|
186
|
-
unless success
|
187
|
-
raise "Channel execution failed while executing command #{command}"
|
188
|
-
end
|
189
|
-
|
190
|
-
channel.on_data do |ch, data|
|
191
|
-
response.stdout += data
|
192
|
-
log.info "[#{host}](SSH) #{data}" if data.present? and data != "\r\n"
|
193
|
-
end
|
194
|
-
|
195
|
-
channel.on_extended_data do |ch, type, data|
|
196
|
-
response.stderr += data
|
197
|
-
log.info "[#{host}](SSH) #{data}" if data.present? and data != "\r\n"
|
198
|
-
end
|
199
|
-
|
200
|
-
channel.on_request("exit-status") do |ch, data|
|
201
|
-
response.exit_code = data.read_long
|
202
|
-
end
|
203
|
-
|
204
|
-
channel.on_request("exit-signal") do |ch, data|
|
205
|
-
response.exit_signal = data.read_string
|
206
|
-
end
|
207
|
-
end
|
208
|
-
end
|
209
|
-
end
|
210
|
-
end
|
211
|
-
end
|