Postgress | SQL | Get a row only if the subnet is part of a given ip list

淺唱寂寞╮ 提交于 2020-08-10 22:34:03

问题


I have a table with text column that holds ip with subnet

| ip
-------------
| 1.1.1.1/30

when you convert 1.1.1.1/30 to list of ip you get:

1.1.1.0
1.1.1.1
1.1.1.2
1.1.1.3

I want to run a sql on this table and give a list of ips somehow as part of "where" or anything else, and get this row only if the list of the ips that I give contain the ips of the range in the row.

meaning,

where ('1.1.1.0','1.1.1.1) 

--> I will not get the row

but:

where ('1.1.1.0','1.1.1.1,1.1.1.2,1.1.1.3) 

--> I will get the row

but:

where ('1.1.1.0','1.1.1.1,1.1.1.2,1.1.1.3,1.1.1.4,1.1.1.5) 

--> I will get the row

Is there anyway to do that ?


回答1:


You have to expand out the inet into all its host values and then use containment to accomplish this:

with blowout as (
  select t.ip, array_agg(host(network(t.ip::inet) + gs.n)) as all_ips
    from t
   cross join lateral 
         generate_series(0, broadcast(t.ip::inet) - network(t.ip::inet)) as gs(n)
   group by t.ip;
)
select *
  from blowout
 where all_ips <@ array['1.1.1.0', '1.1.1.1', '1.1.1.2', 
                        '1.1.1.3', '1.1.1.4', '1.1.1.5']::text[] 
;

Since you are not using any special inet functions in the comparison, it is best to do the comparisons using text.



来源:https://stackoverflow.com/questions/63270241/postgress-sql-get-a-row-only-if-the-subnet-is-part-of-a-given-ip-list

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!