This patch does what it says on the label: the descriptor still
contains a valid SQL query, but with all table names rewritten to use
numeric table references. These are hidden initially, until
the referenced tables gets a new schema.
For example:
```
CREATE TABLE kv(k INT PRIMARY KEY, v INT);
CREATE VIEW vx AS SELECT v AS x FROM kv;
SHOW CREATE VIEW vx;
+------+-----------------------------------------+
| View | CreateView |
+------+-----------------------------------------+
| vx | CREATE VIEW vx AS SELECT v AS x FROM kv |
+------+-----------------------------------------+
(1 row)
ALTER TABLE kv ADD COLUMN d INT;
SHOW CREATE VIEW vx;
+------+--------------------------------------------------------------+
| View | CreateView |
+------+--------------------------------------------------------------+
| vx | CREATE VIEW vx AS SELECT v AS x FROM [64(1, 2) AS kv (k, v)] |
+------+--------------------------------------------------------------+
(1 row)
```
A side effect of this patch is that view definitions can now use star
expansion, i.e. `CREATE VIEW kv_alias AS SELECT * FROM kv` is now
possible and valid. (And there was much rejoicing.)
Another side effect, visible in the example above, is that `SHOW
CREATE VIEW` now reveals the structural dependency (showing both the
ID and the original table name) when the table's name or column
definitions change.
This may or may not be desirable from a UX perspective, however anyone
wishing to improve upon this will take note that if the column list in
the table descriptor was altered after the view was created (e.g. to
add new columns, rename columns or remove columns not depended on by
the view), there is no valid way to print out the view definition
using valid SQL but without using the table reference syntax. Consider
the example above: suppose column "v" was renamed to "w"; trying to
print out as `create view vx as select v as x from kv` would be
invalid because then column "v" would have disappeared; then suppose
"v" was renamed to "w" and a new unrelated column "v" was added,
trying `create view vx as select v as x from kv as kv(v)` would be
invalid as well because the new column `v` is unrelated to the one the
view was intended to depend on. Due to these obstacles, it is
advisable to let the numeric table reference show up in the output of
`SHOW CREATE VIEW` and document this behavior.
Although it would be correct to do so for newly-created clusters, this
patch does *not* lift the restriction on ALTER that prevents it from
renaming tables or columns depended on by views. This change would be
correct on new clusters because once the guarantee is enforced that
all view descriptors depend on table/columns by IDs, renaming becomes
possible (renaming preserves the ID); however, for previously created
clusters there may exist already some view descriptors containing
by-name table references, and allowing those to be renamed would be
unsound. The proper approach is to completement this patch by a
cluster migration which rewrites all existing view descriptors. This
work is left to a subsequent commit.
A last improvement brought by this PR is that column renames are now
properly visible in pg_catalog:
```sql
> CREATE VIEW v (x) AS SELECT k FROM kv
> SELECT definition FROM pg_catalog.pg_views WHERE viewname = 'v'
SELECT k AS x FROM (SELECT k FROM kv)
```