Class: Philiprehberger::IpAddr::Range
- Inherits:
-
Object
- Object
- Philiprehberger::IpAddr::Range
- Includes:
- Enumerable
- Defined in:
- lib/philiprehberger/ip_addr.rb
Overview
CIDR range wrapper
Instance Method Summary collapse
-
#broadcast ⇒ Address
Broadcast address (last address in the block).
-
#each {|Address| ... } ⇒ Enumerator
Iterate over all addresses in the range.
-
#include?(ip) ⇒ Boolean
True if the range includes the given IP.
-
#initialize(cidr) ⇒ Range
constructor
A new instance of Range.
-
#ipv4? ⇒ Boolean
True if this is an IPv4 range.
-
#ipv6? ⇒ Boolean
True if this is an IPv6 range.
-
#netmask ⇒ String
Subnet mask.
-
#network ⇒ Address
Network address (first address in the block).
-
#overlap?(other) ⇒ Boolean
True if the two ranges share any addresses.
-
#prefix ⇒ Integer
CIDR prefix length.
-
#size ⇒ Integer
Number of addresses in the range.
-
#subnets(prefix:) {|Range| ... } ⇒ Enumerator<Range>
Split the range into equal-size child subnets at the given prefix length.
-
#to_a ⇒ Array<Address>
All addresses in the range.
-
#to_s ⇒ String
String representation.
Constructor Details
Instance Method Details
#broadcast ⇒ Address
Returns broadcast address (last address in the block).
152 153 154 |
# File 'lib/philiprehberger/ip_addr.rb', line 152 def broadcast Address.new(@network.to_range.last.to_s) end |
#each {|Address| ... } ⇒ Enumerator
Iterate over all addresses in the range
191 192 193 194 195 196 197 198 199 200 201 |
# File 'lib/philiprehberger/ip_addr.rb', line 191 def each(&block) return enum_for(:each) unless block start_int = @network.to_range.first.to_i end_int = @network.to_range.last.to_i (start_int..end_int).each do |int| addr = @network.ipv4? ? int_to_v4(int) : int_to_v6(int) block.call(Address.new(addr)) end end |
#include?(ip) ⇒ Boolean
Returns true if the range includes the given IP.
181 182 183 184 185 186 |
# File 'lib/philiprehberger/ip_addr.rb', line 181 def include?(ip) addr = ip.is_a?(Address) ? ::IPAddr.new(ip.to_s) : ::IPAddr.new(ip.to_s) @network.include?(addr) rescue ::IPAddr::InvalidAddressError false end |
#ipv4? ⇒ Boolean
Returns true if this is an IPv4 range.
209 210 211 |
# File 'lib/philiprehberger/ip_addr.rb', line 209 def ipv4? @network.ipv4? end |
#ipv6? ⇒ Boolean
Returns true if this is an IPv6 range.
214 215 216 |
# File 'lib/philiprehberger/ip_addr.rb', line 214 def ipv6? @network.ipv6? end |
#netmask ⇒ String
Returns subnet mask.
162 163 164 165 166 167 168 169 |
# File 'lib/philiprehberger/ip_addr.rb', line 162 def netmask if @network.ipv4? mask_int = (0xFFFFFFFF << (32 - prefix)) & 0xFFFFFFFF [24, 16, 8, 0].map { |shift| (mask_int >> shift) & 0xFF }.join('.') else "/#{prefix}" end end |
#network ⇒ Address
Returns network address (first address in the block).
147 148 149 |
# File 'lib/philiprehberger/ip_addr.rb', line 147 def network Address.new(@network.to_range.first.to_s) end |
#overlap?(other) ⇒ Boolean
Returns true if the two ranges share any addresses.
173 174 175 176 177 |
# File 'lib/philiprehberger/ip_addr.rb', line 173 def overlap?(other) raise Error, 'Argument must be a Range' unless other.is_a?(Range) @network.include?(other.network.to_s) || other.include?(network.to_s) end |
#prefix ⇒ Integer
Returns CIDR prefix length.
157 158 159 |
# File 'lib/philiprehberger/ip_addr.rb', line 157 def prefix @network.prefix end |
#size ⇒ Integer
Returns number of addresses in the range.
138 139 140 141 142 143 144 |
# File 'lib/philiprehberger/ip_addr.rb', line 138 def size if @network.ipv4? 2**(32 - prefix) else 2**(128 - prefix) end end |
#subnets(prefix:) {|Range| ... } ⇒ Enumerator<Range>
Split the range into equal-size child subnets at the given prefix length
223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 |
# File 'lib/philiprehberger/ip_addr.rb', line 223 def subnets(prefix:) max_prefix = ipv6? ? 128 : 32 unless prefix.is_a?(Integer) && prefix > @network.prefix && prefix <= max_prefix raise ArgumentError, "prefix must be an Integer greater than #{@network.prefix} and <= #{max_prefix}, got #{prefix.inspect}" end return enum_for(:subnets, prefix: prefix) unless block_given? step = 2**(max_prefix - prefix) start_int = @network.to_range.first.to_i end_int = @network.to_range.last.to_i int = start_int while int <= end_int addr = ipv4? ? int_to_v4(int) : int_to_v6(int) yield Range.new("#{addr}/#{prefix}") int += step end end |
#to_a ⇒ Array<Address>
Returns all addresses in the range.
204 205 206 |
# File 'lib/philiprehberger/ip_addr.rb', line 204 def to_a each.to_a end |
#to_s ⇒ String
Returns string representation.
244 245 246 |
# File 'lib/philiprehberger/ip_addr.rb', line 244 def to_s @cidr end |