net-sftp 0.5.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (77) hide show
  1. data/doc/LICENSE-BSD +27 -0
  2. data/doc/LICENSE-GPL +280 -0
  3. data/doc/LICENSE-RUBY +56 -0
  4. data/examples/asynchronous.rb +57 -0
  5. data/examples/ssh-service.rb +31 -0
  6. data/examples/synchronous.rb +120 -0
  7. data/lib/net/sftp.rb +39 -0
  8. data/lib/net/sftp/errors.rb +25 -0
  9. data/lib/net/sftp/operations/abstract.rb +103 -0
  10. data/lib/net/sftp/operations/close.rb +31 -0
  11. data/lib/net/sftp/operations/errors.rb +76 -0
  12. data/lib/net/sftp/operations/fsetstat.rb +36 -0
  13. data/lib/net/sftp/operations/fstat.rb +32 -0
  14. data/lib/net/sftp/operations/lstat.rb +31 -0
  15. data/lib/net/sftp/operations/mkdir.rb +33 -0
  16. data/lib/net/sftp/operations/open.rb +32 -0
  17. data/lib/net/sftp/operations/opendir.rb +32 -0
  18. data/lib/net/sftp/operations/read.rb +84 -0
  19. data/lib/net/sftp/operations/readdir.rb +55 -0
  20. data/lib/net/sftp/operations/realpath.rb +37 -0
  21. data/lib/net/sftp/operations/remove.rb +31 -0
  22. data/lib/net/sftp/operations/rename.rb +32 -0
  23. data/lib/net/sftp/operations/rmdir.rb +31 -0
  24. data/lib/net/sftp/operations/services.rb +42 -0
  25. data/lib/net/sftp/operations/setstat.rb +33 -0
  26. data/lib/net/sftp/operations/stat.rb +31 -0
  27. data/lib/net/sftp/operations/write.rb +63 -0
  28. data/lib/net/sftp/protocol/01/attributes.rb +146 -0
  29. data/lib/net/sftp/protocol/01/impl.rb +251 -0
  30. data/lib/net/sftp/protocol/01/packet-assistant.rb +82 -0
  31. data/lib/net/sftp/protocol/01/services.rb +47 -0
  32. data/lib/net/sftp/protocol/02/impl.rb +39 -0
  33. data/lib/net/sftp/protocol/02/packet-assistant.rb +32 -0
  34. data/lib/net/sftp/protocol/02/services.rb +44 -0
  35. data/lib/net/sftp/protocol/03/impl.rb +42 -0
  36. data/lib/net/sftp/protocol/03/packet-assistant.rb +35 -0
  37. data/lib/net/sftp/protocol/03/services.rb +44 -0
  38. data/lib/net/sftp/protocol/04/attributes.rb +227 -0
  39. data/lib/net/sftp/protocol/04/impl.rb +134 -0
  40. data/lib/net/sftp/protocol/04/packet-assistant.rb +51 -0
  41. data/lib/net/sftp/protocol/04/services.rb +44 -0
  42. data/lib/net/sftp/protocol/05/services.rb +44 -0
  43. data/lib/net/sftp/protocol/constants.rb +60 -0
  44. data/lib/net/sftp/protocol/driver.rb +232 -0
  45. data/lib/net/sftp/protocol/packet-assistant.rb +84 -0
  46. data/lib/net/sftp/protocol/services.rb +55 -0
  47. data/lib/net/sftp/session.rb +215 -0
  48. data/lib/net/sftp/version.rb +25 -0
  49. data/test/ALL-TESTS.rb +21 -0
  50. data/test/operations/tc_abstract.rb +124 -0
  51. data/test/operations/tc_close.rb +40 -0
  52. data/test/operations/tc_fsetstat.rb +48 -0
  53. data/test/operations/tc_fstat.rb +40 -0
  54. data/test/operations/tc_lstat.rb +40 -0
  55. data/test/operations/tc_mkdir.rb +48 -0
  56. data/test/operations/tc_open.rb +42 -0
  57. data/test/operations/tc_opendir.rb +40 -0
  58. data/test/operations/tc_read.rb +103 -0
  59. data/test/operations/tc_readdir.rb +88 -0
  60. data/test/operations/tc_realpath.rb +54 -0
  61. data/test/operations/tc_remove.rb +40 -0
  62. data/test/operations/tc_rmdir.rb +40 -0
  63. data/test/operations/tc_setstat.rb +48 -0
  64. data/test/operations/tc_stat.rb +40 -0
  65. data/test/operations/tc_write.rb +91 -0
  66. data/test/protocol/01/tc_attributes.rb +138 -0
  67. data/test/protocol/01/tc_impl.rb +294 -0
  68. data/test/protocol/01/tc_packet_assistant.rb +81 -0
  69. data/test/protocol/02/tc_impl.rb +41 -0
  70. data/test/protocol/02/tc_packet_assistant.rb +31 -0
  71. data/test/protocol/03/tc_impl.rb +48 -0
  72. data/test/protocol/03/tc_packet_assistant.rb +34 -0
  73. data/test/protocol/04/tc_attributes.rb +174 -0
  74. data/test/protocol/04/tc_impl.rb +102 -0
  75. data/test/protocol/04/tc_packet_assistant.rb +41 -0
  76. data/test/protocol/tc_driver.rb +219 -0
  77. metadata +137 -0
@@ -0,0 +1,48 @@
1
+ #--
2
+ # =============================================================================
3
+ # Copyright (c) 2004, Jamis Buck (jgb3@email.byu.edu)
4
+ # All rights reserved.
5
+ #
6
+ # This source file is distributed as part of the Net::SFTP Secure FTP Client
7
+ # library for Ruby. This file (and the library as a whole) may be used only as
8
+ # allowed by either the BSD license, or the Ruby license (or, by association
9
+ # with the Ruby license, the GPL). See the "doc" subdirectory of the Net::SFTP
10
+ # distribution for the texts of these licenses.
11
+ # -----------------------------------------------------------------------------
12
+ # net-sftp website: http://net-ssh.rubyforge.org/sftp
13
+ # project website : http://rubyforge.org/projects/net-ssh
14
+ # =============================================================================
15
+ #++
16
+
17
+ $:.unshift "../../../lib"
18
+ $:.unshift File.join( File.dirname( __FILE__ ), ".." )
19
+
20
+ require '02/tc_impl.rb'
21
+ require 'net/sftp/protocol/03/impl'
22
+
23
+ class TC_03_Impl < TC_02_Impl
24
+
25
+ def impl_class
26
+ Net::SFTP::Protocol::V_03::Impl
27
+ end
28
+
29
+ operation :readlink
30
+
31
+ operation :symlink
32
+
33
+ def test_do_status_with_callback
34
+ buffer = Net::SSH::Util::ReaderBuffer.new( "\0\0\0\1\0\0\0\2" +
35
+ "\0\0\0\1a\0\0\0\1b" )
36
+ called = false
37
+ @impl.on_status do |d,i,c,a,b|
38
+ called = true
39
+ assert_equal 1, i
40
+ assert_equal 2, c
41
+ assert_equal "a", a
42
+ assert_equal "b", b
43
+ end
44
+ @impl.do_status nil, buffer
45
+ assert called
46
+ end
47
+
48
+ end
@@ -0,0 +1,34 @@
1
+ #--
2
+ # =============================================================================
3
+ # Copyright (c) 2004, Jamis Buck (jgb3@email.byu.edu)
4
+ # All rights reserved.
5
+ #
6
+ # This source file is distributed as part of the Net::SFTP Secure FTP Client
7
+ # library for Ruby. This file (and the library as a whole) may be used only as
8
+ # allowed by either the BSD license, or the Ruby license (or, by association
9
+ # with the Ruby license, the GPL). See the "doc" subdirectory of the Net::SFTP
10
+ # distribution for the texts of these licenses.
11
+ # -----------------------------------------------------------------------------
12
+ # net-sftp website: http://net-ssh.rubyforge.org/sftp
13
+ # project website : http://rubyforge.org/projects/net-ssh
14
+ # =============================================================================
15
+ #++
16
+
17
+ $:.unshift "../../../lib"
18
+ $:.unshift File.join( File.dirname( __FILE__ ), ".." )
19
+
20
+ require '02/tc_packet_assistant'
21
+ require 'net/sftp/protocol/03/packet-assistant'
22
+
23
+ class TC_03_PacketAssistant < TC_02_PacketAssistant
24
+
25
+ def packet_assistant_class
26
+ Net::SFTP::Protocol::V_03::PacketAssistant
27
+ end
28
+
29
+ packet :readlink, [ "a path" ], "\0\0\0\6a path"
30
+
31
+ packet :symlink, [ "from path", "to path" ],
32
+ "\0\0\0\11from path\0\0\0\7to path"
33
+
34
+ end
@@ -0,0 +1,174 @@
1
+ #--
2
+ # =============================================================================
3
+ # Copyright (c) 2004, Jamis Buck (jgb3@email.byu.edu)
4
+ # All rights reserved.
5
+ #
6
+ # This source file is distributed as part of the Net::SFTP Secure FTP Client
7
+ # library for Ruby. This file (and the library as a whole) may be used only as
8
+ # allowed by either the BSD license, or the Ruby license (or, by association
9
+ # with the Ruby license, the GPL). See the "doc" subdirectory of the Net::SFTP
10
+ # distribution for the texts of these licenses.
11
+ # -----------------------------------------------------------------------------
12
+ # net-sftp website: http://net-ssh.rubyforge.org/sftp
13
+ # project website : http://rubyforge.org/projects/net-ssh
14
+ # =============================================================================
15
+ #++
16
+
17
+ $:.unshift "../../../lib"
18
+
19
+ require 'test/unit'
20
+ require 'net/sftp/protocol/04/attributes'
21
+
22
+ require 'net/ssh'
23
+ require 'net/ssh/util/buffer'
24
+
25
+ class TC_04_Attributes < Test::Unit::TestCase
26
+
27
+ class Buffers
28
+ def writer
29
+ Net::SSH::Util::WriterBuffer.new
30
+ end
31
+ def reader( text )
32
+ Net::SSH::Util::ReaderBuffer.new( text )
33
+ end
34
+ end
35
+
36
+ def setup
37
+ @factory = Net::SFTP::Protocol::V_04::Attributes.init( Buffers.new )
38
+ end
39
+
40
+ def test_empty
41
+ empty = @factory.empty
42
+ assert_equal 1, empty.type
43
+ assert_nil empty.size
44
+ assert_nil empty.owner
45
+ assert_nil empty.group
46
+ assert_nil empty.permissions
47
+ assert_nil empty.atime
48
+ assert_nil empty.atime_nseconds
49
+ assert_nil empty.ctime
50
+ assert_nil empty.ctime_nseconds
51
+ assert_nil empty.mtime
52
+ assert_nil empty.mtime_nseconds
53
+ assert_nil empty.acl
54
+ assert_nil empty.extended
55
+ assert_equal "\0\0\0\0\1", empty.to_s
56
+ end
57
+
58
+ def test_from_buffer_empty
59
+ buffer = @factory.buffers.reader( "\0\0\0\0\2" )
60
+ attrs = @factory.from_buffer( buffer )
61
+ assert_equal 2, attrs.type
62
+ assert_nil attrs.size
63
+ assert_nil attrs.owner
64
+ assert_nil attrs.group
65
+ assert_nil attrs.permissions
66
+ assert_nil attrs.atime
67
+ assert_nil attrs.atime_nseconds
68
+ assert_nil attrs.ctime
69
+ assert_nil attrs.ctime_nseconds
70
+ assert_nil attrs.mtime
71
+ assert_nil attrs.mtime_nseconds
72
+ assert_nil attrs.acl
73
+ assert_nil attrs.extended
74
+ assert_equal "\0\0\0\0\2", attrs.to_s
75
+ end
76
+
77
+ ACL = Net::SFTP::Protocol::V_04::Attributes::ACL
78
+ ATTRIBUTES =
79
+ [ [ 0x00000001, "\1\2\3\4\5\6\7\10", :size, 0x0102030405060708 ],
80
+ [ 0x00000080, "\0\0\0\1a\0\0\0\1b", :owner, "a" ],
81
+ [ 0x00000080, "\0\0\0\1a\0\0\0\1b", :group, "b" ],
82
+ [ 0x00000004, "\21\22\23\24", :permissions, 0x11121314 ],
83
+ [ 0x00000138,
84
+ "\1\1\1\1\1\1\1\1\0\1\2\3" +
85
+ "\2\2\2\2\2\2\2\2\4\5\6\7" +
86
+ "\3\3\3\3\3\3\3\3\2\4\6\10", :atime_nseconds, 0x00010203 ],
87
+ [ 0x00000008, "\1\2\3\4\1\2\3\4", :atime, 0x0102030401020304 ],
88
+ [ 0x00000010, "\4\3\4\3\4\3\4\3", :ctime, 0x0403040304030403 ],
89
+ [ 0x00000020, "\4\3\2\1\4\3\2\1", :mtime, 0x0403020104030201 ],
90
+ [ 0x00000040, "\0\0\0\46\0\0\0\2\0\0\0\1\0\0\0\2\0\0\0\3\0\0\0\1a" +
91
+ "\0\0\0\4\0\0\0\5\0\0\0\6\0\0\0\1b", :acl,
92
+ [ ACL.new( 1, 2, 3, "a" ), ACL.new( 4, 5, 6, "b" ) ] ],
93
+ [ 0x80000000,
94
+ "\0\0\0\4" +
95
+ "\0\0\0\01a\0\0\0\01b" +
96
+ "\0\0\0\01c\0\0\0\01d" +
97
+ "\0\0\0\01e\0\0\0\01f" +
98
+ "\0\0\0\01g\0\0\0\01h",
99
+ :extended,
100
+ { "a" => "b", "c" => "d", "e" => "f", "g" => "h" } ] ]
101
+
102
+ # find all possible combinations of the elements of ATTRIBUTES
103
+ # (i.e., 'n' choose k, for k in [1..ATTRIBUTES.length]).
104
+ def self.choose( from, k )
105
+ result = []
106
+ ( from.length - k + 1 ).times do |i|
107
+ if i+1 < from.length && k > 1
108
+ choose( from[i+1..-1], k-1 ).each do |chosen|
109
+ result << [ from[i], *chosen ]
110
+ end
111
+ else
112
+ result << [ from[i] ]
113
+ end
114
+ end
115
+ result
116
+ end
117
+
118
+ method_id = 0
119
+ ATTRIBUTES.length.times do |k|
120
+ choose( ATTRIBUTES, k+1 ).each do |attrs|
121
+ vars = attrs.map { |a| a[2] }.join( "_" )
122
+ define_method( "test_attributes_#{vars}_%03d" % method_id ) do
123
+ flags = 0
124
+ buffer = "\1"
125
+ attrs.each do |a|
126
+ if ( flags & a[0] ) == 0
127
+ flags |= a[0]
128
+ buffer += a[1]
129
+ end
130
+ end
131
+ buffer = [ flags, buffer ].pack( "NA*" )
132
+ input = @factory.buffers.reader( buffer )
133
+ obj = @factory.from_buffer( input )
134
+ assert_equal 1, obj.type, vars
135
+ flags = 0
136
+ attrs.each do |a|
137
+ if ( flags & a[0] ) == 0
138
+ assert_equal a[3], obj.__send__( a[2] ), a[2]
139
+ flags |= a[0]
140
+ end
141
+ end
142
+ assert_equal buffer, obj.to_s, vars
143
+ end
144
+ method_id += 1
145
+ end
146
+ end
147
+
148
+ require 'etc'
149
+ [
150
+ [ { :type => 3 }, :type, 3 ],
151
+ [ { :size => 1000 }, :size, 1000, :permissions ],
152
+ [ { :owner => ENV['USER'] }, :owner, ENV['USER'] ],
153
+ [ { :group => 'root' }, :group, 'root' ],
154
+ [ { :uid => Etc.getpwnam(ENV['USER']).uid }, :owner, ENV['USER'] ],
155
+ [ { :gid => Etc.getgrnam('root').gid }, :group, 'root' ],
156
+ [ { :permissions => 0600 }, :permissions, 0600 ],
157
+ [ { :atime => 1 }, :atime, 1 ],
158
+ [ { :atime_nseconds => 2 }, :atime_nseconds, 2 ],
159
+ [ { :ctime => 1 }, :ctime, 1 ],
160
+ [ { :ctime_nseconds => 2 }, :ctime_nseconds, 2 ],
161
+ [ { :mtime => 1 }, :mtime, 1 ],
162
+ [ { :mtime_nseconds => 2 }, :mtime_nseconds, 2 ],
163
+ [ { :acl => [ ACL.new(1,2,3,4), ACL.new(5,6,7,8) ] },
164
+ :acl, [ ACL.new(1,2,3,4), ACL.new(5,6,7,8) ] ],
165
+ [ { :extended => { "foo" => "bar" } }, :extended, { "foo" => "bar" } ]
166
+ ].each do |fixture|
167
+ define_method( "test_from_hash_#{fixture[1]}" ) do
168
+ attrs = @factory.from_hash( fixture[0] )
169
+ assert_equal fixture[2], attrs.__send__( fixture[1] )
170
+ assert_nil attrs.__send__( fixture[3] || :size )
171
+ end
172
+ end
173
+
174
+ end
@@ -0,0 +1,102 @@
1
+ #--
2
+ # =============================================================================
3
+ # Copyright (c) 2004, Jamis Buck (jgb3@email.byu.edu)
4
+ # All rights reserved.
5
+ #
6
+ # This source file is distributed as part of the Net::SFTP Secure FTP Client
7
+ # library for Ruby. This file (and the library as a whole) may be used only as
8
+ # allowed by either the BSD license, or the Ruby license (or, by association
9
+ # with the Ruby license, the GPL). See the "doc" subdirectory of the Net::SFTP
10
+ # distribution for the texts of these licenses.
11
+ # -----------------------------------------------------------------------------
12
+ # net-sftp website: http://net-ssh.rubyforge.org/sftp
13
+ # project website : http://rubyforge.org/projects/net-ssh
14
+ # =============================================================================
15
+ #++
16
+
17
+ $:.unshift "../../../lib"
18
+ $:.unshift File.join( File.dirname( __FILE__ ), ".." )
19
+
20
+ require 'net/sftp/protocol/04/impl'
21
+ require '03/tc_impl'
22
+
23
+ class TC_04_Impl < TC_03_Impl
24
+
25
+ def impl_class
26
+ Net::SFTP::Protocol::V_04::Impl
27
+ end
28
+
29
+ unless defined?( IO_FLAGS_V4 )
30
+ IO_FLAGS_V4 = [ IO::RDONLY, IO::WRONLY, IO::RDWR, IO::APPEND ]
31
+ OTHER_FLAGS_V4 = [ 0, IO::CREAT, IO::TRUNC, IO::EXCL ]
32
+ FLAG_MAP_V4 = { IO::RDONLY => 2, IO::WRONLY => 1, IO::RDWR => 3,
33
+ IO::APPEND => 11, IO::CREAT => 3, IO::TRUNC => 4 }
34
+ ACCESS_MAP_V4 = { IO::RDONLY => 0x81, IO::WRONLY => 0x102,
35
+ IO::RDWR => 0x183, IO::APPEND => 0x106 }
36
+
37
+ IO_FLAGS_V4.each do |flag|
38
+ OTHER_FLAGS_V4.each do |oflag|
39
+ [ nil, 0400 ].each do |mode|
40
+ define_method( "test_open_#{flag}_#{oflag}_#{mode||"nil"}" ) do
41
+ return if oflag == IO::EXCL
42
+ @assistant.mock_handle( :open ) { |*a| [ a[0], a[1..-1] ] }
43
+ args = [ 14, "a path", flag | oflag ]
44
+ args << mode if mode
45
+ assert_equal 14, @impl.open( *args )
46
+ assert_equal 1, @assistant.mock_count( :open )
47
+ assert_equal( ( mode || 0660 ), @permissions )
48
+ sftp_flag = FLAG_MAP_V4[flag] |
49
+ ( oflag == 0 ? 0 : FLAG_MAP_V4[oflag] )
50
+ access_flag = ACCESS_MAP_V4[flag]
51
+ assert_equal Net::SFTP::Protocol::Constants::FXP_OPEN,
52
+ @sent_data.first[0]
53
+ assert_equal [ "a path", access_flag, sftp_flag ],
54
+ @sent_data.first[1][0,3]
55
+ end
56
+ end
57
+ end
58
+ end
59
+ end
60
+
61
+ def test_stat_flags
62
+ @assistant.mock_handle( :stat ) { |*a| [ a[0], a[1..-1] ] }
63
+ id = @impl.stat( 14, :a, :b )
64
+ assert_equal 14, id
65
+ assert_equal 1, @assistant.mock_count( :stat )
66
+ assert_equal 1, @driver.mock_count( :send_data )
67
+ assert_equal [
68
+ [ Net::SFTP::Protocol::Constants::FXP_STAT, [ :a, :b ]] ], @sent_data
69
+ end
70
+
71
+ def test_lstat_flags
72
+ @assistant.mock_handle( :lstat ) { |*a| [ a[0], a[1..-1] ] }
73
+ id = @impl.lstat( 14, :a, :b )
74
+ assert_equal 14, id
75
+ assert_equal 1, @assistant.mock_count( :lstat )
76
+ assert_equal 1, @driver.mock_count( :send_data )
77
+ assert_equal [
78
+ [ Net::SFTP::Protocol::Constants::FXP_LSTAT, [ :a, :b ]] ], @sent_data
79
+ end
80
+
81
+ def test_fstat_flags
82
+ @assistant.mock_handle( :fstat ) { |*a| [ a[0], a[1..-1] ] }
83
+ id = @impl.fstat( 14, :a, :b )
84
+ assert_equal 14, id
85
+ assert_equal 1, @assistant.mock_count( :fstat )
86
+ assert_equal 1, @driver.mock_count( :send_data )
87
+ assert_equal [
88
+ [ Net::SFTP::Protocol::Constants::FXP_FSTAT, [ :a, :b ]] ], @sent_data
89
+ end
90
+
91
+ def test_rename_flags
92
+ @assistant.mock_handle( :rename ) { |*a| [ a[0], a[1..-1] ] }
93
+ id = @impl.rename( 14, :a, :b, :c )
94
+ assert_equal 14, id
95
+ assert_equal 1, @assistant.mock_count( :rename )
96
+ assert_equal 1, @driver.mock_count( :send_data )
97
+ assert_equal [
98
+ [ Net::SFTP::Protocol::Constants::FXP_RENAME, [ :a, :b, :c ]] ],
99
+ @sent_data
100
+ end
101
+
102
+ end
@@ -0,0 +1,41 @@
1
+ #--
2
+ # =============================================================================
3
+ # Copyright (c) 2004, Jamis Buck (jgb3@email.byu.edu)
4
+ # All rights reserved.
5
+ #
6
+ # This source file is distributed as part of the Net::SFTP Secure FTP Client
7
+ # library for Ruby. This file (and the library as a whole) may be used only as
8
+ # allowed by either the BSD license, or the Ruby license (or, by association
9
+ # with the Ruby license, the GPL). See the "doc" subdirectory of the Net::SFTP
10
+ # distribution for the texts of these licenses.
11
+ # -----------------------------------------------------------------------------
12
+ # net-sftp website: http://net-ssh.rubyforge.org/sftp
13
+ # project website : http://rubyforge.org/projects/net-ssh
14
+ # =============================================================================
15
+ #++
16
+
17
+ $:.unshift "../../../lib"
18
+ $:.unshift File.join( File.dirname( __FILE__ ), ".." )
19
+
20
+ require '03/tc_packet_assistant'
21
+ require 'net/sftp/protocol/04/packet-assistant'
22
+
23
+ class TC_04_PacketAssistant < TC_03_PacketAssistant
24
+
25
+ def packet_assistant_class
26
+ Net::SFTP::Protocol::V_04::PacketAssistant
27
+ end
28
+
29
+ packet :open, [ "a path", 1, 2, "attrs" ],
30
+ "\0\0\0\6a path\0\0\0\1\0\0\0\2attrs"
31
+
32
+ packet :rename, [ "old name", "new name", 1 ],
33
+ "\0\0\0\10old name\0\0\0\10new name\0\0\0\1"
34
+
35
+ packet :stat, [ "a path", 1 ], "\0\0\0\6a path\0\0\0\1"
36
+
37
+ packet :lstat, [ "a path", 1 ], "\0\0\0\6a path\0\0\0\1"
38
+
39
+ packet :fstat, [ "handle", 1 ], "\0\0\0\6handle\0\0\0\1"
40
+
41
+ end
@@ -0,0 +1,219 @@
1
+ #--
2
+ # =============================================================================
3
+ # Copyright (c) 2004, Jamis Buck (jgb3@email.byu.edu)
4
+ # All rights reserved.
5
+ #
6
+ # This source file is distributed as part of the Net::SFTP Secure FTP Client
7
+ # library for Ruby. This file (and the library as a whole) may be used only as
8
+ # allowed by either the BSD license, or the Ruby license (or, by association
9
+ # with the Ruby license, the GPL). See the "doc" subdirectory of the Net::SFTP
10
+ # distribution for the texts of these licenses.
11
+ # -----------------------------------------------------------------------------
12
+ # net-sftp website: http://net-ssh.rubyforge.org/sftp
13
+ # project website : http://rubyforge.org/projects/net-ssh
14
+ # =============================================================================
15
+ #++
16
+
17
+ $:.unshift "../../lib"
18
+
19
+ require 'test/unit'
20
+ require 'net/sftp/protocol/driver'
21
+ require 'net/ssh/util/buffer'
22
+ require 'flexmock'
23
+
24
+ class TC_Protocol_Driver < Test::Unit::TestCase
25
+
26
+ class Buffers
27
+ def writer
28
+ Net::SSH::Util::WriterBuffer.new
29
+ end
30
+ def reader( text )
31
+ Net::SSH::Util::ReaderBuffer.new( text )
32
+ end
33
+ end
34
+
35
+ def reader( text )
36
+ Net::SSH::Util::ReaderBuffer.new( text )
37
+ end
38
+
39
+ def force_state( state )
40
+ @driver.instance_eval { @state = state }
41
+ end
42
+
43
+ def setup
44
+ @channel = FlexMock.new
45
+ @channel.mock_handle( :close )
46
+ @channel.mock_handle( :subsystem )
47
+ @channel.mock_handle( :on_success )
48
+ @channel.mock_handle( :on_data )
49
+ @channel.mock_handle( :send_data )
50
+
51
+ @connection = FlexMock.new
52
+ @connection.mock_handle( :open_channel ) { @channel }
53
+
54
+ @log = FlexMock.new
55
+ @log.mock_handle( :debug? )
56
+ @log.mock_handle( :debug )
57
+ @log.mock_handle( :info? )
58
+ @log.mock_handle( :info )
59
+
60
+ @dispatchers = FlexMock.new
61
+
62
+ @dispatcher = FlexMock.new
63
+
64
+ @dispatchers.mock_handle( :[] ) do |v,e|
65
+ @version = v
66
+ @extensions = e
67
+ @dispatcher
68
+ end
69
+
70
+ @driver = Net::SFTP::Protocol::Driver.new( @connection, Buffers.new, 5,
71
+ @dispatchers, @log )
72
+ end
73
+
74
+ def test_initial_state
75
+ assert_equal :unconfirmed, @driver.state
76
+ end
77
+
78
+ def test_close
79
+ @driver.close
80
+ assert_equal 1, @channel.mock_count( :close )
81
+ assert_equal :closed, @driver.state
82
+ end
83
+
84
+ def test_next_request_id
85
+ assert_equal 0, @driver.next_request_id
86
+ assert_equal 1, @driver.next_request_id
87
+ assert_equal 2, @driver.next_request_id
88
+ end
89
+
90
+ def test_do_confirm_bad_state
91
+ force_state :bogus
92
+ assert_raise( Net::SFTP::Bug ) { @driver.do_confirm @channel }
93
+ end
94
+
95
+ def test_do_confirm
96
+ force_state :unconfirmed
97
+ @channel.mock_handle( :subsystem ) { |a| assert_equal "sftp", a }
98
+ @driver.do_confirm @channel
99
+ assert_equal 1, @channel.mock_count( :subsystem )
100
+ assert_equal 1, @channel.mock_count( :on_success )
101
+ assert_equal 1, @channel.mock_count( :on_data )
102
+ assert_equal :init, @driver.state
103
+ end
104
+
105
+ def test_do_success_bad_state
106
+ force_state :bogus
107
+ assert_raise( Net::SFTP::Bug ) { @driver.do_success @channel }
108
+ end
109
+
110
+ def test_do_success
111
+ force_state :init
112
+ packet = nil
113
+ @channel.mock_handle( :send_data ) { |p| packet = p }
114
+ @driver.do_success @channel
115
+ assert_equal 1, @channel.mock_count( :send_data )
116
+ assert_equal "\0\0\0\5\1\0\0\0\5", packet.to_s
117
+ end
118
+
119
+ def test_version_bad_state
120
+ force_state :bogus
121
+ assert_raise( Net::SFTP::Bug ) { @driver.do_version nil }
122
+ end
123
+
124
+ def test_version_server_higher
125
+ force_state :version
126
+ @driver.do_version reader( "\0\0\0\7" )
127
+ assert_equal 5, @version
128
+ assert_equal Hash.new, @extensions
129
+ assert_equal :open, @driver.state
130
+ end
131
+
132
+ def test_version_server_lower
133
+ force_state :version
134
+ @driver.do_version reader( "\0\0\0\3" )
135
+ assert_equal 3, @version
136
+ assert_equal Hash.new, @extensions
137
+ assert_equal :open, @driver.state
138
+ end
139
+
140
+ def test_version_extensions
141
+ force_state :version
142
+ @driver.do_version reader( "\0\0\0\3\0\0\0\1a\0\0\0\1b\0\0\0\1c\0\0\0\1d" )
143
+ assert_equal( {"a"=>"b","c"=>"d"}, @extensions )
144
+ end
145
+
146
+ def test_version_with_on_open
147
+ force_state :version
148
+ called = false
149
+ @driver.on_open { called = true }
150
+ @driver.do_version reader( "\0\0\0\3" )
151
+ assert called
152
+ end
153
+
154
+ def test_do_data_version
155
+ force_state :version
156
+ @driver.do_data( nil, "\0\0\0\5\2\0\0\0\3" )
157
+ assert_equal 1, @dispatchers.mock_count( :[] )
158
+ end
159
+
160
+ def test_do_dispatch
161
+ # define the dispatcher
162
+ force_state :version
163
+ @driver.do_version reader( "\0\0\0\3" )
164
+
165
+ channel = type = content = 0
166
+ @dispatcher.mock_handle( :dispatch ) { |c,t,n|
167
+ channel, type, content = c,t,n }
168
+ @driver.do_data( nil, "\0\0\0\5\7\0\0\0\0" )
169
+ assert_equal 1, @dispatcher.mock_count(:dispatch)
170
+ assert_nil channel
171
+ assert_equal 7, type
172
+ assert_equal "\0\0\0\0", content.to_s
173
+ end
174
+
175
+ def test_do_dispatch_multipass
176
+ # define the dispatcher
177
+ force_state :version
178
+ @driver.do_version reader( "\0\0\0\3" )
179
+
180
+ channel = type = content = 0
181
+ @dispatcher.mock_handle( :dispatch ) { |c,t,n|
182
+ channel, type, content = c,t,n }
183
+ @driver.do_data( nil, "\0\0\0\5\7\0\0" )
184
+
185
+ assert_equal 0, @dispatcher.mock_count(:dispatch)
186
+ assert_equal 0, channel
187
+ assert_equal 0, type
188
+ assert_equal 0, content
189
+
190
+ @driver.do_data( nil, "\0\0" )
191
+
192
+ assert_equal 1, @dispatcher.mock_count(:dispatch)
193
+ assert_nil channel
194
+ assert_equal 7, type
195
+ assert_equal "\0\0\0\0", content.to_s
196
+ end
197
+
198
+ def test_method_missing_found
199
+ force_state :version
200
+ @driver.do_version reader( "\0\0\0\3" )
201
+
202
+ def @dispatcher.respond_to?(sym)
203
+ super || sym == :foo
204
+ end
205
+
206
+ @dispatcher.mock_handle( :foo )
207
+ assert @driver.respond_to?( :foo )
208
+
209
+ @driver.foo
210
+
211
+ assert_equal 1, @dispatcher.mock_count( :foo )
212
+ end
213
+
214
+ def test_method_missing_not_found
215
+ assert !@driver.respond_to?( :foo )
216
+ assert_raise( NoMethodError ) { @driver.foo }
217
+ end
218
+
219
+ end