rspec-networking 0.0.1 → 0.1.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.
@@ -0,0 +1,343 @@
1
+ 009EC8
2
+ 00C30A
3
+ 00EC0A
4
+ 04106B
5
+ 046761
6
+ 047A0B
7
+ 04AE47
8
+ 04B167
9
+ 04C807
10
+ 04CF8C
11
+ 04D13A
12
+ 04E598
13
+ 081C6E
14
+ 082525
15
+ 08B339
16
+ 0C07DF
17
+ 0C1DAF
18
+ 0C9838
19
+ 0CC6FD
20
+ 0CEDC8
21
+ 0CF346
22
+ 102AB3
23
+ 103F44
24
+ 10C197
25
+ 1449D4
26
+ 14907A
27
+ 14993E
28
+ 14D881
29
+ 14F65A
30
+ 1801F1
31
+ 185936
32
+ 188740
33
+ 18F0E4
34
+ 1C2575
35
+ 1C2AB0
36
+ 1C8BEF
37
+ 1CCCD6
38
+ 1CEAAC
39
+ 2025CC
40
+ 203462
41
+ 2034FB
42
+ 203B34
43
+ 2047DA
44
+ 2072A9
45
+ 2082C0
46
+ 209952
47
+ 20A60C
48
+ 20F478
49
+ 241145
50
+ 246477
51
+ 24CF24
52
+ 24D337
53
+ 28167F
54
+ 285923
55
+ 286C07
56
+ 28D127
57
+ 28E31F
58
+ 2C0B97
59
+ 2C0DCF
60
+ 2C195C
61
+ 2CD066
62
+ 2CFE4F
63
+ 3007EB
64
+ 3050CE
65
+ 341CF0
66
+ 343932
67
+ 3480B3
68
+ 34B98D
69
+ 34CE00
70
+ 34F015
71
+ 34FA1C
72
+ 38A4ED
73
+ 38C1ED
74
+ 38C6BD
75
+ 38E60A
76
+ 3C135A
77
+ 3C2CA6
78
+ 3C3824
79
+ 3C7F6E
80
+ 3CAFB7
81
+ 3CBD3E
82
+ 3CCD57
83
+ 400877
84
+ 40313C
85
+ 44237C
86
+ 444A37
87
+ 44579F
88
+ 447147
89
+ 44BDC8
90
+ 44CBAD
91
+ 44DF65
92
+ 44E213
93
+ 44F770
94
+ 482CA0
95
+ 488759
96
+ 48FDA3
97
+ 4C0220
98
+ 4C49E3
99
+ 4C55B2
100
+ 4C6371
101
+ 4C8E19
102
+ 4CC64C
103
+ 4CE0DB
104
+ 4CE20F
105
+ 4CF202
106
+ 503DC6
107
+ 504F3B
108
+ 50642B
109
+ 508811
110
+ 508E49
111
+ 508F4C
112
+ 50926A
113
+ 509839
114
+ 50A009
115
+ 50D2F5
116
+ 50DAD6
117
+ 50EC50
118
+ 50FE39
119
+ 5448E6
120
+ 582059
121
+ 584498
122
+ 58B623
123
+ 58EA1F
124
+ 5C0214
125
+ 5C4071
126
+ 5CD06E
127
+ 5CE50C
128
+ 606EE8
129
+ 60AB67
130
+ 60F723
131
+ 640980
132
+ 646306
133
+ 64644A
134
+ 6490C1
135
+ 649E31
136
+ 64A200
137
+ 64B473
138
+ 64CC2E
139
+ 64DDE9
140
+ 684DB6
141
+ 68ABBC
142
+ 68B8BB
143
+ 68C44C
144
+ 68DFDD
145
+ 6C0699
146
+ 6C0DC4
147
+ 6C483F
148
+ 6CF784
149
+ 70217F
150
+ 703A51
151
+ 705FA3
152
+ 709751
153
+ 70BBE9
154
+ 741575
155
+ 742344
156
+ 743822
157
+ 7451BA
158
+ 74F2FA
159
+ 7802F8
160
+ 7811DC
161
+ 785333
162
+ 789987
163
+ 78D840
164
+ 7C035E
165
+ 7C03AB
166
+ 7C0CF1
167
+ 7C1DD9
168
+ 7C2ADB
169
+ 7C49EB
170
+ 7CA449
171
+ 7CC294
172
+ 7CD661
173
+ 7CFD6B
174
+ 8035C1
175
+ 808F97
176
+ 80AD16
177
+ 80E63C
178
+ 844693
179
+ 84AEDE
180
+ 882F92
181
+ 884604
182
+ 8852EB
183
+ 886C60
184
+ 88B951
185
+ 88C397
186
+ 8C53C3
187
+ 8C5AF8
188
+ 8C7A3D
189
+ 8CAACE
190
+ 8CBEBE
191
+ 8CD0B2
192
+ 8CD9D6
193
+ 8CDEF9
194
+ 902AEE
195
+ 9078B2
196
+ 90FB5D
197
+ 941700
198
+ 94626D
199
+ 947BAE
200
+ 9487E0
201
+ 948B93
202
+ 94D331
203
+ 9812E0
204
+ 98171A
205
+ 987552
206
+ 98E081
207
+ 98EE94
208
+ 98F621
209
+ 98FAE3
210
+ 9C28F7
211
+ 9C2EA1
212
+ 9C5A81
213
+ 9C99A0
214
+ 9C9D7E
215
+ 9C9ED5
216
+ 9CBCF0
217
+ A086C6
218
+ A439B3
219
+ A44519
220
+ A44BD5
221
+ A45046
222
+ A45590
223
+ A4A930
224
+ A4BA70
225
+ A4C3BE
226
+ A4C788
227
+ A4CCB3
228
+ A4E287
229
+ A4FF9F
230
+ A82BD5
231
+ A86A86
232
+ A89CED
233
+ AC1E9E
234
+ AC8C46
235
+ ACC1EE
236
+ ACE4D8
237
+ ACF7F3
238
+ B00BE2
239
+ B09C63
240
+ B0E235
241
+ B405A1
242
+ B460ED
243
+ B47E9F
244
+ B4C4FC
245
+ B83BCC
246
+ B850D8
247
+ B852E0
248
+ B85384
249
+ B894E7
250
+ B8EA98
251
+ BC6193
252
+ BC6AD1
253
+ BC7FA4
254
+ C01693
255
+ C05B44
256
+ C40BCB
257
+ C46940
258
+ C46AB7
259
+ C4710F
260
+ C493BB
261
+ C82832
262
+ C83DDC
263
+ C85CCC
264
+ C8BF4C
265
+ CC033D
266
+ CC4210
267
+ CC4D75
268
+ CCB5D1
269
+ CCD843
270
+ CCDA20
271
+ CCEB5E
272
+ D09C7A
273
+ D0AE05
274
+ D0C1BF
275
+ D0CEC0
276
+ D41761
277
+ D43538
278
+ D4438A
279
+ D4532A
280
+ D45EEC
281
+ D4970B
282
+ D4A365
283
+ D4DA21
284
+ D4F0EA
285
+ D832E3
286
+ D86375
287
+ D893D4
288
+ D8B053
289
+ D8CE3A
290
+ D8E374
291
+ D8EDA8
292
+ DC6AE7
293
+ DCB72E
294
+ DCED83
295
+ E01F88
296
+ E06267
297
+ E0806B
298
+ E0B655
299
+ E0CCF8
300
+ E0DCFF
301
+ E41B43
302
+ E44519
303
+ E446DA
304
+ E484D3
305
+ E4AAE4
306
+ E4BCAA
307
+ E4D398
308
+ E4DB6D
309
+ E4FE43
310
+ E84A54
311
+ E85A8B
312
+ E85FB4
313
+ E87EEF
314
+ E88843
315
+ E89847
316
+ E8BA17
317
+ E8F791
318
+ EC1055
319
+ EC30B3
320
+ EC4118
321
+ EC4D3E
322
+ ECD09F
323
+ ECFA5C
324
+ F06C5D
325
+ F0B429
326
+ F41A9C
327
+ F4308B
328
+ F460E2
329
+ F48B32
330
+ F4F5DB
331
+ F843EF
332
+ F8710C
333
+ F88306
334
+ F8A45F
335
+ F8AB82
336
+ FC0296
337
+ FC1999
338
+ FC4345
339
+ FC5B8C
340
+ FC64BA
341
+ FCA9F5
342
+ FCC17D
343
+ FCD908
@@ -0,0 +1,72 @@
1
+ 001349
2
+ 0019CB
3
+ 0023F8
4
+ 00A0C5
5
+ 042336
6
+ 04BF6D
7
+ 082697
8
+ 1071B3
9
+ 107BEF
10
+ 10C5FA
11
+ 143375
12
+ 14360E
13
+ 14C7C4
14
+ 1C740D
15
+ 28285D
16
+ 301577
17
+ 30BD13
18
+ 3CF75D
19
+ 404A03
20
+ 445E82
21
+ 4463C2
22
+ 48EDE6
23
+ 4C9EFF
24
+ 4CC53E
25
+ 5067F0
26
+ 50E039
27
+ 54833A
28
+ 588BF3
29
+ 5C648E
30
+ 5C6A80
31
+ 5CE28C
32
+ 5CF4AB
33
+ 603197
34
+ 64DD68
35
+ 6C4F89
36
+ 7049A2
37
+ 78C57D
38
+ 7C7716
39
+ 80EA0B
40
+ 88ACC0
41
+ 88F3D5
42
+ 8C5973
43
+ 909F22
44
+ 90EF68
45
+ 980D67
46
+ A0E4CB
47
+ B0B2DC
48
+ B8D526
49
+ B8ECA3
50
+ BC7EC3
51
+ BC9911
52
+ BCCF4F
53
+ C02E5F
54
+ C49A31
55
+ C83374
56
+ C8544B
57
+ C86C87
58
+ CC5D4E
59
+ D41AD1
60
+ D43DF3
61
+ D8912A
62
+ D8ECE5
63
+ E4186B
64
+ E8377A
65
+ EC3EB3
66
+ EC43F6
67
+ F08756
68
+ F44D5C
69
+ F80DA9
70
+ FC22F4
71
+ FC9F2A
72
+ FCF528
@@ -1,26 +1,105 @@
1
- # https://en.wikipedia.org/wiki/MAC_address
1
+ require "rspec/networking/mac_address_manufacturers"
2
+
3
+ module RSpec
4
+ module Networking
5
+ module MacAddress
6
+ # MM:MM:MM:SS:SS:SS, MM-MM-MM-SS-SS-SS, MMMM.MMSS.SSSS
7
+ EUI48 = /\A\h{2}([:-])(\h{2}\1){4}\h{2}\z|\A\h{4}(\.\h{4}){2}\z/
8
+
9
+ # MM:MM:MM:FF:FE:SS:SS:SS, MMMM:MMFF:FESS:SSSS
10
+ EUI64 = /\A\h{2}([:-])(\h{2}\1){6}\h{2}\z|\A\h{4}(:\h{4}){3}\z/
11
+
12
+ # half an EUI-48: MM:MM:MM or SS-SS-SS
13
+ HALF = /\A\h{2}([:-])\h{2}\1\h{2}\z/
14
+
15
+ def self.normalize(str)
16
+ str.delete(".:-").upcase
17
+ end
18
+ end
19
+ end
20
+ end
2
21
 
3
22
  RSpec::Matchers.define :be_a_mac_address do
4
- match do |actual|
5
- @actual = actual
23
+ mac = RSpec::Networking::MacAddress
6
24
 
7
- return false unless actual.is_a?(String)
25
+ chain :from do |manufacturer|
26
+ @manufacturer = manufacturer
8
27
 
9
- hex = ['\h{2}'] * 5
10
- actual.match?(/^\h{2}([:-])#{hex.join('\1')}$/)
28
+ @prefixes = if mac::HALF.match?(manufacturer.to_s)
29
+ Set[mac.normalize(manufacturer)]
30
+ else
31
+ RSpec::Networking::MANUFACTURERS.fetch(manufacturer.to_s.downcase.tr(" ", "_")) do
32
+ raise ArgumentError, "unknown manufacturer: #{manufacturer}"
33
+ end
34
+ end
11
35
  end
12
36
 
13
- description do
14
- "a MAC address"
37
+ chain :for do |device|
38
+ raise ArgumentError, "invalid device: #{device}" unless mac::HALF.match?(device.to_s)
39
+
40
+ @device = device
41
+ @suffix = mac.normalize(device)
42
+ end
43
+
44
+ chain :bits do |bits|
45
+ raise ArgumentError, "invalid bit length: #{bits}" unless [48, 64].include?(bits)
46
+
47
+ @bits = bits
48
+ end
49
+
50
+ chain :broadcast do
51
+ @broadcast = true
15
52
  end
16
53
 
17
- failure_message do
18
- "expected '#{@actual}' to be #{description}"
54
+ chain :unicast do
55
+ @cast = :unicast
19
56
  end
20
57
 
21
- failure_message_when_negated do
22
- "expected '#{@actual}' not to be #{description}"
58
+ chain :multicast do
59
+ @cast = :multicast
60
+ end
61
+
62
+ match do |actual|
63
+ return false unless actual.is_a?(String)
64
+
65
+ if mac::EUI64.match?(actual)
66
+ return false if @bits == 48
67
+
68
+ hex = mac.normalize(actual)
69
+ return false unless hex[6, 4] == "FFFE"
70
+
71
+ # normalize to 48 bits
72
+ hex = hex[0, 6] + hex[10, 6]
73
+ elsif mac::EUI48.match?(actual)
74
+ return false if @bits == 64
75
+
76
+ hex = mac.normalize(actual)
77
+ else
78
+ return false
79
+ end
80
+
81
+ return false if @broadcast && hex != "FF" * 6
82
+
83
+ # the I/G bit: least significant bit of the first octet
84
+ return false if @cast && hex[0, 2].to_i(16).odd? != (@cast == :multicast)
85
+
86
+ return false if @prefixes && !@prefixes.include?(hex[0, 6])
87
+ return false if @suffix && @suffix != hex[6, 6]
88
+
89
+ true
90
+ end
91
+
92
+ description do
93
+ [
94
+ "be a",
95
+ ("broadcast" if @broadcast),
96
+ @cast,
97
+ "MAC address",
98
+ ("with #{@bits} bits" if @bits),
99
+ ("from #{@manufacturer}" if @manufacturer),
100
+ ("for #{@device}" if @device),
101
+ ].compact.join(" ")
23
102
  end
24
103
  end
25
104
 
26
- RSpec::Matchers.alias_matcher :a_mac_address, :be_a_mac_address
105
+ RSpec::Matchers.alias_matcher(:a_mac_address, :be_a_mac_address) { |desc| desc.delete_prefix("be ") }
@@ -0,0 +1,10 @@
1
+ require "set"
2
+
3
+ module RSpec
4
+ module Networking
5
+ # generated by script/update_manufacturers
6
+ MANUFACTURERS = Dir["#{__dir__}/mac_address/*.txt"].to_h do |file|
7
+ [File.basename(file, ".txt"), Set.new(File.readlines(file, chomp: true))]
8
+ end.freeze
9
+ end
10
+ end
@@ -1,5 +1,5 @@
1
1
  module RSpec
2
2
  module Networking
3
- VERSION = "0.0.1"
3
+ VERSION = "0.1.1"
4
4
  end
5
5
  end
@@ -1,22 +1,25 @@
1
1
  require_relative "lib/rspec/networking/version"
2
- package = RSpec::Networking
3
- package_name = "rspec-networking"
4
2
 
5
3
  Gem::Specification.new do |s|
6
4
  s.authors = ["Daniel Pepper"]
7
- s.description = "RSpec matchers for IP and MAC Addresses"
5
+ s.description = "RSpec matchers for IP and MAC addresses"
8
6
  s.files = `git ls-files * ':!:spec'`.split("\n")
9
- s.homepage = "https://github.com/dpep/#{package_name}"
7
+ s.homepage = "https://github.com/dpep/rspec-networking"
10
8
  s.license = "MIT"
11
- s.name = package_name
12
- s.summary = package.to_s
13
- s.version = package.const_get "VERSION"
9
+ s.name = "rspec-networking"
10
+ s.summary = "RSpec matchers for IP and MAC addresses"
11
+ s.version = RSpec::Networking::VERSION
12
+
13
+ s.metadata = {
14
+ "changelog_uri" => "https://github.com/dpep/rspec-networking/blob/main/CHANGELOG.md",
15
+ "rubygems_mfa_required" => "true",
16
+ }
14
17
 
15
18
  s.required_ruby_version = ">= 3"
16
19
 
17
20
  s.add_dependency "rspec-expectations", ">= 3"
18
21
 
19
- s.add_development_dependency "byebug"
22
+ s.add_development_dependency "debug"
20
23
  s.add_development_dependency "faker"
21
24
  s.add_development_dependency "rspec"
22
25
  s.add_development_dependency "simplecov"
@@ -0,0 +1,43 @@
1
+ #!/usr/bin/env ruby
2
+ # Regenerates lib/rspec/networking/mac_address/*.txt from the IEEE OUI registry.
3
+ #
4
+ # usage: script/update_manufacturers [path/to/oui.csv]
5
+
6
+ require "csv"
7
+ require "net/http"
8
+
9
+ URL = "https://standards-oui.ieee.org/oui/oui.csv"
10
+ DIR = File.expand_path("../lib/rspec/networking/mac_address", __dir__)
11
+
12
+ # matched against the registry's "Organization Name"
13
+ MANUFACTURERS = {
14
+ "apple" => /\AApple, Inc/,
15
+ "eero" => /\Aeero/i,
16
+ "google" => /\AGoogle/,
17
+ "microsoft" => /\AMicrosoft/i,
18
+ "nokia" => /\ANokia/,
19
+ "oracle" => /\AOracle/,
20
+ "sony" => /\ASony/i,
21
+ "texas_instruments" => /\ATexas Instruments/,
22
+ "toshiba" => /Toshiba/i,
23
+ "xerox" => /\AXerox/i,
24
+ "xiaomi" => /Xiaomi/i,
25
+ "zyxel" => /Zyxel/i,
26
+ }
27
+
28
+ csv = ARGV[0] ? File.read(ARGV[0]) : Net::HTTP.get(URI(URL))
29
+
30
+ # only MA-L assignments are full 24-bit OUIs
31
+ rows = CSV.parse(csv, headers: true).select { |row| row["Registry"] == "MA-L" }
32
+
33
+ MANUFACTURERS.each do |name, pattern|
34
+ ouis = rows.select { |row| row["Organization Name"].to_s.strip.match?(pattern) }
35
+ .map { |row| row["Assignment"].upcase }
36
+ .sort
37
+ .uniq
38
+
39
+ abort "no OUIs found for #{name}" if ouis.empty?
40
+
41
+ File.write("#{DIR}/#{name}.txt", ouis.join("\n") + "\n")
42
+ puts "#{name}: #{ouis.size}"
43
+ end
metadata CHANGED
@@ -1,14 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rspec-networking
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.1
4
+ version: 0.1.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Daniel Pepper
8
- autorequire:
9
8
  bindir: bin
10
9
  cert_chain: []
11
- date: 2024-08-31 00:00:00.000000000 Z
10
+ date: 1980-01-02 00:00:00.000000000 Z
12
11
  dependencies:
13
12
  - !ruby/object:Gem::Dependency
14
13
  name: rspec-expectations
@@ -25,7 +24,7 @@ dependencies:
25
24
  - !ruby/object:Gem::Version
26
25
  version: '3'
27
26
  - !ruby/object:Gem::Dependency
28
- name: byebug
27
+ name: debug
29
28
  requirement: !ruby/object:Gem::Requirement
30
29
  requirements:
31
30
  - - ">="
@@ -80,8 +79,7 @@ dependencies:
80
79
  - - ">="
81
80
  - !ruby/object:Gem::Version
82
81
  version: '0'
83
- description: RSpec matchers for IP and MAC Addresses
84
- email:
82
+ description: RSpec matchers for IP and MAC addresses
85
83
  executables: []
86
84
  extensions: []
87
85
  extra_rdoc_files: []
@@ -95,13 +93,28 @@ files:
95
93
  - lib/rspec/networking.rb
96
94
  - lib/rspec/networking/ip_address.rb
97
95
  - lib/rspec/networking/mac_address.rb
96
+ - lib/rspec/networking/mac_address/apple.txt
97
+ - lib/rspec/networking/mac_address/eero.txt
98
+ - lib/rspec/networking/mac_address/google.txt
99
+ - lib/rspec/networking/mac_address/microsoft.txt
100
+ - lib/rspec/networking/mac_address/nokia.txt
101
+ - lib/rspec/networking/mac_address/oracle.txt
102
+ - lib/rspec/networking/mac_address/sony.txt
103
+ - lib/rspec/networking/mac_address/texas_instruments.txt
104
+ - lib/rspec/networking/mac_address/toshiba.txt
105
+ - lib/rspec/networking/mac_address/xerox.txt
106
+ - lib/rspec/networking/mac_address/xiaomi.txt
107
+ - lib/rspec/networking/mac_address/zyxel.txt
108
+ - lib/rspec/networking/mac_address_manufacturers.rb
98
109
  - lib/rspec/networking/version.rb
99
110
  - rspec-networking.gemspec
111
+ - script/update_manufacturers
100
112
  homepage: https://github.com/dpep/rspec-networking
101
113
  licenses:
102
114
  - MIT
103
- metadata: {}
104
- post_install_message:
115
+ metadata:
116
+ changelog_uri: https://github.com/dpep/rspec-networking/blob/main/CHANGELOG.md
117
+ rubygems_mfa_required: 'true'
105
118
  rdoc_options: []
106
119
  require_paths:
107
120
  - lib
@@ -116,8 +129,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
116
129
  - !ruby/object:Gem::Version
117
130
  version: '0'
118
131
  requirements: []
119
- rubygems_version: 3.5.17
120
- signing_key:
132
+ rubygems_version: 4.0.16
121
133
  specification_version: 4
122
- summary: RSpec::Networking
134
+ summary: RSpec matchers for IP and MAC addresses
123
135
  test_files: []