symphony-ssh 0.1.0 → 0.4.0

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
- SHA1:
3
- metadata.gz: ecf234436b7966c1062b9d13dbfe4c71015c29fe
4
- data.tar.gz: 89636ab1155f42de42d0bc9f74e45f6b51299e18
2
+ SHA256:
3
+ metadata.gz: f30fb65c28ed9ed46e7e4778e1a53ddc6a62e56c2d966ec51a7bf386bf111fb2
4
+ data.tar.gz: 8fb32494e41a1836deade9158906a803f16afa1b65baa350cf46936cec49525e
5
5
  SHA512:
6
- metadata.gz: a6b1681a726bbb2a554f2429c5dd11f3695e149c1341991088ad4deac99f0edd7728fcaca02480362cce98218dbe7b1e13dbfc1bcc01ef468df8199f3d9746df
7
- data.tar.gz: bcc024b3faed110b348714ee2925d13544448da998f5a9d145ff1d017ed69c8b244047fe18019c6234aa8143c05aa3db1d5803e9430da9724cbd3808bf6d1df6
6
+ metadata.gz: 73e175a3c18dfdcfd473d36ec4d2b8e47c4b613d7ceee7ef42dda2652a14f41c2fdc6e2c000fe13255115cb56cab582b235b30a4e5b780eae47fcf59b3304888
7
+ data.tar.gz: b2cbc3bbb891de3bc13d1623b2658b7dc6a0d7712135a11826a04a307d530e78d42ab751872e3c32647e4daec9a1629d7254a95aac517c733432b39168b94c3b
Binary file
Binary file
@@ -19,11 +19,12 @@ require 'symphony/task' unless defined?( Symphony::Task )
19
19
  ### command: (required) The command to run on the remote host
20
20
  ### port: (optional) The port to connect to (defaults to 22)
21
21
  ### opts: (optional) Explicit SSH client options
22
+ ### env: (optional) A hash of environment vars to set for the connection.
22
23
  ### user: (optional) The user to connect as (defaults to root)
23
24
  ### key: (optional) The path to an SSH private key
24
25
  ###
25
26
  ###
26
- ### Additionally, this class responds to the 'symphony_ssh' configurability
27
+ ### Additionally, this class responds to the 'symphony.ssh' configurability
27
28
  ### key. Currently, you can set the 'path' argument, which is the
28
29
  ### full path to the local ssh binary (defaults to '/usr/bin/ssh') and
29
30
  ### override the default ssh user, key, and client opts.
@@ -47,67 +48,55 @@ require 'symphony/task' unless defined?( Symphony::Task )
47
48
  ###
48
49
  class Symphony::Task::SSH < Symphony::Task
49
50
  extend Configurability
50
- config_key :symphony_ssh
51
51
 
52
- # SSH default options.
52
+ # The default set of ssh command line flags.
53
53
  #
54
- CONFIG_DEFAULTS = {
55
- :path => '/usr/bin/ssh',
56
- :opts => [
57
- '-e', 'none',
58
- '-T',
59
- '-x',
60
- '-q',
61
- '-o', 'CheckHostIP=no',
62
- '-o', 'BatchMode=yes',
63
- '-o', 'StrictHostKeyChecking=no'
64
- ],
65
- :user => 'root',
66
- :key => nil
67
- }
54
+ DEFAULT_SSH_OPTS = %w[
55
+ -e none
56
+ -T
57
+ -x
58
+ -q
59
+ -o CheckHostIP=no
60
+ -o BatchMode=yes
61
+ -o StrictHostKeyChecking=no
62
+ ]
68
63
 
69
64
  # SSH "informative" stdout output that should be cleaned from the
70
65
  # command output.
71
66
  SSH_CLEANUP = %r/Warning: no access to tty|Thus no job control in this shell/
72
67
 
73
- class << self
68
+
69
+ # Configurability API
70
+ #
71
+ configurability( :symphony__ssh ) do
72
+
74
73
  # The full path to the ssh binary.
75
- attr_reader :path
74
+ setting :path, default: '/usr/bin/ssh'
76
75
 
77
- # A default set of ssh client options when connecting
78
- # to remote hosts.
79
- attr_reader :opts
76
+ # The default user to use when connecting.
77
+ setting :user, default: 'root'
80
78
 
81
- # The default user to use when connecting. If unset, 'root' is used.
82
- attr_reader :user
79
+ # A default Array of ssh client options when connecting
80
+ # to remote hosts.
81
+ setting :opts, default: DEFAULT_SSH_OPTS do |val|
82
+ Array( val )
83
+ end
83
84
 
84
85
  # An absolute path to a password-free ssh private key.
85
- attr_reader :key
86
- end
87
-
88
- ### Configurability API.
89
- ###
90
- def self::configure( config=nil )
91
- config = self.defaults.merge( config || {} )
92
- @path = config.delete( :path )
93
- @opts = config.delete( :opts )
94
- @user = config.delete( :user )
95
- @key = config.delete( :key )
96
- super
86
+ setting :key
97
87
  end
98
88
 
99
89
 
100
- ### Perform the ssh connection, passing the command to the pipe
101
- ### and retreiving any output from the remote end.
90
+ ### Perform the ssh connection in 'exec' mode, and retrieve any
91
+ ### output from the remote end.
102
92
  ###
103
93
  def work( payload, metadata )
104
- command = payload[ 'command' ]
105
- raise ArgumentError, "Missing required option 'command'" unless command
94
+ raise ArgumentError, "Missing required option 'command'" unless payload[ 'command' ]
106
95
  raise ArgumentError, "Missing required option 'host'" unless payload[ 'host' ]
107
96
 
108
97
  exitcode = self.open_connection( payload, metadata ) do |reader, writer|
109
- self.log.debug "Writing command #{command}..."
110
- writer.puts( command )
98
+ #self.log.debug "Writing command #{command}..."
99
+ #writer.puts( command )
111
100
  self.log.debug " closing child's writer."
112
101
  writer.close
113
102
  self.log.debug " reading from child."
@@ -134,31 +123,46 @@ class Symphony::Task::SSH < Symphony::Task
134
123
  opts = payload[ 'opts' ] || Symphony::Task::SSH.opts
135
124
  user = payload[ 'user' ] || Symphony::Task::SSH.user
136
125
  key = payload[ 'key' ] || Symphony::Task::SSH.key
126
+ env = payload[ 'env' ] || {}
137
127
 
138
128
  cmd = []
139
129
  cmd << Symphony::Task::SSH.path
140
- cmd += Symphony::Task::SSH.opts
130
+ cmd += opts
141
131
 
142
132
  cmd << '-p' << port.to_s
143
133
  cmd << '-i' << key if key
144
134
  cmd << '-l' << user
145
135
  cmd << payload[ 'host' ]
136
+ cmd << payload[ 'command' ]
146
137
  cmd.flatten!
147
138
  self.log.debug "Running SSH command with: %p" % [ Shellwords.shelljoin(cmd) ]
148
139
 
149
140
  parent_reader, child_writer = IO.pipe
150
141
  child_reader, parent_writer = IO.pipe
151
142
 
152
- pid = spawn( *cmd, :out => child_writer, :in => child_reader, :close_others => true )
143
+ pid = Process.spawn( env, *cmd,
144
+ out: child_writer,
145
+ in: child_reader,
146
+ close_others: true,
147
+ unsetenv_others: true
148
+ )
149
+
153
150
  child_writer.close
154
151
  child_reader.close
155
152
 
156
153
  self.log.debug "Yielding back to the run block."
157
154
  @output = yield( parent_reader, parent_writer )
158
- @output = @output.split("\n").reject{|l| l =~ SSH_CLEANUP }.join
155
+ @output = @output.split( /\r?\n/ ).reject{|l| l =~ SSH_CLEANUP }.join
159
156
  self.log.debug " run block done."
160
157
 
161
- pid, status = Process.waitpid2( pid )
158
+ rescue => err
159
+ self.log.error( err.message )
160
+ ensure
161
+ if pid
162
+ active = Process.kill( 0, pid ) rescue false
163
+ Process.kill( :TERM, pid ) if active
164
+ pid, status = Process.waitpid2( pid )
165
+ end
162
166
  return status
163
167
  end
164
168
 
@@ -1,12 +1,13 @@
1
1
  #!/usr/bin/env ruby
2
2
  # vim: set nosta noet ts=4 sw=4:
3
3
 
4
+ require 'securerandom'
4
5
  require 'net/ssh'
5
6
  require 'net/sftp'
6
- require 'tmpdir'
7
7
  require 'inversion'
8
8
  require 'symphony'
9
9
  require 'symphony/task'
10
+ require 'symphony/tasks/ssh'
10
11
 
11
12
 
12
13
  ### A base class for connecting to a remote host, then uploading and
@@ -26,9 +27,12 @@ require 'symphony/task'
26
27
  ### key: (optional) The path to an SSH private key
27
28
  ### attributes: (optional) Additional data to attach to the template
28
29
  ### nocleanup: (optional) Leave the remote script after execution? (default to false)
30
+ ### delete_cmd: (optional) The command to delete the remote script. (default to 'rm')
31
+ ### run_binary: (optional) Windows doesn't allow direct execution of scripts, this is prefixed to the remote command if present.
32
+ ### tempdir: (optional) The destination temp directory. (defaults to /tmp/, needs to include the separator character)
29
33
  ###
30
34
  ###
31
- ### Additionally, this class responds to the 'symphony_ssh' configurability
35
+ ### Additionally, this class responds to the 'symphony.ssh' configurability
32
36
  ### key. Currently, you can override the default ssh user and private key.
33
37
  ###
34
38
  ### Textual output of the command is stored in the @output instance variable.
@@ -49,53 +53,27 @@ require 'symphony/task'
49
53
  ### end
50
54
  ###
51
55
  class Symphony::Task::SSHScript < Symphony::Task
52
- extend Configurability
53
- config_key :symphony_ssh
54
56
 
55
57
  # Template config
56
58
  #
57
59
  TEMPLATE_OPTS = {
58
- :ignore_unknown_tags => false,
59
- :on_render_error => :propagate,
60
- :strip_tag_lines => true
60
+ ignore_unknown_tags: false,
61
+ on_render_error: :propagate,
62
+ strip_tag_lines: true
61
63
  }
62
64
 
63
65
  # The defaults to use when connecting via SSH
64
66
  #
65
67
  DEFAULT_SSH_OPTIONS = {
66
- :auth_methods => [ 'publickey' ],
67
- :compression => true,
68
- :config => false,
69
- :keys_only => true,
70
- :paranoid => false,
71
- :global_known_hosts_file => '/dev/null',
72
- :user_known_hosts_file => '/dev/null'
68
+ auth_methods: [ 'publickey' ],
69
+ compression: true,
70
+ config: false,
71
+ keys_only: true,
72
+ verify_host_key: :never,
73
+ global_known_hosts_file: '/dev/null',
74
+ user_known_hosts_file: '/dev/null'
73
75
  }
74
76
 
75
- # SSH default options.
76
- #
77
- CONFIG_DEFAULTS = {
78
- :user => 'root',
79
- :key => nil
80
- }
81
-
82
- class << self
83
- # The default user to use when connecting. If unset, 'root' is used.
84
- attr_reader :user
85
-
86
- # An absolute path to a password-free ssh private key.
87
- attr_reader :key
88
- end
89
-
90
- ### Configurability API.
91
- ###
92
- def self::configure( config=nil )
93
- config = self.defaults.merge( config || {} )
94
- @user = config.delete( :user )
95
- @key = config.delete( :key )
96
- super
97
- end
98
-
99
77
 
100
78
  ### Perform the ssh connection, render the template, send it, and
101
79
  ### execute it.
@@ -103,21 +81,30 @@ class Symphony::Task::SSHScript < Symphony::Task
103
81
  def work( payload, metadata )
104
82
  template = payload[ 'template' ]
105
83
  attributes = payload[ 'attributes' ] || {}
106
- port = payload[ 'port' ] || 22
107
- user = payload[ 'user' ] || Symphony::Task::SSHScript.user
108
- key = payload[ 'key' ] || Symphony::Task::SSHScript.key
109
- nocleanup = payload[ 'nocleanup' ]
84
+ user = payload[ 'user' ] || Symphony::Task::SSH.user
85
+ key = payload[ 'key' ] || Symphony::Task::SSH.key
86
+ tempdir = payload[ 'tempdir' ] || '/tmp/'
110
87
 
111
- raise ArgumentError, "Missing required option 'command'" unless template
112
- raise ArgumentError, "Missing required option 'host'" unless payload[ 'host' ]
88
+ raise ArgumentError, "Missing required option 'template'" unless template
89
+ raise ArgumentError, "Missing required option 'host'" unless payload[ 'host' ]
113
90
 
114
- remote_filename = self.make_remote_filename( template )
91
+ remote_filename = self.make_remote_filename( template, tempdir )
115
92
  source = self.generate_script( template, attributes )
116
93
 
117
- ssh_options = DEFAULT_SSH_OPTIONS.merge( :port => port, :keys => [key] )
94
+ # Map any configuration parameters in the payload to ssh
95
+ # options, for potential per-message behavior overrides.
96
+ ssh_opts_override = payload.
97
+ slice( *DEFAULT_SSH_OPTIONS.keys.map( &:to_s ) ).
98
+ transform_keys{|k| k.to_sym }
99
+
100
+ ssh_options = DEFAULT_SSH_OPTIONS.dup.merge!(
101
+ ssh_opts_override,
102
+ port: payload[ 'port' ] || 22,
103
+ keys: Array( key )
104
+ )
118
105
  ssh_options.merge!(
119
- :logger => Loggability[ Net::SSH ],
120
- :verbose => :debug
106
+ logger: Loggability[ Net::SSH ],
107
+ verbose: :debug
121
108
  ) if payload[ 'debug' ]
122
109
 
123
110
  Net::SSH.start( payload['host'], user, ssh_options ) do |conn|
@@ -126,7 +113,7 @@ class Symphony::Task::SSHScript < Symphony::Task
126
113
  self.upload_script( conn, source, remote_filename )
127
114
  self.log.debug " done with the upload."
128
115
 
129
- self.run_script( conn, remote_filename, nocleanup )
116
+ self.run_script( conn, remote_filename, payload )
130
117
  self.log.debug "Output was:\n#{@output}"
131
118
  end
132
119
 
@@ -141,11 +128,15 @@ class Symphony::Task::SSHScript < Symphony::Task
141
128
  ### Generate a unique filename for the script on the remote host,
142
129
  ### based on +template+ name.
143
130
  ###
144
- def make_remote_filename( template )
131
+ def make_remote_filename( template, tempdir="/tmp/" )
145
132
  basename = File.basename( template, File.extname(template) )
146
- tmpname = Dir::Tmpname.make_tmpname( basename, rand(10000) )
133
+ tmpname = "%s%s-%s" % [
134
+ tempdir,
135
+ basename,
136
+ SecureRandom.hex( 6 )
137
+ ]
147
138
 
148
- return "/tmp/#{tmpname}"
139
+ return tmpname
149
140
  end
150
141
 
151
142
 
@@ -172,11 +163,16 @@ class Symphony::Task::SSHScript < Symphony::Task
172
163
 
173
164
 
174
165
  ### Run the +remote_filename+ via the ssh +conn+. The script
175
- ### will be deleted automatically unless +nocleanup+ is true.
166
+ ### will be deleted automatically unless +nocleanup+ is set
167
+ ### in the payload.
176
168
  ###
177
- def run_script( conn, remote_filename, nocleanup=false )
178
- @output = conn.exec!( remote_filename )
179
- conn.exec!( "rm #{remote_filename}" ) unless nocleanup
169
+ def run_script( conn, remote_filename, payload )
170
+ delete_cmd = payload[ 'delete_cmd' ] || 'rm'
171
+ command = remote_filename
172
+ command = "%s %s" % [ payload['run_binary'], remote_filename ] if payload[ 'run_binary' ]
173
+
174
+ @output = conn.exec!( command )
175
+ conn.exec!( "#{delete_cmd} #{remote_filename}" ) unless payload[ 'nocleanup' ]
180
176
  end
181
177
 
182
178
  end # Symphony::Task::SSHScript
metadata CHANGED
@@ -1,103 +1,159 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: symphony-ssh
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 0.4.0
5
5
  platform: ruby
6
6
  authors:
7
- - Mahlon E. Smith <mahlon@martini.nu>
8
- - Michael Granger <ged@faeriemud.org>
7
+ - Mahlon E. Smith
8
+ - Michael Granger
9
9
  autorequire:
10
10
  bindir: bin
11
- cert_chain: []
12
- date: 2014-05-11 00:00:00.000000000 Z
11
+ cert_chain:
12
+ - |
13
+ -----BEGIN CERTIFICATE-----
14
+ MIIDMDCCAhigAwIBAgIBAjANBgkqhkiG9w0BAQsFADA+MQ8wDQYDVQQDDAZtYWhs
15
+ b24xFzAVBgoJkiaJk/IsZAEZFgdtYXJ0aW5pMRIwEAYKCZImiZPyLGQBGRYCbnUw
16
+ HhcNMjAwNzA5MjIxMzE4WhcNMjEwNzA5MjIxMzE4WjA+MQ8wDQYDVQQDDAZtYWhs
17
+ b24xFzAVBgoJkiaJk/IsZAEZFgdtYXJ0aW5pMRIwEAYKCZImiZPyLGQBGRYCbnUw
18
+ ggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDpXGN0YbMVpYv4EoiCxpQw
19
+ sxKdyhlkvpvENUkpEhbpnEuMKXgUfRHO4T/vBZf0h8eYgwnrHCRhAeIqesFKfoj9
20
+ mpEJk5JUuADOAz18aT+v24UqAtJdiwBJLuqhslSNB6CFXZv3OOMny9bjoJegz0hI
21
+ Fht9ppCuNmxJNd+L3zAX8lD01RUWNRC+8L5QLCjViJtjFDDCFfh9NCirs+XnTCzo
22
+ AJgFbsZIzFJtSiXUtFgscKr4Ik8ruhRbPbYbmx9rf6W74aTMPxggq/d3gj0Eh32y
23
+ WsXsQ5giVnmkbsRkBNu3QyZ8Xr5+7mvy5AWyqXKOrcW7lnYaob6Z9x/MGXGNeD6j
24
+ AgMBAAGjOTA3MAkGA1UdEwQCMAAwCwYDVR0PBAQDAgSwMB0GA1UdDgQWBBRY8ea6
25
+ +6kAaW7ukKph2/4MTAD8/TANBgkqhkiG9w0BAQsFAAOCAQEAryZehbiEumHsUsce
26
+ FoBVuDoVdlJf8ae11G8IPXnEHCT8S5b+MBSYd55V3aGQm4bKoZA3GmmD8Y0a+oxt
27
+ l2kkTvE0r1bBb/qYQI97AjnqzHByseBRoaHtJ12JtrDEdi8y4jd5AJt4aW+G/roD
28
+ I2/ymUodKw9Cteom0RdJNzBUJ+Bq+qFOy7mVKNIfhXRRFYEy11y1712FsJXqUEku
29
+ qr3lnAEvEy9hQila4NoJT2+aQEKsjVON9D3a727naKDFUcKDg6P4KqS+yOKgR+QH
30
+ D8llK3JPaqKXuJkbd8jKchDk0Q+fA8Klan5SSnm7pMD51QM1mPsVPm5bEw5ib0bn
31
+ oR3hTQ==
32
+ -----END CERTIFICATE-----
33
+ date: 2020-07-16 00:00:00.000000000 Z
13
34
  dependencies:
35
+ - !ruby/object:Gem::Dependency
36
+ name: configurability
37
+ requirement: !ruby/object:Gem::Requirement
38
+ requirements:
39
+ - - ">="
40
+ - !ruby/object:Gem::Version
41
+ version: '3.2'
42
+ - - "<="
43
+ - !ruby/object:Gem::Version
44
+ version: '4.99'
45
+ type: :runtime
46
+ prerelease: false
47
+ version_requirements: !ruby/object:Gem::Requirement
48
+ requirements:
49
+ - - ">="
50
+ - !ruby/object:Gem::Version
51
+ version: '3.2'
52
+ - - "<="
53
+ - !ruby/object:Gem::Version
54
+ version: '4.99'
14
55
  - !ruby/object:Gem::Dependency
15
56
  name: symphony
16
57
  requirement: !ruby/object:Gem::Requirement
17
58
  requirements:
18
- - - ~>
59
+ - - "~>"
60
+ - !ruby/object:Gem::Version
61
+ version: '0.13'
62
+ type: :runtime
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - "~>"
67
+ - !ruby/object:Gem::Version
68
+ version: '0.13'
69
+ - !ruby/object:Gem::Dependency
70
+ name: inversion
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - "~>"
19
74
  - !ruby/object:Gem::Version
20
- version: '0.6'
75
+ version: '1.3'
21
76
  type: :runtime
22
77
  prerelease: false
23
78
  version_requirements: !ruby/object:Gem::Requirement
24
79
  requirements:
25
- - - ~>
80
+ - - "~>"
26
81
  - !ruby/object:Gem::Version
27
- version: '0.6'
82
+ version: '1.3'
28
83
  - !ruby/object:Gem::Dependency
29
84
  name: net-ssh
30
85
  requirement: !ruby/object:Gem::Requirement
31
86
  requirements:
32
- - - ~>
87
+ - - "~>"
33
88
  - !ruby/object:Gem::Version
34
- version: '2.9'
89
+ version: '6.0'
35
90
  type: :runtime
36
91
  prerelease: false
37
92
  version_requirements: !ruby/object:Gem::Requirement
38
93
  requirements:
39
- - - ~>
94
+ - - "~>"
40
95
  - !ruby/object:Gem::Version
41
- version: '2.9'
96
+ version: '6.0'
42
97
  - !ruby/object:Gem::Dependency
43
98
  name: net-sftp
44
99
  requirement: !ruby/object:Gem::Requirement
45
100
  requirements:
46
- - - ~>
101
+ - - "~>"
47
102
  - !ruby/object:Gem::Version
48
- version: '2.1'
103
+ version: '3.0'
49
104
  type: :runtime
50
105
  prerelease: false
51
106
  version_requirements: !ruby/object:Gem::Requirement
52
107
  requirements:
53
- - - ~>
108
+ - - "~>"
54
109
  - !ruby/object:Gem::Version
55
- version: '2.1'
110
+ version: '3.0'
56
111
  - !ruby/object:Gem::Dependency
57
112
  name: rspec
58
113
  requirement: !ruby/object:Gem::Requirement
59
114
  requirements:
60
- - - ~>
115
+ - - "~>"
61
116
  - !ruby/object:Gem::Version
62
- version: '3.0'
117
+ version: '3.9'
63
118
  type: :development
64
119
  prerelease: false
65
120
  version_requirements: !ruby/object:Gem::Requirement
66
121
  requirements:
67
- - - ~>
122
+ - - "~>"
68
123
  - !ruby/object:Gem::Version
69
- version: '3.0'
124
+ version: '3.9'
70
125
  - !ruby/object:Gem::Dependency
71
126
  name: simplecov
72
127
  requirement: !ruby/object:Gem::Requirement
73
128
  requirements:
74
- - - ~>
129
+ - - "~>"
75
130
  - !ruby/object:Gem::Version
76
- version: '0.8'
131
+ version: '0.18'
77
132
  type: :development
78
133
  prerelease: false
79
134
  version_requirements: !ruby/object:Gem::Requirement
80
135
  requirements:
81
- - - ~>
136
+ - - "~>"
82
137
  - !ruby/object:Gem::Version
83
- version: '0.8'
138
+ version: '0.18'
84
139
  description: |
85
140
  A small collection of base classes used for interacting with remote
86
141
  machines over ssh. With them, you can use AMQP (via Symphony) to
87
142
  run batch commands, execute templates as scripts, and perform any
88
143
  batch/remoting stuff you can think of without the need of separate
89
144
  client agents.
90
- email: mahlon@martini.nu
145
+ email:
146
+ - mahlon@martini.nu
147
+ - ged@faeriemud.org
91
148
  executables: []
92
149
  extensions: []
93
150
  extra_rdoc_files: []
94
151
  files:
95
- - README.rdoc
96
152
  - lib/symphony/tasks/ssh.rb
97
153
  - lib/symphony/tasks/sshscript.rb
98
154
  homepage: http://projects.martini.nu/ruby-modules
99
155
  licenses:
100
- - BSD
156
+ - BSD-3-Clause
101
157
  metadata: {}
102
158
  post_install_message:
103
159
  rdoc_options: []
@@ -105,17 +161,16 @@ require_paths:
105
161
  - lib
106
162
  required_ruby_version: !ruby/object:Gem::Requirement
107
163
  requirements:
108
- - - '>='
164
+ - - ">="
109
165
  - !ruby/object:Gem::Version
110
- version: 2.0.0
166
+ version: 2.6.0
111
167
  required_rubygems_version: !ruby/object:Gem::Requirement
112
168
  requirements:
113
- - - '>='
169
+ - - ">="
114
170
  - !ruby/object:Gem::Version
115
- version: 2.0.3
171
+ version: '0'
116
172
  requirements: []
117
- rubyforge_project:
118
- rubygems_version: 2.2.2
173
+ rubygems_version: 3.1.2
119
174
  signing_key:
120
175
  specification_version: 4
121
176
  summary: Base classes for using Symphony with ssh.
Binary file
@@ -1,113 +0,0 @@
1
-
2
- = symphony-ssh
3
-
4
- == Description
5
-
6
- This is a small collection of base classes used for interacting with
7
- remote machines over ssh. With them, you can use AMQP (via Symphony) to
8
- run batch commands, execute templates as scripts, and perform any
9
- batch/remoting stuff you can think of without the need of a separate
10
- client agent.
11
-
12
- These classes assume you have a user that can connect and login to
13
- remote machines using a password-less ssh keypair. They are not meant
14
- to be used directly. Subclass them!
15
-
16
- See the rdoc for additional information and examples.
17
-
18
-
19
- == Options
20
-
21
- Symphony-ssh uses
22
- Configurability[https://rubygems.org/gems/configurability] to determine
23
- behavior. The configuration is a YAML[http://www.yaml.org/] file.
24
-
25
- symphony_ssh:
26
- path: /usr/bin/ssh
27
- user: root
28
- key: /path/to/a/private_key.rsa
29
- opts:
30
- - -e
31
- - none
32
- - -T
33
- - -x
34
- - -o
35
- - CheckHostIP=no'
36
- - -o
37
- - BatchMode=yes'
38
- - -o
39
- - StrictHostKeyChecking=no
40
-
41
-
42
-
43
- === path
44
-
45
- The absolute path to the ssh binary.
46
-
47
- === user
48
-
49
- The default user to connect to remote hosts with. This can be
50
- changes per connection in the AMQP payload.
51
-
52
- === key
53
-
54
- An absolute path to a password-less ssh private key.
55
-
56
- === opts
57
-
58
- SSH client options, passed to the ssh binary on the command line. Note
59
- that the defaults have been tested fairly extensively, these are just
60
- exposed if you have very specific needs and you know what you're doing.
61
-
62
-
63
- == Installation
64
-
65
- gem install symphony-ssh
66
-
67
-
68
- == Contributing
69
-
70
- You can check out the current development source with Mercurial via its
71
- {project page}[http://bitbucket.org/mahlon/symphony-ssh].
72
-
73
- After checking out the source, run:
74
-
75
- $ rake
76
-
77
- This task will run the tests/specs and generate the API documentation.
78
-
79
- If you use {rvm}[http://rvm.io/], entering the project directory will
80
- install any required development dependencies.
81
-
82
-
83
- == License
84
-
85
- Copyright (c) 2014, Mahlon E. Smith and Michael Granger
86
- All rights reserved.
87
-
88
- Redistribution and use in source and binary forms, with or without
89
- modification, are permitted provided that the following conditions are met:
90
-
91
- * Redistributions of source code must retain the above copyright notice,
92
- this list of conditions and the following disclaimer.
93
-
94
- * Redistributions in binary form must reproduce the above copyright notice,
95
- this list of conditions and the following disclaimer in the documentation
96
- and/or other materials provided with the distribution.
97
-
98
- * Neither the name of the author/s, nor the names of the project's
99
- contributors may be used to endorse or promote products derived from this
100
- software without specific prior written permission.
101
-
102
- THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
103
- AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
104
- IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
105
- DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE
106
- FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
107
- DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
108
- SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
109
- CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
110
- OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
111
- OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
112
-
113
-