homeaway 1.0.0
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.
- checksums.yaml +7 -0
- data/LICENSE +21 -0
- data/README.md +114 -0
- data/bin/homeaway +5 -0
- data/lib/homeaway/cli.rb +140 -0
- data/lib/homeaway/config.rb +67 -0
- data/lib/homeaway/network.rb +149 -0
- data/lib/homeaway.rb +7 -0
- metadata +63 -0
checksums.yaml
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
---
|
|
2
|
+
SHA256:
|
|
3
|
+
metadata.gz: 01ef48fbd4fbbd8b863426e4cb4fda814691ee05067df920fca6fe0210c07839
|
|
4
|
+
data.tar.gz: e1606ec3e8cefde4f5beeaf19392e219ac416d8867c9b1583d2358f5cdd2f709
|
|
5
|
+
SHA512:
|
|
6
|
+
metadata.gz: 04db149ea9aed3ebd0b0c15e32d8318a6923fe69d1471b8ec31e2e41c05b52424d6b0785a55d463ae94678c33fc15119fc644fed81c16a6453a079d912661f39
|
|
7
|
+
data.tar.gz: 1eb6d2d36dea2f7f3f48a6f1ad6c9e3605f5c3a0722e4ee210816950b100ca7c78a2016b9880b2f43effe05e4caf8b241e19e15aa77ef79016672268774ff798
|
data/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2024 Good Bran
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
data/README.md
ADDED
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
# Homeaway
|
|
2
|
+
|
|
3
|
+
A CLI tool to quickly toggle your macOS WiFi between manual (static IP) and DHCP mode.
|
|
4
|
+
|
|
5
|
+
## Features
|
|
6
|
+
|
|
7
|
+
- **Smart IP Detection**: Automatically scans and finds an available IP in your subnet
|
|
8
|
+
- **DNS Management**: Clears DNS settings when switching to DHCP (configurable)
|
|
9
|
+
- **First-Run Wizard**: Interactive setup on first run
|
|
10
|
+
- **Simple Interface**: Just run `homeaway` and toggle with a single keypress
|
|
11
|
+
|
|
12
|
+
## Installation
|
|
13
|
+
|
|
14
|
+
### Via RubyGems (Recommended)
|
|
15
|
+
|
|
16
|
+
```bash
|
|
17
|
+
gem install homeaway
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
### Via curl (One-liner)
|
|
21
|
+
|
|
22
|
+
```bash
|
|
23
|
+
curl -L https://raw.githubusercontent.com/GoodBran/homeaway/main/bin/homeaway -o /usr/local/bin/homeaway && chmod +x /usr/local/bin/homeaway
|
|
24
|
+
```
|
|
25
|
+
|
|
26
|
+
### From Source
|
|
27
|
+
|
|
28
|
+
```bash
|
|
29
|
+
git clone https://github.com/GoodBran/homeaway.git
|
|
30
|
+
cd homeaway
|
|
31
|
+
ruby -Ilib bin/homeaway
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
## Usage
|
|
35
|
+
|
|
36
|
+
Simply run:
|
|
37
|
+
|
|
38
|
+
```bash
|
|
39
|
+
homeaway
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
### First Run
|
|
43
|
+
|
|
44
|
+
On first run, you'll be prompted to configure:
|
|
45
|
+
- Default router address (default: 192.168.1.1)
|
|
46
|
+
- Whether to clear DNS when toggling to DHCP (default: yes)
|
|
47
|
+
- Default DNS server (default: 8.8.8.8)
|
|
48
|
+
|
|
49
|
+
Configuration is stored at `~/.config/homeaway/config.yml`.
|
|
50
|
+
|
|
51
|
+
### Normal Usage
|
|
52
|
+
|
|
53
|
+
```bash
|
|
54
|
+
$ homeaway
|
|
55
|
+
Current mode: DHCP
|
|
56
|
+
|
|
57
|
+
Toggle to Manual mode? [Y/n]: y
|
|
58
|
+
|
|
59
|
+
Scanning for available IP in 192.168.1.x range...
|
|
60
|
+
Configuring static IP:
|
|
61
|
+
IP Address: 192.168.1.42
|
|
62
|
+
Subnet Mask: 255.255.255.0
|
|
63
|
+
Router: 192.168.1.1
|
|
64
|
+
DNS Server: 8.8.8.8
|
|
65
|
+
|
|
66
|
+
Successfully switched to Manual mode!
|
|
67
|
+
Your IP is now: 192.168.1.42
|
|
68
|
+
```
|
|
69
|
+
|
|
70
|
+
## How It Works
|
|
71
|
+
|
|
72
|
+
### Finding Available IP
|
|
73
|
+
|
|
74
|
+
When switching to manual mode, the tool:
|
|
75
|
+
1. Scans the range 192.168.1.2 through 192.168.1.254
|
|
76
|
+
2. Pings each IP to check if it's in use
|
|
77
|
+
3. Returns the first available IP address
|
|
78
|
+
|
|
79
|
+
### Network Commands Used
|
|
80
|
+
|
|
81
|
+
The tool uses macOS's built-in `networksetup` command:
|
|
82
|
+
|
|
83
|
+
- `networksetup -listallhardwareports` - Detects WiFi interface
|
|
84
|
+
- `networksetup -getinfo <device>` - Gets current configuration
|
|
85
|
+
- `networksetup -setmanual <device> <ip> <subnet> <router>` - Sets static IP
|
|
86
|
+
- `networksetup -setdhcp <device>` - Enables DHCP
|
|
87
|
+
- `networksetup -setdnsservers <device> <dns>` - Sets DNS
|
|
88
|
+
- `networksetup -setdnsservers <device> empty` - Clears DNS
|
|
89
|
+
|
|
90
|
+
## Requirements
|
|
91
|
+
|
|
92
|
+
- macOS (uses `networksetup` command)
|
|
93
|
+
- Ruby 2.6 or higher
|
|
94
|
+
- Administrator privileges (for changing network settings)
|
|
95
|
+
|
|
96
|
+
## Configuration File
|
|
97
|
+
|
|
98
|
+
```yaml
|
|
99
|
+
# ~/.config/homeaway/config.yml
|
|
100
|
+
router: 192.168.1.1
|
|
101
|
+
clear_dns_on_dhcp: true
|
|
102
|
+
dns_server: 8.8.8.8
|
|
103
|
+
subnet_mask: 255.255.255.0
|
|
104
|
+
```
|
|
105
|
+
|
|
106
|
+
## Security Note
|
|
107
|
+
|
|
108
|
+
This tool modifies system network settings. On macOS, you may need to:
|
|
109
|
+
1. Run with sudo: `sudo homeaway`
|
|
110
|
+
2. Or grant Terminal/ITerm permission to modify network settings in System Preferences
|
|
111
|
+
|
|
112
|
+
## License
|
|
113
|
+
|
|
114
|
+
MIT
|
data/bin/homeaway
ADDED
data/lib/homeaway/cli.rb
ADDED
|
@@ -0,0 +1,140 @@
|
|
|
1
|
+
module Homeaway
|
|
2
|
+
class CLI
|
|
3
|
+
def initialize(args = [])
|
|
4
|
+
@args = args
|
|
5
|
+
@config = Config.new
|
|
6
|
+
@network = Network.new
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
def run
|
|
10
|
+
handle_args
|
|
11
|
+
|
|
12
|
+
@config.setup_wizard if @config.first_run?
|
|
13
|
+
|
|
14
|
+
current_mode = @network.current_mode
|
|
15
|
+
current_ip = @network.current_ip
|
|
16
|
+
|
|
17
|
+
display_current_status(current_mode, current_ip)
|
|
18
|
+
|
|
19
|
+
case current_mode
|
|
20
|
+
when :dhcp
|
|
21
|
+
handle_dhcp_mode
|
|
22
|
+
when :manual
|
|
23
|
+
handle_manual_mode
|
|
24
|
+
else
|
|
25
|
+
puts 'Error: Could not determine current network mode'
|
|
26
|
+
exit 1
|
|
27
|
+
end
|
|
28
|
+
rescue StandardError => e
|
|
29
|
+
puts "Error: #{e.message}"
|
|
30
|
+
exit 1
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
private
|
|
34
|
+
|
|
35
|
+
def handle_args
|
|
36
|
+
case @args[0]
|
|
37
|
+
when '--version', '-v'
|
|
38
|
+
puts "homeaway #{Homeaway::VERSION}"
|
|
39
|
+
exit 0
|
|
40
|
+
when '--help', '-h'
|
|
41
|
+
show_help
|
|
42
|
+
exit 0
|
|
43
|
+
when '--config', '-c'
|
|
44
|
+
@config.setup_wizard
|
|
45
|
+
exit 0
|
|
46
|
+
end
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
def show_help
|
|
50
|
+
puts <<~HELP
|
|
51
|
+
homeaway #{Homeaway::VERSION} - Toggle WiFi between manual and DHCP mode
|
|
52
|
+
|
|
53
|
+
Usage:
|
|
54
|
+
homeaway [options]
|
|
55
|
+
|
|
56
|
+
Options:
|
|
57
|
+
-h, --help Show this help message
|
|
58
|
+
-v, --version Show version
|
|
59
|
+
-c, --config Re-run configuration wizard
|
|
60
|
+
|
|
61
|
+
Description:
|
|
62
|
+
When in DHCP mode, toggles to manual with auto-selected IP.
|
|
63
|
+
When in manual mode, toggles back to DHCP.
|
|
64
|
+
HELP
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
def display_current_status(mode, ip)
|
|
68
|
+
case mode
|
|
69
|
+
when :dhcp
|
|
70
|
+
puts 'Current mode: DHCP'
|
|
71
|
+
puts "Current IP: #{ip}" if ip
|
|
72
|
+
when :manual
|
|
73
|
+
puts 'Current mode: Manual (Static IP)'
|
|
74
|
+
puts "Current IP: #{ip}" if ip
|
|
75
|
+
else
|
|
76
|
+
puts 'Current mode: Unknown'
|
|
77
|
+
end
|
|
78
|
+
puts
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
def handle_dhcp_mode
|
|
82
|
+
print 'Toggle to Manual mode? [Y/n]: '
|
|
83
|
+
answer = gets.chomp.downcase
|
|
84
|
+
|
|
85
|
+
if answer.empty? || answer == 'y' || answer == 'yes'
|
|
86
|
+
switch_to_manual
|
|
87
|
+
else
|
|
88
|
+
puts 'Cancelled.'
|
|
89
|
+
end
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
def handle_manual_mode
|
|
93
|
+
print 'Toggle to DHCP mode? [Y/n]: '
|
|
94
|
+
answer = gets.chomp.downcase
|
|
95
|
+
|
|
96
|
+
if answer.empty? || answer == 'y' || answer == 'yes'
|
|
97
|
+
switch_to_dhcp
|
|
98
|
+
else
|
|
99
|
+
puts 'Cancelled.'
|
|
100
|
+
end
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
def switch_to_manual
|
|
104
|
+
ip = @network.find_available_ip
|
|
105
|
+
subnet = @config['subnet_mask']
|
|
106
|
+
router = @config['router']
|
|
107
|
+
dns = @config['dns_server']
|
|
108
|
+
|
|
109
|
+
puts "\nConfiguring static IP:"
|
|
110
|
+
puts " IP Address: #{ip}"
|
|
111
|
+
puts " Subnet Mask: #{subnet}"
|
|
112
|
+
puts " Router: #{router}"
|
|
113
|
+
puts " DNS Server: #{dns}"
|
|
114
|
+
puts
|
|
115
|
+
|
|
116
|
+
@network.set_manual_mode(ip, subnet, router, dns)
|
|
117
|
+
|
|
118
|
+
puts 'Successfully switched to Manual mode!'
|
|
119
|
+
puts "Your IP is now: #{ip}"
|
|
120
|
+
end
|
|
121
|
+
|
|
122
|
+
def switch_to_dhcp
|
|
123
|
+
clear_dns = @config['clear_dns_on_dhcp']
|
|
124
|
+
|
|
125
|
+
puts "\nSwitching to DHCP mode..."
|
|
126
|
+
|
|
127
|
+
@network.set_dhcp_mode(clear_dns: clear_dns)
|
|
128
|
+
|
|
129
|
+
puts 'Successfully switched to DHCP mode!'
|
|
130
|
+
|
|
131
|
+
# Give the system a moment to get an IP
|
|
132
|
+
sleep 1
|
|
133
|
+
|
|
134
|
+
new_ip = @network.current_ip
|
|
135
|
+
return unless new_ip
|
|
136
|
+
|
|
137
|
+
puts "Your new IP is: #{new_ip}"
|
|
138
|
+
end
|
|
139
|
+
end
|
|
140
|
+
end
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
require 'yaml'
|
|
2
|
+
require 'fileutils'
|
|
3
|
+
|
|
4
|
+
module Homeaway
|
|
5
|
+
class Config
|
|
6
|
+
CONFIG_DIR = File.expand_path('~/.config/homeaway')
|
|
7
|
+
CONFIG_FILE = File.join(CONFIG_DIR, 'config.yml')
|
|
8
|
+
|
|
9
|
+
DEFAULTS = {
|
|
10
|
+
'router' => '192.168.1.1',
|
|
11
|
+
'clear_dns_on_dhcp' => true,
|
|
12
|
+
'dns_server' => '8.8.8.8',
|
|
13
|
+
'subnet_mask' => '255.255.255.0'
|
|
14
|
+
}.freeze
|
|
15
|
+
|
|
16
|
+
attr_reader :data
|
|
17
|
+
|
|
18
|
+
def initialize
|
|
19
|
+
@data = load_config
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
def first_run?
|
|
23
|
+
!File.exist?(CONFIG_FILE)
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
def setup_wizard
|
|
27
|
+
puts "\nWelcome to homeaway! Let's configure your preferences.\n\n"
|
|
28
|
+
|
|
29
|
+
print "Default router address [#{DEFAULTS['router']}]: "
|
|
30
|
+
router_input = gets.chomp
|
|
31
|
+
@data['router'] = router_input.empty? ? DEFAULTS['router'] : router_input
|
|
32
|
+
|
|
33
|
+
print 'Clear DNS records when toggling to DHCP? [Y/n]: '
|
|
34
|
+
clear_dns_input = gets.chomp.downcase
|
|
35
|
+
@data['clear_dns_on_dhcp'] = clear_dns_input.empty? || clear_dns_input == 'y' || clear_dns_input == 'yes'
|
|
36
|
+
|
|
37
|
+
print "Default DNS server [#{DEFAULTS['dns_server']}]: "
|
|
38
|
+
dns_input = gets.chomp
|
|
39
|
+
@data['dns_server'] = dns_input.empty? ? DEFAULTS['dns_server'] : dns_input
|
|
40
|
+
|
|
41
|
+
@data['subnet_mask'] = DEFAULTS['subnet_mask']
|
|
42
|
+
|
|
43
|
+
save!
|
|
44
|
+
|
|
45
|
+
puts "\nConfiguration saved to #{CONFIG_FILE}\n\n"
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
def save!
|
|
49
|
+
FileUtils.mkdir_p(CONFIG_DIR)
|
|
50
|
+
File.write(CONFIG_FILE, @data.to_yaml)
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
def [](key)
|
|
54
|
+
@data[key]
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
private
|
|
58
|
+
|
|
59
|
+
def load_config
|
|
60
|
+
if File.exist?(CONFIG_FILE)
|
|
61
|
+
YAML.load_file(CONFIG_FILE) || {}
|
|
62
|
+
else
|
|
63
|
+
{}
|
|
64
|
+
end
|
|
65
|
+
end
|
|
66
|
+
end
|
|
67
|
+
end
|
|
@@ -0,0 +1,149 @@
|
|
|
1
|
+
require 'open3'
|
|
2
|
+
require 'timeout'
|
|
3
|
+
require 'ipaddr'
|
|
4
|
+
|
|
5
|
+
module Homeaway
|
|
6
|
+
class Network
|
|
7
|
+
SUBNET_PREFIX = '192.168.1'.freeze
|
|
8
|
+
IP_RANGE = (2..254).freeze
|
|
9
|
+
TIMEOUT_SECONDS = 1
|
|
10
|
+
|
|
11
|
+
def self.detect_wifi_interface
|
|
12
|
+
# Get the WiFi service name using networksetup
|
|
13
|
+
output, status = Open3.capture2('networksetup', '-listallhardwareports')
|
|
14
|
+
|
|
15
|
+
raise 'Failed to list hardware ports' unless status.success?
|
|
16
|
+
|
|
17
|
+
# Parse the output to find WiFi service name (not device name)
|
|
18
|
+
# networksetup commands require the service name (e.g., "Wi-Fi"), not device (e.g., "en0")
|
|
19
|
+
lines = output.split("\n")
|
|
20
|
+
lines.each do |line|
|
|
21
|
+
next unless line =~ /Hardware Port:\s*(.+)/i
|
|
22
|
+
|
|
23
|
+
service_name = ::Regexp.last_match(1).strip
|
|
24
|
+
# Check if this is a WiFi interface by name
|
|
25
|
+
return service_name if service_name =~ /Wi-Fi|AirPort|Wireless/i
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
raise 'Could not find Wi-Fi interface'
|
|
29
|
+
end
|
|
30
|
+
|
|
31
|
+
def initialize
|
|
32
|
+
@device = self.class.detect_wifi_interface
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
def current_mode
|
|
36
|
+
output, status = Open3.capture2('networksetup', '-getinfo', @device)
|
|
37
|
+
|
|
38
|
+
raise "Failed to get network info for '#{@device}'" unless status.success?
|
|
39
|
+
|
|
40
|
+
if output.include?('DHCP Configuration')
|
|
41
|
+
:dhcp
|
|
42
|
+
elsif output.include?('Manual Configuration')
|
|
43
|
+
:manual
|
|
44
|
+
else
|
|
45
|
+
:unknown
|
|
46
|
+
end
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
def current_ip
|
|
50
|
+
output, status = Open3.capture2('networksetup', '-getinfo', @device)
|
|
51
|
+
|
|
52
|
+
return nil unless status.success?
|
|
53
|
+
|
|
54
|
+
# Extract IP address from output
|
|
55
|
+
return unless output =~ /IP address:\s*(\d+\.\d+\.\d+\.\d+)/
|
|
56
|
+
|
|
57
|
+
::Regexp.last_match(1)
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
def find_available_ip
|
|
61
|
+
puts "Scanning for available IP in #{SUBNET_PREFIX}.x range..."
|
|
62
|
+
|
|
63
|
+
available_ip = nil
|
|
64
|
+
|
|
65
|
+
IP_RANGE.each do |last_octet|
|
|
66
|
+
ip = "#{SUBNET_PREFIX}.#{last_octet}"
|
|
67
|
+
|
|
68
|
+
# Check if IP is the router
|
|
69
|
+
next if ip == router_ip
|
|
70
|
+
|
|
71
|
+
# Check if IP is already in use
|
|
72
|
+
unless ip_in_use?(ip)
|
|
73
|
+
available_ip = ip
|
|
74
|
+
break
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
print '.'
|
|
78
|
+
$stdout.flush
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
puts
|
|
82
|
+
|
|
83
|
+
available_ip || raise("No available IP found in #{SUBNET_PREFIX}.2-254")
|
|
84
|
+
end
|
|
85
|
+
|
|
86
|
+
def set_manual_mode(ip, subnet_mask, router, dns)
|
|
87
|
+
# Set manual IP configuration
|
|
88
|
+
output, status = Open3.capture2(
|
|
89
|
+
'networksetup', '-setmanual', @device, ip, subnet_mask, router
|
|
90
|
+
)
|
|
91
|
+
|
|
92
|
+
raise "Failed to set manual configuration: #{output}" unless status.success?
|
|
93
|
+
|
|
94
|
+
# Set DNS
|
|
95
|
+
output, status = Open3.capture2(
|
|
96
|
+
'networksetup', '-setdnsservers', @device, dns
|
|
97
|
+
)
|
|
98
|
+
|
|
99
|
+
raise "Failed to set DNS: #{output}" unless status.success?
|
|
100
|
+
|
|
101
|
+
true
|
|
102
|
+
end
|
|
103
|
+
|
|
104
|
+
def set_dhcp_mode(clear_dns: true)
|
|
105
|
+
# Switch to DHCP
|
|
106
|
+
output, status = Open3.capture2('networksetup', '-setdhcp', @device)
|
|
107
|
+
|
|
108
|
+
raise "Failed to set DHCP: #{output}" unless status.success?
|
|
109
|
+
|
|
110
|
+
# Clear DNS if requested
|
|
111
|
+
if clear_dns
|
|
112
|
+
puts 'Clearing DNS settings...'
|
|
113
|
+
_, status = Open3.capture2(
|
|
114
|
+
'networksetup', '-setdnsservers', @device, 'empty'
|
|
115
|
+
)
|
|
116
|
+
|
|
117
|
+
puts 'Warning: Failed to clear DNS settings' unless status.success?
|
|
118
|
+
end
|
|
119
|
+
|
|
120
|
+
true
|
|
121
|
+
end
|
|
122
|
+
|
|
123
|
+
def device_name
|
|
124
|
+
@device
|
|
125
|
+
end
|
|
126
|
+
|
|
127
|
+
private
|
|
128
|
+
|
|
129
|
+
def router_ip
|
|
130
|
+
@router_ip ||= Config.new['router']
|
|
131
|
+
end
|
|
132
|
+
|
|
133
|
+
def ip_in_use?(ip)
|
|
134
|
+
# Use ping with timeout to check if IP is in use
|
|
135
|
+
# -c 1: send 1 packet
|
|
136
|
+
# -W 500: wait 500ms for response
|
|
137
|
+
# -t 1: TTL of 1 (macOS specific)
|
|
138
|
+
|
|
139
|
+
cmd = ['ping', '-c', '1', '-W', '500', '-t', '1', ip]
|
|
140
|
+
_output, status = Open3.capture2(*cmd)
|
|
141
|
+
|
|
142
|
+
# If ping succeeds (status 0), IP is in use
|
|
143
|
+
status.success?
|
|
144
|
+
rescue StandardError
|
|
145
|
+
# If ping fails for any reason, assume IP is not in use
|
|
146
|
+
false
|
|
147
|
+
end
|
|
148
|
+
end
|
|
149
|
+
end
|
data/lib/homeaway.rb
ADDED
metadata
ADDED
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
|
2
|
+
name: homeaway
|
|
3
|
+
version: !ruby/object:Gem::Version
|
|
4
|
+
version: 1.0.0
|
|
5
|
+
platform: ruby
|
|
6
|
+
authors:
|
|
7
|
+
- Good Bran
|
|
8
|
+
bindir: bin
|
|
9
|
+
cert_chain: []
|
|
10
|
+
date: 1980-01-02 00:00:00.000000000 Z
|
|
11
|
+
dependencies:
|
|
12
|
+
- !ruby/object:Gem::Dependency
|
|
13
|
+
name: bundler
|
|
14
|
+
requirement: !ruby/object:Gem::Requirement
|
|
15
|
+
requirements:
|
|
16
|
+
- - "~>"
|
|
17
|
+
- !ruby/object:Gem::Version
|
|
18
|
+
version: '2.0'
|
|
19
|
+
type: :development
|
|
20
|
+
prerelease: false
|
|
21
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
22
|
+
requirements:
|
|
23
|
+
- - "~>"
|
|
24
|
+
- !ruby/object:Gem::Version
|
|
25
|
+
version: '2.0'
|
|
26
|
+
description: Homeaway allows you to quickly switch your macOS WiFi between manual
|
|
27
|
+
static IP configuration and DHCP mode, with automatic IP scanning and DNS management.
|
|
28
|
+
email:
|
|
29
|
+
- bran.liang@icloud.com
|
|
30
|
+
executables:
|
|
31
|
+
- homeaway
|
|
32
|
+
extensions: []
|
|
33
|
+
extra_rdoc_files: []
|
|
34
|
+
files:
|
|
35
|
+
- LICENSE
|
|
36
|
+
- README.md
|
|
37
|
+
- bin/homeaway
|
|
38
|
+
- lib/homeaway.rb
|
|
39
|
+
- lib/homeaway/cli.rb
|
|
40
|
+
- lib/homeaway/config.rb
|
|
41
|
+
- lib/homeaway/network.rb
|
|
42
|
+
homepage: https://github.com/GoodBran/homeaway
|
|
43
|
+
licenses:
|
|
44
|
+
- MIT
|
|
45
|
+
metadata: {}
|
|
46
|
+
rdoc_options: []
|
|
47
|
+
require_paths:
|
|
48
|
+
- lib
|
|
49
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
|
50
|
+
requirements:
|
|
51
|
+
- - ">="
|
|
52
|
+
- !ruby/object:Gem::Version
|
|
53
|
+
version: 2.6.0
|
|
54
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
|
55
|
+
requirements:
|
|
56
|
+
- - ">="
|
|
57
|
+
- !ruby/object:Gem::Version
|
|
58
|
+
version: '0'
|
|
59
|
+
requirements: []
|
|
60
|
+
rubygems_version: 4.0.3
|
|
61
|
+
specification_version: 4
|
|
62
|
+
summary: A CLI tool to toggle WiFi between manual and DHCP mode
|
|
63
|
+
test_files: []
|