Module:IP: Difference between revisions

From the Croc Wiki, the Croc encyclopedia
Jump to navigationJump to search
1,023 bytes removed ,  7 years ago
use __index plus a unique key to access any IPAddress object's internal data
(implement Subnet (very rushed; will check and refactor!))
(use __index plus a unique key to access any IPAddress object's internal data)
Line 10:
local V4 = 'IPv4'
local V6 = 'IPv6'
 
--------------------------------------------------------------------------------
-- TODO Remove items from these notes when satisfied they are ok.
 
-- IPAddress does not need mt:__le(obj) as Lua evaluates (a <= b) as (not (b < a))
-- and that is correct for IP addresses.
 
-- IPAddress obj:getIP() needs thought.
-- At first, it looked like the representation of the IP (the numbers).
-- But perhaps it is intended to be a string as in the testcases.
-- Is it really just a copy of the input string?
-- What if the input is " 1.2.3.4 " (with leading and trailing spaces which
-- the code ignores)?
-- Also, tostring(ip) for an IPv6 address will return the normalized string
-- which might be different from the input. Example:
-- input "1:02:003:0004:0:0:0:0" is "1:2:3:4::" after normalization.
 
-- Should obj:getIPParts() be removed?
-- Instead, move the metamethods into IPAddress.new(ip) so they can
-- access the data upvalue?
-- Hmmm, that would work only for self, not for the other object.
-- Is there a way of keeping data private but accessing it from metamethods?
-- If getIPParts is kept, perhaps it should be changed to "getParts" or similar
-- as "IP" is redundant in an IPAddress class.
 
------------------------------------------------------------------------
Line 263 ⟶ 239:
 
do
local dataKey = {} -- A unique key to access objects' internal data.
local uniqueId = {}
 
-- Initialize metatable
-- Static private methods
local mt = {}
local function ipEquals(ip1, ip2)
local lhs = ip1[dataKey].parts
local rhs = ip2[dataKey].parts
if lhs.n == rhs.n then
for i = 1, lhs.n do
if lhs[i] ~= rhs[i] then
return false
end
end
return true
end
return false
end
 
local function ipLessThan(ip1, ip2)
local lhs = ip1[dataKey].parts
local rhs = ip2[dataKey].parts
if lhs.n == rhs.n then
for i = 1, lhs.n do
if lhs[i] ~= rhs[i] then
return lhs[i] < rhs[i]
end
end
return false
end
return lhs.n < rhs.n
end
 
-- Constructor
function IPAddress.new(ip, parts)
checkType('IPAddress.new', 1, ip, 'string')
 
-- Set up structure
local obj = setmetatable({}, mt)
local data = {}
 
-- Set initial values
if not (ipv4Address(data, ip) or ipv6Address(data, ip)) then
error('invalid IP', 2)
end
data.version = data.parts.n == 2 and V4 or V6
 
-- Public methods
Line 322 ⟶ 332:
end
 
-- Set initial valuesMetamethods
return setmetatable(obj, {
if ip == uniqueId then
data.parts__eq = partsipEquals,
__lt = ipLessThan,
else
__index = function (self, key)
checkType('IPAddress.new', 1, ip, 'string')
if notkey (ipv4Address(data,== ip) or ipv6Address(data, ip))dataKey then
return data
error('invalid IP', 2)
end
end
data.version = data.parts.n == 2 and V4 or V6
 
return obj
end
 
-- Metamethods
function mt:__concat(obj)
return tostring(self) .. tostring(obj)
end
 
function mt:__eq(obj)
local lhs, rhs = self:getIPParts(), obj:getIPParts()
if lhs.n == rhs.n then
for i = 1, lhs.n do
if lhs[i] ~= rhs[i] then
return false
end
end,
__concat = function (self, obj)
return true
return tostring(self) .. tostring(obj)
end
end,
return false
__tostring = function (self)
end
return ipString(self:getIPParts())
 
end,
function mt:__lt(obj)
})
local lhs, rhs = self:getIPParts(), obj:getIPParts()
if lhs.n == rhs.n then
for i = 1, lhs.n do
if lhs[i] ~= rhs[i] then
return lhs[i] < rhs[i]
end
end
return false
end
return lhs.n < rhs.n
end
 
function mt:__tostring()
return ipString(self:getIPParts())
end
end
Cookies help us deliver our services. By using our services, you agree to our use of cookies.

Navigation menu