Re: Repair plan for inet and cidr types - Mailing list pgsql-hackers
From | Peter Eisentraut |
---|---|
Subject | Re: Repair plan for inet and cidr types |
Date | |
Msg-id | Pine.LNX.4.21.0007070156410.4191-100000@localhost.localdomain Whole thread Raw |
In response to | Re: Repair plan for inet and cidr types (darcy@druid.net (D'Arcy J.M. Cain)) |
List | pgsql-hackers |
D'Arcy J.M. Cain writes: > > Automatic casts should not lose information. How would you feel if floats > > were automatically rounded when you store them into int fields? I think > > this is an important principle in any type system. > > If it was defined well I would have no problem with it. That is certainly not how type systems operate anywhere. > I guess what I was really getting at was this. > > host OP cidr > > where inet would cast to host on one side and cidr on the other. What > we have now is > > cidr OP cidr > > with both sides casting to cidr. Of course there is no such thing as a host > type so I don't know how we would cast such a thing. I think that while the implicit casting could sometimes be convenient, it's also a source of confusion. Consider the statement select '10.0.0.3'::cidr < '10.0.0.2'::inet; => f This cannot possibly make sense on closer inspection. Firstly, it's semantic nonsense, you cannot order a network and a host. Secondly, it's also wrong. According to the documentation, the '10.0.0.3'::cidr should be converted to '10/8' internally. Then one of two things could have happened here: 1) cidr was implicitly converted to inet and '10.0.0.3' is taken to be a host, which is completely wrong. Or 2) inet was converted to cidr. But then we're looking at '10/8' < '10.0.0.2/32', which should be true. See also select '10.0.0.2'::cidr = '10.0.0.2'::inet; => t which is wrong for similar reasons. Then let's look at the << family of operators. select '10.0.0.2'::cidr >> '10.0.0.2'::inet; => f Again, there are two ways this could currently be resolved: '10/8'::cidr >> '10.0.0.2/32'::cidr which does return true or'10.0.0.2'::inet >> '10.0.0.2'::inet which doesn't make any sense. On closer inspection, the inet << cidr case is completely misbehaving: select '10.0.0.5/8'::inet << '10.0.0.0/16'::cidr; => f select '10.0.0.5/24'::inet << '10.0.0.0/16'::cidr; => t This is not what I'd expect. Concretely, the casesinet << cidrcidr << cidr are not the same: '10.0.0.5/8'::inet << '10.0.0.0/16'::cidr should be true '10.0.0.5/8'::cidr << '10.0.0.0/16'::cidr should be false, if you allow the left-side value in at all, which I wouldn't. What this tells me is that the cast from inet to cidr is not well-defined in the mathematical sense, and therefore no implicit casting should be allowed. So the bottom line here is that these two types are, while from a related domain, different, and the user should be the one that controls when and how they are mixed together. -- Peter Eisentraut Sernanders väg 10:115 peter_e@gmx.net 75262 Uppsala http://yi.org/peter-e/ Sweden
pgsql-hackers by date: