On Tue, Aug 3, 2010 at 3:05 PM, Yeb Havinga wrote:

Yeb Havinga wrote:

confusing, since that relation might not be commutative. C.x 'inherits

properties from' A.x, or C.x 'is defined by' A.x are perhaps better names,

that reflect that the converse might not hold. OTOH, what does C.x 'inherits

(all) properties from' A.x mean? If it means that for all properties P,

P(C.x) iff P(A.x), then C.x = A.x commutatively and by similar reasoning

A.x = B.x.

first thing I found was this recent thread about the exactly the same

problem http://archives.postgresql.org/pgsql-hackers/2010-01/msg03117.php

Sorry for the double post, however the previous discussion postponed work to

.. now, so maybe there is some value in first trying to specify exactly what

'inherits' means, and derive consequences for code behaviour from that.

Yeb Havinga wrote:

The underlying cause is the failure of the code to recognize that if

relation C inherits from both A and B, where A and B both have column x,

that A.x 'is the same as' B.x, where the 'is the same as' relation is the

same that holds for (A.x, C.x) and (B.x, C.x), which the code does a lot of

trouble for to recognize. This means that if some definition is altered on

A.x, only C.x is updated and B.x not touched. IMO this is wrong and either a

multiple inheritance structure like this should be prohibited, since the

user did not explicitly declare that A.x and B.x 'are the same' (by e.g.

defining a relation D.x and have A and B inherit from that), or the code

should update parents of relations when the childs are updated.

Thinking about this a bit more, the name 'is the same as' is a bitrelation C inherits from both A and B, where A and B both have column x,

that A.x 'is the same as' B.x, where the 'is the same as' relation is the

same that holds for (A.x, C.x) and (B.x, C.x), which the code does a lot of

trouble for to recognize. This means that if some definition is altered on

A.x, only C.x is updated and B.x not touched. IMO this is wrong and either a

multiple inheritance structure like this should be prohibited, since the

user did not explicitly declare that A.x and B.x 'are the same' (by e.g.

defining a relation D.x and have A and B inherit from that), or the code

should update parents of relations when the childs are updated.

confusing, since that relation might not be commutative. C.x 'inherits

properties from' A.x, or C.x 'is defined by' A.x are perhaps better names,

that reflect that the converse might not hold. OTOH, what does C.x 'inherits

(all) properties from' A.x mean? If it means that for all properties P,

P(C.x) iff P(A.x), then C.x = A.x commutatively and by similar reasoning

A.x = B.x.

ALTER TABLE top1 RENAME COLUMN a_table_column TO another_table_column;

When looking for previous discussions that was referred to upthread, thefirst thing I found was this recent thread about the exactly the same

problem http://archives.postgresql.org/pgsql-hackers/2010-01/msg03117.php

Sorry for the double post, however the previous discussion postponed work to

.. now, so maybe there is some value in first trying to specify exactly what

'inherits' means, and derive consequences for code behaviour from that.

Metuchen. I wouldn't get too bogged down in formal logic; it seems

there are a couple of distinct cases here:

1. If you're changing properties of a column, you need to verify for

each relation in the inheritance tree that the "expected attinhcount"

and the actual attinhcount match. If, for any relation in the

inheritance tree rooted at the named table, they don't, then they are

doubly inherited there, from some other table outside the hierarchy

rooted at the named table, and the operation must fail. We'd need

similar logic for constraints, if we had support for renaming or

otherwise modifying them, but right now we don't.

2. If you're adding a column, you need to propagate the new column to

relations that don't have it yet, but if you find one that already has

it than you adjust attinhcount and don't recurse to its chidlren.

3. If you're dropping a column, you essentially decrement the

attinhcount of all your children; then you recurse into any that reach

attincount = 0 and not attislocal and drop the column there as well.