6

我的 Rails 项目有问题。在以前的项目(不是 Rails)中,我只是在 PostgreSQL 中使用“inet”类型来存储带有子网的 IP 地址,如下所示:

 192.168.1.0/30 
 192.168.1.1/30
 192.168.1.2/30
 192.168.1.3/30

这是将 IP 和子网存储在一个字段中的好方法。现在我在 Rails (4.0.1) 和 Ruby (2.0.0 p247) 中使用 inet 类型,但是当我阅读和尝试时,Rails 将其转换为 IPAddr 对象。但是这个 IPAddr 对象正在破坏我的格式。它将上面的四个示例转换为以下示例:

 192.168.1.0/30

有没有办法阻止 Rails 这样做,或者有没有办法用字符串代替它?或者也许是另一个宝石?

当我尝试存储某些内容时,甚至当我尝试从数据库中读取现有值时,就会出现问题。

只是为了更细化:

 IPAddr.new("192.168.1.2/255.255.255.252") 

创建数据库条目:

 192.168.1.0/24
4

1 回答 1

3

如果我没记错的话,192.168.1.0/30在技术上是正确的。

这里有几件事可能会有所帮助:

  • 除了 IPAddr 之外,使用 IPv4 和 IPv6 的一个非常好的 gem 是IPAddress。如果 Active Record 已经将值传递给 IPAddr 并没有太大帮助,并且它已经更改了值,因此您需要告诉 Active Record 使用 IPAddress。
  • 如果您打算使用 PostgreSQL 通过其内置的 IP 函数来处理子网划分需求,那么将您的地址存储为 PostgreSQL“inet”类型就可以了。如您所见,如果您只想存储 IP 地址并检索它,这是一个坏主意。Active Record 尝试尊重字段类型,并将其映射到最近的 Ruby 类,即 IPAddr。相反,我总是将我的 IP 存储为字符串,以便以我想要的形式快速检索,以及作为适当大小的整数,因此我可以以二进制形式进行所有子网划分操作和匹配。

    如果在查询中告诉 PostgreSQL 在将值返回给 Active Record 之前将其转换为字符串,这可能会有所帮助。此时,您可以在解析后使用 IPAddress 处理该值。如何告诉 Active Record 告诉 PostgreSQL 这样做是一个不同的问题。

于 2014-03-31T22:39:27.843 回答