Ruby IPAddr:查找地址掩码

时间:2017-01-12 03:46:58

标签: ruby ip-address

我有一个应用程序,我处理大量IP地址(分析Checkpoint防火墙规则集)。有一次,我想检查一个特定的地址对象是/ 32还是“网络”。

目前我这样做:

next unless ip.inspect.match(/\/255\.255\.255\.255/)

它有效,但看起来效率有点但我看不到任何从地址对象中提取掩码的方法。

3 个答案:

答案 0 :(得分:5)

Ruby核心库的某些部分有时只是勾勒出来的,而IPAddr似乎是其中之一,不幸的是,它有点不完整。

不用担心。你可以用一个简单的猴子补丁解决这个问题:

class IPAddr
  def cidr_mask
    case (@family)
    when Socket::AF_INET
      32 - Math.log2((1<<32) - @mask_addr).to_i
    when Socket::AF_INET6
      128 - Math.log2((1<<128) - @mask_addr).to_i
    else
      raise AddressFamilyError, "unsupported address family"
    end
  end
end

应处理IPv4和IPv6地址:

IPAddr.new('151.101.65.69').cidr_mask
# => 32

IPAddr.new('151.101.65.69/26').cidr_mask
# => 26

IPAddr.new('151.101.65.69/255.255.255.0').cidr_mask
# => 24

IPAddr.new('2607:f8b0:4006:800::200e').cidr_mask
# => 128

IPAddr.new('2607:f8b0:4006:800::200e/100').cidr_mask
# => 100

这不一定是最好的解决方案,但它确实有效。

答案 1 :(得分:0)

我知道这是一个已有3年历史的问题,但这是我在Google上搜索到的第一个结果,因此我想提供一个新答案。

我今天在控制台上玩耍,发现prefix对象上的IPAddr方法返回cidr mask作为整数。

例如,

ip = IPAddr.new("192.168.1.0/24")
ip.prefix 
  # => 24

结果还表明,强制类型为您提供了地址和掩码的整数表示形式,因此您可以对to_ito_jsonas_jsoninstance_values

网络地址示例:

ip.to_i 
  # => 3232235776

ip.to_i.to_s(2) 
  # => "11000000101010000000000100000000"

然后加上一个网络掩码:

ip.as_json 
  # => {"family"=>2, "addr"=>3232235776, "mask_addr"=>4294967040}

ip.as_json["mask_addr"].to_s(2) 
  # => 11111111111111111111111100000000

ip.as_json["mask_addr"].to_s(2).count("1")
  # => 24

答案 2 :(得分:-3)

对于您筹集的特定情况,您可以这样做:

 my $sql2 = "SELECT CODE_ID,NAME_CODE,SUM(INR_COL + OUT_COL) AS \"TOTAL SUM\" FROM nwsa WHERE trunc(REPORT_DATE) = to_date('?','dd-mm-yyyy')AND CODE_ID IN (?,?,?,?,?,?,?,?,?,?,?)GROUP BY CODE_ID,NAME_CODE"; 
     $sth ->prepare($sql2);
     my $t= "06-01-2017";

     $sth->execute($t,'A12A','A12B','A12C','A12D','A12E','A12EB','A12F','A12G','A12I','A12O','A12U');

也许这种简单的比较比使用正则表达式测试字符串更有效。