Class: WifiWand::Platforms::Mac::InterfaceDetector
- Inherits:
-
Object
- Object
- WifiWand::Platforms::Mac::InterfaceDetector
show all
- Includes:
- StringPredicates, Timing
- Defined in:
- lib/wifi_wand/platforms/mac/interface_detector.rb
Defined Under Namespace
Classes: DetectionResult
Constant Summary
collapse
- WIFI_PORT_PATTERNS =
[
/Wi[-\s]?Fi/i,
/Air[-\s]?Port/i,
/Wireless/i,
/WLAN/i,
].freeze
- SYSTEM_PROFILER_NETWORK_ARGS =
%w[system_profiler -json SPNetworkDataType].freeze
- SYSTEM_PROFILER_TIMEOUT_SECONDS =
SystemProfilerWifiDataProvider::SYSTEM_PROFILER_TIMEOUT_SECONDS
Instance Method Summary
collapse
-
#detect_using_networksetup(timeout_in_secs: nil, known_interface: nil) ⇒ Object
-
#detect_wifi_interface_from_profiler_networks(nets, known_interface: nil, known_service_name: nil) ⇒ Object
-
#detected_wifi_service_name(known_interface: nil, timeout_in_secs: nil) ⇒ Object
-
#fetch_hardware_ports(timeout_in_secs: nil) ⇒ Object
-
#initialize(command_runner:) ⇒ InterfaceDetector
constructor
A new instance of InterfaceDetector.
-
#is_wifi_interface?(interface) ⇒ Boolean
-
#parse_hardware_ports(output) ⇒ Object
-
#probe(timeout_in_secs: nil, known_interface: nil, known_service_name: nil) ⇒ Object
-
#wifi_interface_using_networksetup(timeout_in_secs: nil, known_interface: nil) ⇒ Object
-
#wifi_interface_using_system_profiler(timeout_in_secs: nil, known_interface: nil, known_service_name: nil) ⇒ Object
-
#wifi_port_from_ports(ports) ⇒ Object
-
#wifi_service_name(known_interface: nil, timeout_in_secs: nil) ⇒ Object
-
#wifi_service_name_from_ports(ports, known_interface: nil, fallback_service_name: 'Wi-Fi') ⇒ Object
Methods included from Timing
monotonic_now, status_deadline, status_timeout_for
string_nil_or_blank?, string_nil_or_empty?
Constructor Details
Returns a new instance of InterfaceDetector.
30
31
32
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 30
def initialize(command_runner:)
@command_runner = command_runner
end
|
Instance Method Details
#detect_using_networksetup(timeout_in_secs: nil, known_interface: nil) ⇒ Object
103
104
105
106
107
108
109
110
111
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 103
def detect_using_networksetup(timeout_in_secs: nil, known_interface: nil)
result = wifi_interface_using_networksetup(
timeout_in_secs: timeout_in_secs,
known_interface: known_interface
)
raise WifiInterfaceError if string_nil_or_empty?(result.interface)
result
end
|
#detect_wifi_interface_from_profiler_networks(nets, known_interface: nil, known_service_name: nil) ⇒ Object
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 171
def detect_wifi_interface_from_profiler_networks(nets, known_interface: nil,
known_service_name: nil)
wifi = if known_service_name && !known_service_name.empty?
nets.find { |net| net['_name'] == known_service_name }
end
wifi ||= if known_interface && !known_interface.empty?
nets.find { |net| net['interface'] == known_interface }
end
wifi ||= nets.find do |net|
name = net['_name'].to_s
WIFI_PORT_PATTERNS.any? { |pattern| pattern.match?(name) }
end
DetectionResult.new(
interface: present_string(wifi && wifi['interface']),
service_name: present_string(wifi && wifi['_name'])
)
end
|
#detected_wifi_service_name(known_interface: nil, timeout_in_secs: nil) ⇒ Object
95
96
97
98
99
100
101
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 95
def detected_wifi_service_name(known_interface: nil, timeout_in_secs: nil)
wifi_service_name_from_ports(
fetch_hardware_ports(timeout_in_secs: timeout_in_secs),
known_interface: known_interface,
fallback_service_name: nil
)
end
|
#fetch_hardware_ports(timeout_in_secs: nil) ⇒ Object
34
35
36
37
38
39
40
41
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 34
def fetch_hardware_ports(timeout_in_secs: nil)
output = command_runner.call(
%w[networksetup -listallhardwareports],
timeout_in_secs: timeout_in_secs
).stdout
parse_hardware_ports(output)
end
|
#is_wifi_interface?(interface) ⇒ Boolean
192
193
194
195
196
197
198
199
200
201
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 192
def is_wifi_interface?(interface)
command_runner.call(['networksetup', '-listpreferredwirelessnetworks', interface])
true
rescue WifiWand::CommandExecutor::OsCommandError => e
if e.exitstatus == 10
false
else
raise
end
end
|
#parse_hardware_ports(output) ⇒ Object
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 43
def parse_hardware_ports(output)
ports = []
current = {}
output.each_line do |line|
stripped = line.strip
next if stripped.empty?
if (match = stripped.match(/^Hardware Port:\s*(.+)$/))
ports << current if current[:device]
current = { name: match[1] }
elsif (match = stripped.match(/^Device:\s*(.+)$/))
current[:device] = match[1]
elsif (match = stripped.match(/^Ethernet Address:\s*(.+)$/))
current[:ethernet_address] = match[1]
end
end
ports << current if current[:device]
ports
end
|
#probe(timeout_in_secs: nil, known_interface: nil, known_service_name: nil) ⇒ Object
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 113
def probe(timeout_in_secs: nil, known_interface: nil, known_service_name: nil)
deadline = status_deadline(timeout_in_secs)
networksetup_result = nil
begin
networksetup_result = wifi_interface_using_networksetup(
timeout_in_secs: status_timeout_for(deadline),
known_interface: known_interface
)
if networksetup_result.interface && !networksetup_result.interface.empty?
return networksetup_result
end
rescue WifiWand::Error
end
service_name = networksetup_result&.service_name || known_service_name
interface = networksetup_result&.interface || known_interface
wifi_interface_using_system_profiler(
timeout_in_secs: status_timeout_for(deadline),
known_interface: interface,
known_service_name: service_name
)
end
|
#wifi_interface_using_networksetup(timeout_in_secs: nil, known_interface: nil) ⇒ Object
138
139
140
141
142
143
144
145
146
147
148
149
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 138
def wifi_interface_using_networksetup(timeout_in_secs: nil, known_interface: nil)
ports = fetch_hardware_ports(timeout_in_secs: timeout_in_secs)
service_name = wifi_service_name_from_ports(ports, known_interface: known_interface)
wifi_port = ports.find do |port|
port[:name] == service_name && port[:device] && !port[:device].empty?
end
wifi_port ||= wifi_port_from_ports(ports)
iface = wifi_port && wifi_port[:device]
DetectionResult.new(interface: present_string(iface), service_name: present_string(service_name))
end
|
#wifi_interface_using_system_profiler(timeout_in_secs: nil, known_interface: nil, known_service_name: nil) ⇒ Object
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 151
def wifi_interface_using_system_profiler(timeout_in_secs: nil, known_interface: nil,
known_service_name: nil)
json_text = command_runner.call(
SYSTEM_PROFILER_NETWORK_ARGS,
raise_on_error: true,
timeout_in_secs: timeout_in_secs || SYSTEM_PROFILER_TIMEOUT_SECONDS
).stdout
return DetectionResult.new if string_nil_or_blank?(json_text)
net_data = JSON.parse(json_text)
nets = net_data['SPNetworkDataType']
return DetectionResult.new if nets.nil? || nets.empty?
detect_wifi_interface_from_profiler_networks(
nets,
known_interface: known_interface,
known_service_name: known_service_name
)
end
|
#wifi_port_from_ports(ports) ⇒ Object
65
66
67
68
69
70
71
72
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 65
def wifi_port_from_ports(ports)
ports.find do |port|
name = port[:name].to_s
next false if name.empty?
WIFI_PORT_PATTERNS.any? { |pattern| pattern.match?(name) }
end
end
|
#wifi_service_name(known_interface: nil, timeout_in_secs: nil) ⇒ Object
88
89
90
91
92
93
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 88
def wifi_service_name(known_interface: nil, timeout_in_secs: nil)
wifi_service_name_from_ports(
fetch_hardware_ports(timeout_in_secs: timeout_in_secs),
known_interface: known_interface
)
end
|
#wifi_service_name_from_ports(ports, known_interface: nil, fallback_service_name: 'Wi-Fi') ⇒ Object
74
75
76
77
78
79
80
81
82
83
84
85
86
|
# File 'lib/wifi_wand/platforms/mac/interface_detector.rb', line 74
def wifi_service_name_from_ports(ports, known_interface: nil, fallback_service_name: 'Wi-Fi')
wifi_port = wifi_port_from_ports(ports)
return wifi_port[:name] if wifi_port && wifi_port[:name] && !wifi_port[:name].empty?
if known_interface && !known_interface.empty?
match = ports.find do |port|
port[:device] == known_interface && port[:name] && !port[:name].empty?
end
return match[:name] if match
end
fallback_service_name
end
|