首页 > 解决方案 > postgres 在 2 db 列之间找到 IP 地址

问题描述

我有一个 IP 地址表。该表有两列名称starting_ipending_ip。该表如下所示: 在此处输入图像描述

现在,假设我有一个随机 IP 地址。从那个随机的 IP 地址,我想知道city_name. 这意味着我需要知道随机 IP 地址位于哪个范围之间,基于starting_ipending_ip。然后找到 1 条记录并获取city_name.

我写了一个这样的查询:

class IpToCity < ActiveRecord::Base
  establish_connection :"ip_database_#{Rails.env}"
  
  scope :search_within_ip_range, -> (ip_address) do
    self.connection.select_all("
      with candidate as (
        select * from ip_cities
        where ending_ip >= '#{ip_address}'::inet
        order by ending_ip asc
        limit 1
      )
      select * from candidate
      where starting_ip <= '#{ip_address}'::inet;
    ")
  end
end

这是一个范围,我通过随机 IP 并获得一条记录。问题是,查询工作正常,但速度很慢。任何建议,如何使它更快?

提前致谢!

标签: ruby-on-railsruby-on-rails-4activerecordip-addresspostgresql-9.3

解决方案


所有行都符合这种格式吗?

starting_ip  ending_ip
x.y.z.0      x.y.z.255

如果是这样,那么您可以为“前缀”添加另一列:xyz

然后将目标的前 3 个八位字节与前缀列进行匹配。

更新数据库时,将跨越多个前缀的行分成多行。

最大行数为 16.8M (256 3 ),它很小,仅比您当前的 5M 略大。


推荐阅读