net-ssh 3.0.1 → 3.0.2.rc1

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.
@@ -0,0 +1,93 @@
1
+ require_relative './common'
2
+ require 'net/ssh/buffer'
3
+ require 'net/ssh'
4
+ require 'timeout'
5
+ require 'tempfile'
6
+ require 'net/ssh/proxy/command'
7
+
8
+ class TestProxy < Test::Unit::TestCase
9
+ include IntegrationTestHelpers
10
+
11
+ def localhost
12
+ 'localhost'
13
+ end
14
+
15
+ def user
16
+ 'net_ssh_1'
17
+ end
18
+
19
+ def ssh_start_params(options)
20
+ [localhost ,user , {:keys => @key_id_rsa, :verbose => :debug}.merge(options)]
21
+ end
22
+
23
+ def setup_ssh_env(&block)
24
+ tmpdir do |dir|
25
+ @key_id_rsa = "#{dir}/id_rsa"
26
+ sh "rm -rf #{@key_id_rsa} #{@key_id_rsa}.pub"
27
+ sh "ssh-keygen -f #{@key_id_rsa} -t rsa -N ''"
28
+ set_authorized_key(user,"#{@key_id_rsa}.pub")
29
+ yield
30
+ end
31
+ end
32
+
33
+ def test_smoke
34
+ setup_ssh_env do
35
+ proxy = Net::SSH::Proxy::Command.new("/bin/nc localhost 22")
36
+ msg = 'echo123'
37
+ ret = Net::SSH.start(*ssh_start_params(:proxy => proxy)) do |ssh|
38
+ ssh.exec! "echo \"$USER:#{msg}\""
39
+ end
40
+ assert_equal "net_ssh_1:#{msg}\n", ret
41
+ end
42
+ end
43
+
44
+ def with_spurious_write_wakeup_emulate(rate=99,&block)
45
+ orig_io_select = Net::SSH::Compat.method(:io_select)
46
+ count = 0
47
+ Net::SSH::Compat.singleton_class.send(:define_method,:io_select) do |*params|
48
+ count += 1
49
+ if (count % rate != 0)
50
+ if params && params[1] && !params[1].empty?
51
+ return [[],params[1],[]]
52
+ end
53
+ #if params && params[0] && !params[0].empty?
54
+ #return [params[0],[],[]]
55
+ #end
56
+ end
57
+ IO.select(*params)
58
+ end
59
+ begin
60
+ yield
61
+ ensure
62
+ Net::SSH::Compat.singleton_class.send(:define_method,:io_select,&orig_io_select)
63
+ end
64
+ end
65
+
66
+ def test_with_rate_limit_and_spurious_wakeup
67
+ system("sudo sh -c 'echo 4096 > /proc/sys/fs/pipe-max-size'")
68
+ begin
69
+ setup_ssh_env do
70
+ proxy = Net::SSH::Proxy::Command.new("/usr/bin/pv --rate-limit 100k | /bin/nc localhost 22")
71
+ #proxy = Net::SSH::Proxy::Command.new("/bin/nc localhost 22")
72
+ begin
73
+ large_msg = 'echo123'*30000
74
+ ok = Net::SSH.start(*ssh_start_params(:proxy => proxy)) do |ssh|
75
+ with_spurious_write_wakeup_emulate do
76
+ ret = ssh.exec! "echo \"$USER:#{large_msg}\""
77
+ #assert_equal "net_ssh_1:#{large_msg}\n", ret
78
+ assert_equal "/bin/sh: Argument list too long\n", ret
79
+ hello_count = 1000
80
+ ret = ssh.exec! "ruby -e 'puts \"Hello\"*#{hello_count}'"
81
+ assert_equal "Hello"*hello_count+"\n", ret
82
+ end
83
+ :ok
84
+ end
85
+ end
86
+ assert_equal :ok, ok
87
+ end
88
+ ensure
89
+ system("sudo sh -c 'echo 1048576 > /proc/sys/fs/pipe-max-size'")
90
+ end
91
+ end
92
+
93
+ end
@@ -0,0 +1,27 @@
1
+ require 'common'
2
+ require 'net/ssh'
3
+
4
+ module NetSSH
5
+ class TestStartUserNil < Test::Unit::TestCase
6
+ def setup
7
+ @authentication_session = mock('authentication_session')
8
+ Net::SSH::Authentication::Session.stubs(:new).returns(@authentication_session)
9
+ Net::SSH::Transport::Session.stubs(:new).returns(mock('transport_session'))
10
+ Net::SSH::Connection::Session.stubs(:new).returns(mock('connection_session'))
11
+ end
12
+
13
+ def test_start_should_accept_nil_user
14
+ @authentication_session.stubs(:authenticate).returns(true)
15
+ assert_nothing_raised do
16
+ Net::SSH.start('localhost')
17
+ end
18
+ end
19
+
20
+ def test_start_should_use_default_user_when_nil
21
+ @authentication_session.stubs(:authenticate).with() {|_next_service, user, _password| user == Etc.getlogin }.returns(true)
22
+ assert_nothing_raised do
23
+ Net::SSH.start('localhost')
24
+ end
25
+ end
26
+ end
27
+ end
data/test/test_all.rb CHANGED
@@ -4,7 +4,7 @@ $: << '.'
4
4
  # $ ruby -Ilib -Itest -rrubygems test/transport/test_server_version.rb
5
5
  Dir.chdir(File.dirname(__FILE__)) do
6
6
  test_files = Dir['**/test_*.rb']-['test_all.rb'] # prevent circular require
7
- test_files -= Dir['integration/test_*.rb']
7
+ test_files -= Dir['integration/test_*.rb'] unless ENV['NET_SSH_RUN_INTEGRATION_TESTS']
8
8
  test_files = test_files.reject { |f| f =~ /^manual/ }
9
9
  test_files = test_files.select { |f| f =~ Regexp.new(ENV['ONLY']) } if ENV['ONLY']
10
10
  test_files = test_files.reject { |f| f =~ Regexp.new(ENV['EXCEPT']) } if ENV['EXCEPT']
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: net-ssh
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.0.1
4
+ version: 3.0.2.rc1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jamis Buck
@@ -14,24 +14,24 @@ cert_chain:
14
14
  -----BEGIN CERTIFICATE-----
15
15
  MIIDODCCAiCgAwIBAgIBADANBgkqhkiG9w0BAQUFADBCMRAwDgYDVQQDDAduZXQt
16
16
  c3NoMRkwFwYKCZImiZPyLGQBGRYJc29sdXRpb3VzMRMwEQYKCZImiZPyLGQBGRYD
17
- Y29tMB4XDTE0MTIwMjE3MzkyMFoXDTE1MTIwMjE3MzkyMFowQjEQMA4GA1UEAwwH
17
+ Y29tMB4XDTE1MTIwNjIxMDYyNFoXDTE2MTIwNTIxMDYyNFowQjEQMA4GA1UEAwwH
18
18
  bmV0LXNzaDEZMBcGCgmSJomT8ixkARkWCXNvbHV0aW91czETMBEGCgmSJomT8ixk
19
- ARkWA2NvbTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAJ0qnw4JV5JN
20
- MWelqu7pnW2z6GZJ7+zLFYJQNETJyF0U5zo7aCRK08OeUxnpu/TCCXK8iQVkNLfz
21
- 9pVIhF+X8pMEIruAkYGwBt1aWfuSNeyodyMk0vpZdxBHbOTJ4qBRUc6qOtNOeOzv
22
- 8ObYUX52P/EMMaeXTRU+e7MGkB9pb6FvPPNx5akxwIaoRvtcMsc/hJnQuP5r96w6
23
- t06MgKbXhWAX6gev0RVlrQqzxXst6iuvsrgZGjFqzob5wbTiX9M0+bFAB0EI7tJC
24
- sv5keEbtNRaU7p3ZbMm4wTHHJLOtD+BpUCSzwv4ToNj9mZtJBMYw2Eeo7z1DklEG
25
- mr95zbe+zNMCAwEAAaM5MDcwCQYDVR0TBAIwADAdBgNVHQ4EFgQU1bTfpzmitXwv
26
- LmTXi0IO5vd8NGYwCwYDVR0PBAQDAgSwMA0GCSqGSIb3DQEBBQUAA4IBAQA0Aps8
27
- UPINGa8XUUtrZtzrgX0/iyXNkKY1ld85g1N3WKEAVLfQI7TlGr0Qv2Ekx6RqlxbR
28
- Vyq08pytSnghW2otR3bIGMGQzqxAeRLb25cjEwH7YIJ32n7ZC1fpMnBZOBDmueWA
29
- B9EonmoO3ne7AJSgIvBbZzBPhzM4HrQGRW8LsPFsuj+dcJI43HOQwkmv2TRz0+t6
30
- mGZldmqLcK0abv4JepLfB9XTue3kuyA29NGBibqyvRwlKckLpvKfHZX6Jxad8xxm
31
- MbvRpzgROzyfw1qYi4dnIyMwTtXFFcZ0a2jpxHPkcTYFK6TzvFgDLAP0Y/u9jqUQ
32
- eZ7/3CdSi/isZHEw
19
+ ARkWA2NvbTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMYnhNtn0f6p
20
+ nTylB8mE8lMdoMLJC8KwpMWsvk73Pe2WVDsH/OSwwwz6oUGk1i70cJyDjIEBNpwT
21
+ 88GpVXJSumvqVsf9fCg3mWNeb5t0J+aeNm9MIvYVMTqj5tydoXQiwnILRDYHV9tZ
22
+ 1c3o59/VlahSTpZ7YEgzVufpAkvEGkbJiG849exiipK7MN/ZIkMOxYVnyRXk43Xc
23
+ 6GYlsHOfSgPwcXwW5g57DCwLQLWrjDsTka28dxDmO7B5Lv5EqzINxVxWsu43OgZG
24
+ 21Io/jIyf5PNpeKPKNGDuAQJ8mvdMYBJoDhtCwgsUYbl0BZzA7g4ytl51HtIeP+j
25
+ Qp/eAvs/RrECAwEAAaM5MDcwCQYDVR0TBAIwADAdBgNVHQ4EFgQUBfKiwO2eM4NE
26
+ iRrVG793qEPLYyMwCwYDVR0PBAQDAgSwMA0GCSqGSIb3DQEBBQUAA4IBAQCfZFdb
27
+ p4jzkfIzGDbiOxd0R8sdqJoC4nMLEgnQ7dLulawwA3IXe3sHAKgA5kmH3prsKc5H
28
+ zVmM5NlH2P1nRbegIkQTYiIod1hZQCNxdmVG/fprMqPq0ybpUOjjrP5pj0OtszE1
29
+ F2dQia1hOEstMR+n0nAtWII9HJAEyeZjVV0s2Cl7Pt85XJ3hxFcCKwzqsK5xRI7a
30
+ B3vwh3/JJYrFonIohQ//Lg9qTZASEkoKLlq1/hFeICoCGGIGLq45ZB7CzXLooCKi
31
+ s/ZUKye79ELwFYKJOhjW5g725OL3hy+llhEleytwKRwgXFQBPTC4f5UkdxZVVWGH
32
+ e2C9M1m/2odPZo8h
33
33
  -----END CERTIFICATE-----
34
- date: 2015-09-25 00:00:00.000000000 Z
34
+ date: 2015-12-10 00:00:00.000000000 Z
35
35
  dependencies:
36
36
  - !ruby/object:Gem::Dependency
37
37
  name: test-unit
@@ -195,14 +195,16 @@ files:
195
195
  - test/integration/Vagrantfile
196
196
  - test/integration/common.rb
197
197
  - test/integration/playbook.yml
198
+ - test/integration/test_forward.rb
198
199
  - test/integration/test_id_rsa_keys.rb
200
+ - test/integration/test_proxy.rb
199
201
  - test/known_hosts/github
200
202
  - test/known_hosts/github_hash
201
- - test/manual/test_forward.rb
202
203
  - test/manual/test_pageant.rb
203
204
  - test/start/test_connection.rb
204
205
  - test/start/test_options.rb
205
206
  - test/start/test_transport.rb
207
+ - test/start/test_user_nil.rb
206
208
  - test/test_all.rb
207
209
  - test/test_buffer.rb
208
210
  - test/test_buffered_io.rb
@@ -249,9 +251,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
249
251
  version: '2.0'
250
252
  required_rubygems_version: !ruby/object:Gem::Requirement
251
253
  requirements:
252
- - - ">="
254
+ - - ">"
253
255
  - !ruby/object:Gem::Version
254
- version: '0'
256
+ version: 1.3.1
255
257
  requirements: []
256
258
  rubyforge_project: net-ssh
257
259
  rubygems_version: 2.4.6
metadata.gz.sig CHANGED
Binary file
@@ -1,285 +0,0 @@
1
- # $ ruby -Ilib -Itest -rrubygems test/manual/test_forward.rb
2
-
3
- # Tests for the following patch:
4
- #
5
- # http://github.com/net-ssh/net-ssh/tree/portfwfix
6
- #
7
- # It fixes 3 issues, regarding closing forwarded ports:
8
- #
9
- # 1.) if client closes a forwarded connection, but the server is reading, net-ssh terminates with IOError socket closed.
10
- # 2.) if client force closes (RST) a forwarded connection, but server is reading, net-ssh terminates with
11
- # 3.) if server closes the sending side, the on_eof is not handled.
12
- #
13
- # More info:
14
- #
15
- # http://net-ssh.lighthouseapp.com/projects/36253/tickets/7
16
-
17
- require 'common'
18
- require 'net/ssh/buffer'
19
- require 'net/ssh'
20
- require 'timeout'
21
- require 'tempfile'
22
-
23
- class TestForward < Test::Unit::TestCase
24
-
25
- def localhost
26
- 'localhost'
27
- end
28
-
29
- def ssh_start_params
30
- [localhost ,ENV['USER'], {:keys => "~/.ssh/id_rsa", :verbose => :debug}]
31
- end
32
-
33
- def start_server_sending_lot_of_data(exceptions)
34
- server = TCPServer.open(0)
35
- Thread.start do
36
- loop do
37
- Thread.start(server.accept) do |client|
38
- begin
39
- 10000.times do |i|
40
- client.puts "item#{i}"
41
- end
42
- client.close
43
- rescue
44
- exceptions << $!
45
- raise
46
- end
47
- end
48
- end
49
- end
50
- return server
51
- end
52
-
53
- def start_server_closing_soon(exceptions=nil)
54
- server = TCPServer.open(0)
55
- Thread.start do
56
- loop do
57
- Thread.start(server.accept) do |client|
58
- begin
59
- client.recv(1024)
60
- client.setsockopt(Socket::SOL_SOCKET, Socket::SO_LINGER, [1, 0].pack("ii"))
61
- client.close
62
- rescue
63
- exceptions << $!
64
- raise
65
- end
66
- end
67
- end
68
- end
69
- return server
70
- end
71
-
72
- def test_local_ephemeral_port_should_work_correctly
73
- session = Net::SSH.start(*ssh_start_params)
74
-
75
- assert_nothing_raised do
76
- assigned_port = session.forward.local(0, localhost, 22)
77
- assert_not_nil assigned_port
78
- assert_operator assigned_port, :>, 0
79
- end
80
- end
81
-
82
- def test_remote_ephemeral_port_should_work_correctly
83
- session = Net::SSH.start(*ssh_start_params)
84
-
85
- assert_nothing_raised do
86
- session.forward.remote(22, localhost, 0, localhost)
87
- session.loop { !(session.forward.active_remotes.length > 0) }
88
- assigned_port = session.forward.active_remotes.first[0]
89
- assert_not_nil assigned_port
90
- assert_operator assigned_port, :>, 0
91
- end
92
- end
93
-
94
- def test_remote_callback_should_fire
95
- session = Net::SSH.start(*ssh_start_params)
96
-
97
- assert_nothing_raised do
98
- got_port = nil
99
- session.forward.remote(22, localhost, 0, localhost) do |port|
100
- got_port = port
101
- end
102
- session.loop { !(session.forward.active_remotes.length > 0) }
103
- assert_operator session.forward.active_remote_destinations.length, :==, 1
104
- assert_operator session.forward.active_remote_destinations.keys.first, :==, [ 22, localhost ]
105
- assert_operator session.forward.active_remote_destinations.values.first, :==, [ got_port, localhost ]
106
- assert_operator session.forward.active_remotes.first, :==, [ got_port, localhost ]
107
- assigned_port = session.forward.active_remotes.first[0]
108
- assert_operator got_port, :==, assigned_port
109
- assert_not_nil assigned_port
110
- assert_operator assigned_port, :>, 0
111
- end
112
- end
113
-
114
- def test_remote_callback_should_fire_on_error_and_still_throw_exception
115
- session = Net::SSH.start(*ssh_start_params)
116
-
117
- assert_nothing_raised do
118
- session.forward.remote(22, localhost, 22, localhost) do |port|
119
- assert_operator port, :==, :error
120
- end
121
- end
122
- assert_raises(Net::SSH::Exception) do
123
- session.loop { true }
124
- end
125
- end
126
-
127
- def test_remote_callback_should_fire_on_error_but_not_throw_exception_if_asked_not_to
128
- session = Net::SSH.start(*ssh_start_params)
129
-
130
- assert_nothing_raised do
131
- got_port = nil
132
- session.forward.remote(22, localhost, 22, localhost) do |port|
133
- assert_operator port, :==, :error
134
- got_port = port
135
- :no_exception
136
- end
137
- session.loop { !got_port }
138
- assert_operator port, :==, :error
139
- assert_operator session.forward.active_remotes.length, :==, 0
140
- end
141
- end
142
-
143
- def test_loop_should_not_abort_when_local_side_of_forward_is_closed
144
- session = Net::SSH.start(*ssh_start_params)
145
- server_exc = Queue.new
146
- server = start_server_sending_lot_of_data(server_exc)
147
- remote_port = server.addr[1]
148
- local_port = 0 # request ephemeral port
149
- session.forward.local(local_port, localhost, remote_port)
150
- client_done = Queue.new
151
- Thread.start do
152
- begin
153
- client = TCPSocket.new(localhost, local_port)
154
- client.recv(1024)
155
- client.close
156
- sleep(0.2)
157
- ensure
158
- client_done << true
159
- end
160
- end
161
- session.loop(0.1) { client_done.empty? }
162
- assert_equal "Broken pipe", "#{server_exc.pop}" unless server_exc.empty?
163
- end
164
-
165
- def test_loop_should_not_abort_when_local_side_of_forward_is_reset
166
- session = Net::SSH.start(*ssh_start_params)
167
- server_exc = Queue.new
168
- server = start_server_sending_lot_of_data(server_exc)
169
- remote_port = server.addr[1]
170
- local_port = 0 # request ephemeral port
171
- session.forward.local(local_port, localhost, remote_port)
172
- client_done = Queue.new
173
- Thread.start do
174
- begin
175
- client = TCPSocket.new(localhost, local_port)
176
- client.recv(1024)
177
- client.setsockopt(Socket::SOL_SOCKET, Socket::SO_LINGER, [1, 0].pack("ii"))
178
- client.close
179
- sleep(0.1)
180
- ensure
181
- client_done << true
182
- end
183
- end
184
- session.loop(0.1) { client_done.empty? }
185
- assert_equal "Broken pipe", "#{server_exc.pop}" unless server_exc.empty?
186
- end
187
-
188
- def create_local_socket(&blk)
189
- tempfile = Tempfile.new("net_ssh_forward_test")
190
- path = tempfile.path
191
- tempfile.delete
192
- yield UNIXServer.open(path)
193
- File.delete(path)
194
- end if defined?(UNIXServer)
195
-
196
- def test_forward_local_unix_socket_to_remote_port
197
- session = Net::SSH.start(*ssh_start_params)
198
- server_exc = Queue.new
199
- server = start_server_sending_lot_of_data(server_exc)
200
- remote_port = server.addr[1]
201
- client_data = nil
202
-
203
- create_local_socket do |local_socket|
204
- session.forward.local(local_socket, localhost, remote_port)
205
- client_done = Queue.new
206
-
207
- Thread.start do
208
- begin
209
- client = UNIXSocket.new(local_socket.path)
210
- client_data = client.recv(1024)
211
- client.close
212
- sleep(0.2)
213
- ensure
214
- client_done << true
215
- end
216
- end
217
-
218
- session.loop(0.1) { client_done.empty? }
219
- end
220
-
221
- assert_not_nil(client_data, "client should have received data")
222
- assert(client_data.match(/item\d/), 'client should have received the string item')
223
- end if defined?(UNIXSocket)
224
-
225
- def test_loop_should_not_abort_when_server_side_of_forward_is_closed
226
- session = Net::SSH.start(*ssh_start_params)
227
- server = start_server_closing_soon
228
- remote_port = server.addr[1]
229
- local_port = 0 # request ephemeral port
230
- session.forward.local(local_port, localhost, remote_port)
231
- client_done = Queue.new
232
- Thread.start do
233
- begin
234
- client = TCPSocket.new(localhost, local_port)
235
- 1.times do |i|
236
- client.puts "item#{i}"
237
- end
238
- client.close
239
- sleep(0.1)
240
- ensure
241
- client_done << true
242
- end
243
- end
244
- session.loop(0.1) { client_done.empty? }
245
- end
246
-
247
- def start_server
248
- server = TCPServer.open(0)
249
- Thread.start do
250
- loop do
251
- Thread.start(server.accept) do |client|
252
- yield(client)
253
- end
254
- end
255
- end
256
- return server
257
- end
258
-
259
- def test_server_eof_should_be_handled
260
- session = Net::SSH.start(*ssh_start_params)
261
- server = start_server do |client|
262
- client.write "This is a small message!"
263
- client.close
264
- end
265
- client_done = Queue.new
266
- client_exception = Queue.new
267
- client_data = Queue.new
268
- remote_port = server.addr[1]
269
- local_port = session.forward.local(0, localhost, remote_port)
270
- Thread.start do
271
- begin
272
- client = TCPSocket.new(localhost, local_port)
273
- data = client.read(4096)
274
- client.close
275
- client_done << data
276
- rescue
277
- client_done << $!
278
- end
279
- end
280
- timeout(5) do
281
- session.loop(0.1) { client_done.empty? }
282
- assert_equal "This is a small message!", client_done.pop
283
- end
284
- end
285
- end