uri-smb 0.0.1

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.
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source "http://rubygems.org"
2
+
3
+ # Specify your gem's dependencies in stringglob.gemspec
4
+ gemspec
data/Rakefile ADDED
@@ -0,0 +1,5 @@
1
+ require 'bundler/gem_tasks'
2
+ require 'rake/testtask'
3
+
4
+ Rake::TestTask.new
5
+
@@ -0,0 +1,5 @@
1
+ module URI
2
+ module SMB
3
+ VERSION = "0.0.1"
4
+ end
5
+ end
data/lib/uri/smb.rb ADDED
@@ -0,0 +1,333 @@
1
+ ## Ruby: URI::SMB class
2
+ ##
3
+ ## Author:: SATOH Fumiyasu
4
+ ## Copyright:: (c) 2007-2011 SATOH Fumiyasu @ OSS Technology, Corp.
5
+ ## License:: You can redistribute it and/or modify it under the same term as Ruby.
6
+ ## Date:: 2011-10-28, since 2007-07-06
7
+
8
+ require 'uri'
9
+ require 'cgi'
10
+
11
+ module URI
12
+
13
+ ## SMB URI class. See also: Implementing CIFS - Appendix D: The SMB URL:
14
+ ## http://ubiqx.org/cifs/Appendix-D.html
15
+ class SMB < Generic
16
+ ## A default port of 445 for URI::SMB
17
+ DEFAULT_PORT = 445
18
+ ## An Array of the available components for URI::SMB
19
+ COMPONENT = [
20
+ :scheme,
21
+ :userinfo, :host, :port,
22
+ :share, :path,
23
+ :nbns, :workgroup, :calling, :called,
24
+ :broadcast, :nodetype, :scopeid,
25
+ ].freeze
26
+
27
+ NODETYPE = [
28
+ NODETYPE_BROADCAST = 'b',
29
+ NODETYPE_P2P = 'p',
30
+ NODETYPE_MIXED = 'm',
31
+ NODETYPE_HYBRID = 'h',
32
+ ].freeze
33
+
34
+ URI::REGEXP::PATTERN.const_set(
35
+ :NETBIOSHOSTNAME,
36
+ '[a-zA-Z\d_][a-zA-Z\d_\-]{1,14}'
37
+ )
38
+ URI.const_set(
39
+ :NETBIOSHOSTNAME,
40
+ Regexp.new("^#{URI::REGEXP::PATTERN::NETBIOSHOSTNAME}$")
41
+ )
42
+ URI::REGEXP::PATTERN.const_set(
43
+ :SMBHOSTNAME,
44
+ "#{URI::REGEXP::PATTERN::HOSTNAME}|#{URI::REGEXP::PATTERN::NETBIOSHOSTNAME}"
45
+ )
46
+ URI.const_set(
47
+ :SMBHOSTNAME,
48
+ Regexp.new("^#{URI::REGEXP::PATTERN::SMBHOSTNAME}$")
49
+ )
50
+
51
+ DEFAULT_PARSER = URI::Parser.new(:HOSTNAME=>URI::REGEXP::PATTERN::SMBHOSTNAME)
52
+
53
+ def self.parse(uri)
54
+ DEFAULT_PARSER.parse(uri)
55
+ end
56
+
57
+ def initialize(scheme,
58
+ userinfo, host, port, registry,
59
+ path, opaque,
60
+ query,
61
+ fragment,
62
+ parser = DEFAULT_PARSER,
63
+ arg_check = false)
64
+ super(scheme,
65
+ userinfo, host, port, registry,
66
+ path, opaque,
67
+ query,
68
+ fragment,
69
+ parser,
70
+ arg_check)
71
+
72
+ if @fragment
73
+ raise InvalidURIError, 'bad SMB URI'
74
+ end
75
+
76
+ parse_path
77
+ parse_query
78
+ end
79
+
80
+ def parse_path
81
+ @share = @path ? @path.match(%r#/([^/]+)#) ? $1 : nil : nil;
82
+ end
83
+ private :parse_path
84
+
85
+ def build_path
86
+ if @share
87
+ @path = '/' + @share + @path.sub(%r#^/[^/]*#, '')
88
+ else
89
+ @path = ''
90
+ end
91
+ end
92
+ private :build_path
93
+
94
+ def parse_query
95
+ params = {}
96
+ if @query
97
+ @query.split(/[&;]/).each do |param|
98
+ next if param.empty?
99
+ name, value = param.split('=', 2)
100
+ params[name] = value ? value : nil
101
+ end
102
+ end
103
+
104
+ @nbns = params.delete('nbns') || params.delete('wins')
105
+ @workgroup = params.delete('workgroup') || params.delete('ntdomain')
106
+ @calling = params.delete('calling')
107
+ @called = params.delete('called')
108
+ @broadcast = params.delete('broadcast')
109
+ @nodetype = params.delete('nodetype')
110
+ @scopeid = params.delete('scopeid')
111
+
112
+ unless params.empty?
113
+ raise InvalidURIError,
114
+ "bad query parameter(s) in SMB URI: #{params.keys.join(',')}"
115
+ end
116
+ build_query
117
+ end
118
+ private :parse_query
119
+
120
+ def build_query
121
+ params = []
122
+ params << 'nbns=' + @nbns if @nbns && @nbns.size > 0
123
+ params << 'workgroup=' + @workgroup if @workgroup && @workgroup.size > 0
124
+ params << 'calling=' + @calling if @calling && @calling.size > 0
125
+ params << 'called=' + @called if @called && @called.size > 0
126
+ params << 'broadcast=' + @broadcast if @broadcast && @broadcast.size > 0
127
+ params << 'nodetype=' + @nodetype if @nodetype && @nodetype.size > 0
128
+ params << 'scopeid=' + @scopeid if @scopeid && @scopeid.size > 0
129
+
130
+ @query = !params.empty? ? params.join('&') : nil
131
+ end
132
+ private :build_query
133
+
134
+ def share
135
+ return @share ? @share : ''
136
+ end
137
+
138
+ def check_share(v)
139
+ check_path('/' + v)
140
+ if v && v.include?('/')
141
+ raise InvalidURIError,
142
+ "bad share conponent ('/' not allowed): #{v}"
143
+ end
144
+ end
145
+ private :check_share
146
+
147
+ def set_share(v)
148
+ @share = v
149
+ build_path
150
+ return @share
151
+ end
152
+ protected :set_share
153
+
154
+ def share=(v)
155
+ check_share(v)
156
+ set_share(v)
157
+ end
158
+
159
+ ## returns the NetBIOS name server (WINS) address.
160
+ def nbns
161
+ return @nbns
162
+ end
163
+ alias :wins :nbns
164
+
165
+ def check_nbns(v)
166
+ if v && v!='' && self.parser.regexp[:HOST] !~ v
167
+ raise InvalidURIError,
168
+ "bad NetBIOS name server (WINS) address: #{v}"
169
+ end
170
+ end
171
+ private :check_nbns
172
+
173
+ def set_nbns(v)
174
+ @nbns = v
175
+ build_query
176
+ return @nbns
177
+ end
178
+ protected :set_nbns
179
+
180
+ def nbns=(v)
181
+ check_nbns(v)
182
+ set_nbns(v)
183
+ end
184
+
185
+ ## returns the workgroup (or NT domain) name.
186
+ def workgroup
187
+ return @workgroup
188
+ end
189
+ alias :ntdomain :workgroup
190
+
191
+ def check_workgroup(v)
192
+ if v && v!='' && self.parser.regexp[:HOST] !~ v
193
+ raise InvalidURIError,
194
+ "bad NetBIOS workgroup (or NT domain) name: #{v}"
195
+ end
196
+ end
197
+ private :check_workgroup
198
+
199
+ def set_workgroup(v)
200
+ @workgroup = v
201
+ build_query
202
+ return @workgroup
203
+ end
204
+ protected :set_workgroup
205
+
206
+ def workgroup=(v)
207
+ check_workgroup(v)
208
+ set_workgroup(v)
209
+ end
210
+
211
+ ## returns the NetBIOS source name or address.
212
+ def calling
213
+ return @calling
214
+ end
215
+
216
+ def check_calling(v)
217
+ if v && v!='' && self.parser.regexp[:HOST] !~ v
218
+ raise InvalidURIError,
219
+ "bad NetBIOS calling (source) name: #{v}"
220
+ end
221
+ end
222
+ private :check_calling
223
+
224
+ def set_calling(v)
225
+ @calling = v
226
+ build_query
227
+ return @calling
228
+ end
229
+ protected :set_calling
230
+
231
+ def calling=(v)
232
+ check_calling(v)
233
+ set_calling(v)
234
+ end
235
+
236
+ ## returns the NetBIOS destination name or address.
237
+ def called
238
+ return @called
239
+ end
240
+
241
+ def check_called(v)
242
+ if v && v!='' && self.parser.regexp[:HOST] !~ v
243
+ raise InvalidURIError,
244
+ "bad NetBIOS called (destination) name: #{v}"
245
+ end
246
+ end
247
+ private :check_called
248
+
249
+ def set_called(v)
250
+ @called = v
251
+ build_query
252
+ return @called
253
+ end
254
+ protected :set_called
255
+
256
+ def called=(v)
257
+ check_called(v)
258
+ set_called(v)
259
+ end
260
+
261
+ ## returns the broadcast address.
262
+ def broadcast
263
+ return @broadcast
264
+ end
265
+
266
+ def check_broadcast(v)
267
+ ## FIXME
268
+ end
269
+ private :check_broadcast
270
+
271
+ def set_broadcast(v)
272
+ @broadcast = v
273
+ build_query
274
+ return @broadcast
275
+ end
276
+ protected :set_broadcast
277
+
278
+ def broadcast=(v)
279
+ check_broadcast(v)
280
+ set_broadcast(v)
281
+ end
282
+
283
+ ## returns the NetBIOS node type.
284
+ def nodetype
285
+ return @nodetype
286
+ end
287
+
288
+ def check_nodetype(v)
289
+ if v && v!='' && !NODETYPE.include?(v.downcase)
290
+ raise InvalidURIError,
291
+ "bad nodetype in SMB URI: #{v}"
292
+ end
293
+ end
294
+ private :check_nodetype
295
+
296
+ def set_nodetype(v)
297
+ @nodetype = v
298
+ build_query
299
+ return @nodetype
300
+ end
301
+ protected :set_nodetype
302
+
303
+ def nodetype=(v)
304
+ check_nodetype(v)
305
+ set_nodetype(v)
306
+ end
307
+
308
+ ## returns the NetBIOS scope ID.
309
+ def scopeid
310
+ return @scopeid
311
+ end
312
+
313
+ def check_scopeid(v)
314
+ ## FIXME
315
+ end
316
+ private :check_scopeid
317
+
318
+ def set_scopeid(v)
319
+ @scopeid = v
320
+ build_query
321
+ return @scopeid
322
+ end
323
+ protected :set_scopeid
324
+
325
+ def scopeid=(v)
326
+ check_scopeid(v)
327
+ set_scopeid(v)
328
+ end
329
+ end
330
+
331
+ @@schemes['SMB'] = SMB
332
+ end
333
+
data/test/test_smb.rb ADDED
@@ -0,0 +1,169 @@
1
+ require 'test/unit'
2
+ require 'uri/smb'
3
+
4
+ module URI
5
+
6
+ class TestSMB < Test::Unit::TestCase
7
+ def setup
8
+ end
9
+
10
+ def teardown
11
+ end
12
+
13
+ def uri_to_ary(uri)
14
+ uri.class.component.collect {|c| uri.send(c)}
15
+ end
16
+
17
+ def test_parse
18
+ uri = 'smb://example.jp/share/path'
19
+ u = URI.parse(uri)
20
+ assert_kind_of(URI::SMB, u)
21
+ assert_equal(uri, u.to_s)
22
+ assert_equal('smb', u.scheme)
23
+ assert_equal('example.jp', u.host)
24
+ assert_equal('/share/path', u.path)
25
+
26
+ uri = 'smb://domain;user:pass@example.jp/share/path'
27
+ u = URI.parse(uri)
28
+ assert_equal('domain;user:pass', u.userinfo)
29
+
30
+ uris = {
31
+ 'smb://server' =>
32
+ ['smb', nil, 'server', URI::SMB::DEFAULT_PORT,
33
+ '', '',
34
+ nil, nil, nil, nil,
35
+ nil, nil, nil],
36
+ 'smb://server/share/path' =>
37
+ ['smb', nil, 'server', URI::SMB::DEFAULT_PORT,
38
+ 'share', '/share/path',
39
+ nil, nil, nil, nil,
40
+ nil, nil, nil],
41
+ 'smb://server/share?nbns=10.0.0.1&workgroup=DOMAIN' =>
42
+ ['smb', nil, 'server', URI::SMB::DEFAULT_PORT,
43
+ 'share', '/share',
44
+ '10.0.0.1', 'DOMAIN', nil, nil,
45
+ nil, nil, nil],
46
+ 'smb://server/share?wins=10.0.0.1&ntdomain=DOMAIN' =>
47
+ ['smb', nil, 'server', URI::SMB::DEFAULT_PORT,
48
+ 'share', '/share',
49
+ '10.0.0.1', 'DOMAIN', nil, nil,
50
+ nil, nil, nil],
51
+ 'smb://server/share/path?calling=src&called=dst' =>
52
+ ['smb', nil, 'server', URI::SMB::DEFAULT_PORT,
53
+ 'share', '/share/path',
54
+ nil, nil, 'src', 'dst',
55
+ nil, nil, nil],
56
+ 'smb://server/share/path?broadcast=10.255.255.255&nodetype=P&scopeid=foo' =>
57
+ ['smb', nil, 'server', URI::SMB::DEFAULT_PORT,
58
+ 'share', '/share/path',
59
+ nil, nil, nil, nil,
60
+ '10.255.255.255', 'P', 'foo'],
61
+ }.each do |uri, ary|
62
+ u = URI.parse(uri)
63
+ assert_equal(ary, uri_to_ary(u))
64
+ end
65
+
66
+ assert_raise(URI::InvalidURIError) do
67
+ URI.parse('smb://foo_bar/share/path')
68
+ end
69
+ end
70
+
71
+ def test_parse_netbioshostname
72
+ uri = 'smb://foo_bar/share/path'
73
+ u = URI::SMB.parse(uri)
74
+ assert_kind_of(URI::SMB, u)
75
+ assert_equal(uri, u.to_s)
76
+ assert_equal('smb', u.scheme)
77
+ assert_equal('foo_bar', u.host)
78
+ assert_equal('/share/path', u.path)
79
+
80
+ assert_nothing_raised(URI::InvalidURIError) do
81
+ URI::SMB.parse('smb://foo_barxxxxxxxx/share/path')
82
+ end
83
+ assert_raise(URI::InvalidURIError) do
84
+ URI::SMB.parse('smb://foo_barxxxxxxxxx/share/path')
85
+ end
86
+ end
87
+
88
+ def test_modify
89
+ uri = 'smb://example.jp/share/path'
90
+ u = URI.parse(uri)
91
+
92
+ share = 'foo'
93
+ uri.sub!(/share/, share)
94
+ u.share = share
95
+ assert_equal(uri, u.to_s)
96
+ assert_equal(share, u.share)
97
+ assert_raise(URI::InvalidURIError) do
98
+ u.share = 'invalid/name'
99
+ end
100
+
101
+ nbns = '10.0.0.1'
102
+ uri += "?nbns=#{nbns}"
103
+ u.nbns = nbns
104
+ assert_equal(uri, u.to_s)
105
+ assert_equal(nbns, u.nbns)
106
+ assert_raise(URI::InvalidURIError) do
107
+ u.nbns = 'invalid value'
108
+ end
109
+
110
+ workgroup = 'domain'
111
+ uri += "&workgroup=#{workgroup}"
112
+ u.workgroup = workgroup
113
+ assert_equal(uri, u.to_s)
114
+ assert_equal(workgroup, u.workgroup)
115
+ assert_raise(URI::InvalidURIError) do
116
+ u.workgroup = 'invalid value'
117
+ end
118
+
119
+ calling = 'source'
120
+ uri += "&calling=#{calling}"
121
+ u.calling = calling
122
+ assert_equal(uri, u.to_s)
123
+ assert_equal(calling, u.calling)
124
+ assert_raise(URI::InvalidURIError) do
125
+ u.called = 'invalid value'
126
+ end
127
+
128
+ called = 'source'
129
+ uri += "&called=#{called}"
130
+ u.called = called
131
+ assert_equal(uri, u.to_s)
132
+ assert_equal(called, u.called)
133
+ assert_raise(URI::InvalidURIError) do
134
+ u.called = 'invalid value'
135
+ end
136
+
137
+ broadcast = '10.255.255.255'
138
+ uri += "&broadcast=#{broadcast}"
139
+ u.broadcast = broadcast
140
+ assert_equal(uri, u.to_s)
141
+ assert_equal(broadcast, u.broadcast)
142
+ ## FIXME
143
+ #assert_raise(URI::InvalidURIError) do
144
+ # u.broadcast = 'invalid value'
145
+ #end
146
+
147
+ nodetype = 'p'
148
+ uri += "&nodetype=#{nodetype}"
149
+ u.nodetype = nodetype
150
+ assert_equal(uri, u.to_s)
151
+ assert_equal(nodetype, u.nodetype)
152
+ assert_raise(URI::InvalidURIError) do
153
+ u.nodetype = 'invalid value'
154
+ end
155
+
156
+ scopeid = 'scope'
157
+ uri += "&scopeid=#{scopeid}"
158
+ u.scopeid = scopeid
159
+ assert_equal(uri, u.to_s)
160
+ assert_equal(scopeid, u.scopeid)
161
+ ## FIXME
162
+ #assert_raise(URI::InvalidURIError) do
163
+ # u.scopeid = 'invalid value'
164
+ #end
165
+ end
166
+ end
167
+
168
+ end
169
+
data/uri-smb.gemspec ADDED
@@ -0,0 +1,20 @@
1
+ # -*- encoding: utf-8 -*-
2
+ $:.push File.expand_path("../lib", __FILE__)
3
+ require "uri/smb/version"
4
+
5
+ Gem::Specification.new do |s|
6
+ s.name = "uri-smb"
7
+ s.version = URI::SMB::VERSION
8
+ s.authors = ["SATOH Fumiyasu"]
9
+ s.email = ["fumiyas@osstech.co.jp"]
10
+ s.homepage = ""
11
+ s.summary = %q{SMB URI class}
12
+ s.description = %q{SMB URI class}
13
+
14
+ s.rubyforge_project = "uri-smb"
15
+
16
+ s.files = `git ls-files`.split("\n")
17
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
18
+ s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
19
+ s.require_paths = ["lib"]
20
+ end
metadata ADDED
@@ -0,0 +1,52 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: uri-smb
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - SATOH Fumiyasu
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2011-11-01 00:00:00.000000000 Z
13
+ dependencies: []
14
+ description: SMB URI class
15
+ email:
16
+ - fumiyas@osstech.co.jp
17
+ executables: []
18
+ extensions: []
19
+ extra_rdoc_files: []
20
+ files:
21
+ - Gemfile
22
+ - Rakefile
23
+ - lib/uri/smb.rb
24
+ - lib/uri/smb/version.rb
25
+ - test/test_smb.rb
26
+ - uri-smb.gemspec
27
+ homepage: ''
28
+ licenses: []
29
+ post_install_message:
30
+ rdoc_options: []
31
+ require_paths:
32
+ - lib
33
+ required_ruby_version: !ruby/object:Gem::Requirement
34
+ none: false
35
+ requirements:
36
+ - - ! '>='
37
+ - !ruby/object:Gem::Version
38
+ version: '0'
39
+ required_rubygems_version: !ruby/object:Gem::Requirement
40
+ none: false
41
+ requirements:
42
+ - - ! '>='
43
+ - !ruby/object:Gem::Version
44
+ version: '0'
45
+ requirements: []
46
+ rubyforge_project: uri-smb
47
+ rubygems_version: 1.8.10
48
+ signing_key:
49
+ specification_version: 3
50
+ summary: SMB URI class
51
+ test_files:
52
+ - test/test_smb.rb