!4136 Rename支持修改表的schema

Merge pull request !4136 from Cross-罗/rename_support_schema
This commit is contained in:
opengauss_bot
2023-10-16 06:59:56 +00:00
committed by Gitee
10 changed files with 536 additions and 22 deletions

View File

@ -5585,6 +5585,7 @@ static RenameStmt* _copyRenameStmt(const RenameStmt* from)
COPY_NODE_FIELD(objarg);
COPY_STRING_FIELD(subname);
COPY_STRING_FIELD(newname);
COPY_STRING_FIELD(newschema);
COPY_SCALAR_FIELD(behavior);
COPY_SCALAR_FIELD(missing_ok);
COPY_NODE_FIELD(renameTargetList);

View File

@ -1585,6 +1585,7 @@ static bool _equalRenameStmt(const RenameStmt* a, const RenameStmt* b)
COMPARE_NODE_FIELD(objarg);
COMPARE_STRING_FIELD(subname);
COMPARE_STRING_FIELD(newname);
COMPARE_STRING_FIELD(newschema);
COMPARE_SCALAR_FIELD(behavior);
COMPARE_SCALAR_FIELD(missing_ok);
COMPARE_NODE_FIELD(renameTargetList);

View File

@ -17696,23 +17696,25 @@ RenameStmt: ALTER AGGREGATE func_name aggr_args RENAME TO name
n->missing_ok = true;
$$ = (Node *)n;
}
| ALTER TABLE relation_expr RENAME TO name
| ALTER TABLE relation_expr RENAME TO qualified_name
{
RenameStmt *n = makeNode(RenameStmt);
n->renameType = OBJECT_TABLE;
n->relation = $3;
n->subname = NULL;
n->newname = $6;
n->newname = $6->relname;
n->newschema = $6->schemaname;
n->missing_ok = false;
$$ = (Node *)n;
}
| ALTER TABLE IF_P EXISTS relation_expr RENAME TO name
| ALTER TABLE IF_P EXISTS relation_expr RENAME TO qualified_name
{
RenameStmt *n = makeNode(RenameStmt);
n->renameType = OBJECT_TABLE;
n->relation = $5;
n->subname = NULL;
n->newname = $8;
n->newname = $8->relname;
n->newschema = $8->schemaname;
n->missing_ok = true;
$$ = (Node *)n;
}

View File

@ -781,6 +781,8 @@ static int128 EvaluateAutoIncrement(Relation rel, TupleDesc desc, AttrNumber att
static void SetRelAutoIncrement(Relation rel, TupleDesc desc, int128 autoinc);
static Node* RecookAutoincAttrDefault(Relation rel, int attrno, Oid targettype, int targettypmod);
static void check_unsupported_charset_for_column(Oid collation, const char* col_name);
static void AlterTableNamespaceDependentProcess(Relation classRel ,Relation rel, Oid oldNspOid,
Oid nspOid, ObjectAddresses* objsMoved, char* newrelname);
inline static bool CStoreSupportATCmd(AlterTableType cmdtype)
{
@ -6585,7 +6587,7 @@ ObjectAddress RenameRelation(RenameStmt* stmt)
#endif
/* Do the work */
RenameRelationInternal(relid, stmt->newname);
RenameRelationInternal(relid, stmt->newname, stmt->newschema);
/*
* Record the changecsn of the table that defines the index
*/
@ -6610,13 +6612,22 @@ ObjectAddress RenameRelation(RenameStmt* stmt)
* the sequence name should probably be removed from the
* sequence, AFAIK there's no need for it to be there.
*/
void RenameRelationInternal(Oid myrelid, const char* newrelname)
void RenameRelationInternal(Oid myrelid, const char* newrelname, char* newschema)
{
Relation targetrelation;
Relation relrelation; /* for RELATION relation */
HeapTuple reltup;
Form_pg_class relform;
Oid namespaceId;
Oid oldNspOid = InvalidOid;
bool needChangeNsp = false;
ObjectAddresses* objsMoved = NULL;
ObjectAddress thisobj;
bool is_present = false;
thisobj.classId = RelationRelationId;
thisobj.objectId = myrelid;
thisobj.objectSubId = 0;
/*
* Grab an exclusive lock on the target table, index, sequence or view,
@ -6624,6 +6635,26 @@ void RenameRelationInternal(Oid myrelid, const char* newrelname)
*/
targetrelation = relation_open(myrelid, AccessExclusiveLock);
if (newschema != NULL) {
if (targetrelation->rd_mlogoid != InvalidOid) {
ereport(ERROR,
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
(errmsg("Un-support feature"),
errdetail("table owning matview doesn't support this ALTER yet."))));
}
if (targetrelation->rd_rel->relkind == RELKIND_MATVIEW) {
ereport(ERROR,
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
errmsg("ALTER MATERIALIZED VIEW is not yet supported.")));
}
/* Permission check */
if (!pg_class_ownercheck(RelationGetRelid(targetrelation), GetUserId())) {
aclcheck_error(ACLCHECK_NOT_OWNER, ACL_KIND_CLASS, RelationGetRelationName(targetrelation));
}
}
if (RelationIsSubPartitioned(targetrelation)) {
ereport(
ERROR,
@ -6655,6 +6686,24 @@ void RenameRelationInternal(Oid myrelid, const char* newrelname)
relform = (Form_pg_class)GETSTRUCT(reltup);
oldNspOid = namespaceId;
if (newschema != NULL) {
/* Get and lock schema OID and check its permissions. */
RangeVar* newrv = makeRangeVar(newschema, (char*)newrelname, -1);
Oid newNspOid = RangeVarGetAndCheckCreationNamespace(newrv, NoLock, NULL, '\0');
needChangeNsp = (newNspOid != namespaceId);
if (needChangeNsp) {
/* common checks on switching namespaces */
CheckSetNamespace(namespaceId, newNspOid, RelationRelationId, myrelid);
ledger_check_switch_schema(namespaceId, newNspOid);
objsMoved = new_object_addresses();
namespaceId = newNspOid;
is_present = object_address_present(&thisobj, objsMoved);
}
}
/*
* Check relation name to ensure that it doesn't conflict with existing synonym.
*/
@ -6664,8 +6713,17 @@ void RenameRelationInternal(Oid myrelid, const char* newrelname)
get_namespace_name(namespaceId))));
}
if (get_relname_relid(newrelname, namespaceId) != InvalidOid)
ereport(ERROR, (errcode(ERRCODE_DUPLICATE_TABLE), errmsg("relation \"%s\" already exists", newrelname)));
if (get_relname_relid(newrelname, namespaceId) != InvalidOid) {
if (newschema != NULL) {
ereport(ERROR,
(errcode(ERRCODE_DUPLICATE_TABLE),
errmsg("relation \"%s\" already exists in schema \"%s\"",
newrelname,
newschema)));
} else {
ereport(ERROR, (errcode(ERRCODE_DUPLICATE_TABLE), errmsg("relation \"%s\" already exists", newrelname)));
}
}
#ifdef ENABLE_MULTIPLE_NODES
if (RelationIsTsStore(targetrelation)) {
@ -6692,6 +6750,9 @@ void RenameRelationInternal(Oid myrelid, const char* newrelname)
*/
(void)namestrcpy(&(relform->relname), newrelname);
/* Update pg_class tuple with new nsp. */
relform->relnamespace = namespaceId;
simple_heap_update(relrelation, &reltup->t_self, reltup);
/* keep the system catalog indexes current */
@ -6708,14 +6769,33 @@ void RenameRelationInternal(Oid myrelid, const char* newrelname)
renamePartitionedTable(myrelid, newrelname);
}
if (needChangeNsp && !is_present) {
if (changeDependencyFor(RelationRelationId, myrelid, NamespaceRelationId, oldNspOid, namespaceId) != 1) {
ereport(ERROR,
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
errmsg("failed to change schema dependency for relation \"%s\"", NameStr(relform->relname))));
}
add_exact_object_address(&thisobj, objsMoved);
}
tableam_tops_free_tuple(reltup);
heap_close(relrelation, RowExclusiveLock);
/*
* Also rename the associated type, if any.
*/
if (OidIsValid(targetrelation->rd_rel->reltype))
RenameTypeInternal(targetrelation->rd_rel->reltype, newrelname, namespaceId);
if (needChangeNsp && !is_present) {
AlterTableNamespaceDependentProcess(relrelation, targetrelation, oldNspOid, namespaceId, objsMoved,
(char*)newrelname);
if (targetrelation->rd_isblockchain) {
rename_hist_by_newnsp(myrelid, newschema);
}
free_object_addresses(objsMoved);
} else {
/*
* Also rename the associated type, if any.
*/
if (OidIsValid(targetrelation->rd_rel->reltype))
RenameTypeInternal(targetrelation->rd_rel->reltype, newrelname, oldNspOid);
}
/*
* Also rename the associated constraint, if any.
@ -21500,8 +21580,16 @@ void AlterTableNamespaceInternal(Relation rel, Oid oldNspOid, Oid nspOid, Object
AlterRelationNamespaceInternal(classRel, RelationGetRelid(rel), oldNspOid, nspOid, true, objsMoved);
AlterTableNamespaceDependentProcess(classRel, rel, oldNspOid, nspOid, objsMoved, NULL);
heap_close(classRel, RowExclusiveLock);
}
static void AlterTableNamespaceDependentProcess(Relation classRel ,Relation rel, Oid oldNspOid,
Oid nspOid, ObjectAddresses* objsMoved, char* newrelname)
{
/* Fix the table's row type too */
(void)AlterTypeNamespaceInternal(rel->rd_rel->reltype, nspOid, false, false, objsMoved);
(void)AlterTypeNamespaceInternal(rel->rd_rel->reltype, nspOid, false, false, objsMoved, newrelname);
/* Change the table's set type too */
TupleDesc tupDesc = rel->rd_att;
@ -21518,8 +21606,6 @@ void AlterTableNamespaceInternal(Relation rel, Oid oldNspOid, Oid nspOid, Object
AlterSeqNamespaces(classRel, rel, oldNspOid, nspOid, objsMoved, AccessExclusiveLock);
AlterConstraintNamespaces(RelationGetRelid(rel), oldNspOid, nspOid, false, objsMoved);
}
heap_close(classRel, RowExclusiveLock);
}
/*

View File

@ -3653,7 +3653,7 @@ Oid AlterTypeNamespace_oid(Oid typeOid, Oid nspOid, ObjectAddresses* objsMoved)
* Returns the type's old namespace OID.
*/
Oid AlterTypeNamespaceInternal(
Oid typeOid, Oid nspOid, bool isImplicitArray, bool errorOnTableType, ObjectAddresses* objsMoved)
Oid typeOid, Oid nspOid, bool isImplicitArray, bool errorOnTableType, ObjectAddresses* objsMoved, char* newTypeName)
{
Relation rel;
HeapTuple tup;
@ -3687,7 +3687,8 @@ Oid AlterTypeNamespaceInternal(
CheckSetNamespace(oldNspOid, nspOid, TypeRelationId, typeOid);
/* check for duplicate name (more friendly than unique-index failure) */
if (SearchSysCacheExists2(TYPENAMENSP, CStringGetDatum(NameStr(typform->typname)), ObjectIdGetDatum(nspOid)))
char* checkTypeName = (newTypeName == NULL) ? NameStr(typform->typname) : newTypeName;
if (SearchSysCacheExists2(TYPENAMENSP, CStringGetDatum(checkTypeName), ObjectIdGetDatum(nspOid)))
ereport(ERROR,
(errcode(ERRCODE_DUPLICATE_OBJECT),
errmsg("type \"%s\" already exists in schema \"%s\"",
@ -3709,6 +3710,9 @@ Oid AlterTypeNamespaceInternal(
* tup is a copy, so we can scribble directly on it
*/
typform->typnamespace = nspOid;
if (newTypeName != NULL) {
(void)namestrcpy(&(typform->typname), newTypeName);
}
simple_heap_update(rel, &tup->t_self, tup);
CatalogUpdateIndexes(rel, tup);
@ -3756,8 +3760,10 @@ Oid AlterTypeNamespaceInternal(
add_exact_object_address(&thisobj, objsMoved);
/* Recursively alter the associated array type, if any */
if (OidIsValid(arrayOid))
AlterTypeNamespaceInternal(arrayOid, nspOid, true, true, objsMoved);
if (OidIsValid(arrayOid)) {
AlterTypeNamespaceInternal(arrayOid, nspOid, true, true, objsMoved,
(newTypeName == NULL) ? NULL : makeArrayTypeName(newTypeName, nspOid));
}
return oldNspOid;
}

View File

@ -157,7 +157,7 @@ extern ObjectAddress RenameConstraint(RenameStmt* stmt);
extern ObjectAddress RenameRelation(RenameStmt* stmt);
extern void RenameRelationInternal(Oid myrelid, const char* newrelname);
extern void RenameRelationInternal(Oid myrelid, const char* newrelname, char* newschema = NULL);
extern void find_composite_type_dependencies(Oid typeOid, Relation origRelation, const char* origTypeName);

View File

@ -47,7 +47,8 @@ extern void AlterTypeOwnerInternal(Oid typeOid, Oid newOwnerId, bool hasDependEn
extern ObjectAddress AlterTypeNamespace(List* names, const char* newschema, ObjectType objecttype);
extern Oid AlterTypeNamespace_oid(Oid typeOid, Oid nspOid, ObjectAddresses* objsMoved);
extern Oid AlterTypeNamespaceInternal(
Oid typeOid, Oid nspOid, bool isImplicitArray, bool errorOnTableType, ObjectAddresses* objsMoved);
Oid typeOid, Oid nspOid, bool isImplicitArray, bool errorOnTableType, ObjectAddresses* objsMoved,
char* newTypeName = NULL);
extern void AlterTypeOwnerByPkg(Oid pkgOid, Oid newOwnerId);
extern void AlterTypeOwnerByFunc(Oid funcOid, Oid newOwnerId);

View File

@ -2380,6 +2380,7 @@ typedef struct RenameStmt {
char* subname; /* name of contained object (column, rule,
* trigger, etc) */
char* newname; /* the new name */
char* newschema; /* the new schema name */
DropBehavior behavior; /* RESTRICT or CASCADE behavior */
bool missing_ok; /* skip error if missing? */
List* renameTargetList = NULL;

View File

@ -8796,5 +8796,293 @@ SELECT pg_get_tabledef('t1');
(1 row)
drop table if exists t1 cascade;
-- test about setting schema by RenameStmt
CREATE SCHEMA test1;
CREATE SCHEMA test2;
CREATE TABLE test1.test(a int primary key, b int not null);
NOTICE: CREATE TABLE / PRIMARY KEY will create implicit index "test_pkey" for table "test"
CREATE INDEX ON test1.test using btree(b);
INSERT INTO test1.test VALUES (1, 1);
\d+ test1.test
Table "test1.test"
Column | Type | Modifiers | Storage | Stats target | Description
--------+---------+-----------+---------+--------------+-------------
a | integer | not null | plain | |
b | integer | not null | plain | |
Indexes:
"test_pkey" PRIMARY KEY, btree (a) TABLESPACE pg_default
"test_b_idx" btree (b) TABLESPACE pg_default
Has OIDs: no
Options: orientation=row, compression=no
SELECT n.nspname, c.relname from pg_class c, pg_namespace n where n.oid = c.relnamespace and c.relname in ('test', 'test_pkey', 'test_b_idx', 'tttt');
nspname | relname
---------+------------
test1 | test
test1 | test_pkey
test1 | test_b_idx
(3 rows)
SELECT * FROM test1.test;
a | b
---+---
1 | 1
(1 row)
-- check about type
SELECT n.nspname, t.typname FROM pg_type t, pg_namespace n where t.typnamespace = n.oid and t.typname in ('test','tttt');
nspname | typname
---------+---------
test1 | test
(1 row)
ALTER TABLE test1.test RENAME TO test2.tttt;
\d+ test1.test
\d+ test2.tttt
Table "test2.tttt"
Column | Type | Modifiers | Storage | Stats target | Description
--------+---------+-----------+---------+--------------+-------------
a | integer | not null | plain | |
b | integer | not null | plain | |
Indexes:
"test_pkey" PRIMARY KEY, btree (a) TABLESPACE pg_default
"test_b_idx" btree (b) TABLESPACE pg_default
Has OIDs: no
Options: orientation=row, compression=no
SELECT n.nspname, c.relname from pg_class c, pg_namespace n where n.oid = c.relnamespace and c.relname in ('test', 'test_pkey', 'test_b_idx', 'tttt');
nspname | relname
---------+------------
test2 | tttt
test2 | test_pkey
test2 | test_b_idx
(3 rows)
INSERT INTO test2.tttt VALUES (2, 2);
SELECT * FROM test1.test;
ERROR: relation "test1.test" does not exist on datanode1
LINE 1: SELECT * FROM test1.test;
^
SELECT * FROM test2.tttt;
a | b
---+---
1 | 1
2 | 2
(2 rows)
-- check about type
SELECT n.nspname, t.typname FROM pg_type t, pg_namespace n where t.typnamespace = n.oid and t.typname in ('test','tttt');
nspname | typname
---------+---------
test2 | tttt
(1 row)
-- just rename
ALTER TABLE test2.tttt RENAME TO test2.ttt;
SELECT * FROM test2.tttt;
ERROR: relation "test2.tttt" does not exist on datanode1
LINE 1: SELECT * FROM test2.tttt;
^
SELECT * FROM test2.ttt;
a | b
---+---
1 | 1
2 | 2
(2 rows)
-- check about type
SELECT n.nspname, t.typname FROM pg_type t, pg_namespace n where t.typnamespace = n.oid and t.typname = 'ttt';
nspname | typname
---------+---------
test2 | ttt
(1 row)
-- just move to other schema
CREATE TABLE test1.t1 (a int);
\d+ test1.t1
Table "test1.t1"
Column | Type | Modifiers | Storage | Stats target | Description
--------+---------+-----------+---------+--------------+-------------
a | integer | | plain | |
Has OIDs: no
Options: orientation=row, compression=no
ALTER TABLE test1.t1 RENAME TO test2.t1;
\d+ test1.t1
\d+ test2.t1
Table "test2.t1"
Column | Type | Modifiers | Storage | Stats target | Description
--------+---------+-----------+---------+--------------+-------------
a | integer | | plain | |
Has OIDs: no
Options: orientation=row, compression=no
-- check about type
SELECT n.nspname, t.typname FROM pg_type t, pg_namespace n where t.typnamespace = n.oid and t.typname = 't1';
nspname | typname
---------+---------
test2 | t1
(1 row)
-- test about partition table
CREATE TABLE test1.sales_table1
(
order_no INTEGER NOT NULL,
goods_name CHAR(20) NOT NULL,
sales_date DATE NOT NULL,
sales_volume INTEGER,
sales_store CHAR(20)
)
PARTITION BY RANGE(sales_date)
(
PARTITION sales_table1_season1 VALUES LESS THAN('2021-04-01 00:00:00'),
PARTITION sales_table1_season2 VALUES LESS THAN('2021-07-01 00:00:00'),
PARTITION sales_table1_season3 VALUES LESS THAN('2021-10-01 00:00:00'),
PARTITION sales_table1_season4 VALUES LESS THAN(MAXVALUE)
);
CREATE TABLE test1.sales_table2
(
order_no INTEGER NOT NULL,
goods_name CHAR(20) NOT NULL,
sales_date DATE NOT NULL,
sales_volume INTEGER,
sales_store CHAR(20)
)
PARTITION BY RANGE(sales_date)
(
PARTITION sales_table2_season1 VALUES LESS THAN('2021-04-01 00:00:00'),
PARTITION sales_table2_season2 VALUES LESS THAN('2021-07-01 00:00:00'),
PARTITION sales_table2_season3 VALUES LESS THAN('2021-10-01 00:00:00'),
PARTITION sales_table2_season4 VALUES LESS THAN(MAXVALUE)
);
CREATE TABLE test1.sales_table3
(
order_no INTEGER NOT NULL,
goods_name CHAR(20) NOT NULL,
sales_date DATE NOT NULL,
sales_volume INTEGER,
sales_store CHAR(20)
)
PARTITION BY RANGE(sales_date)
(
PARTITION sales_table3_season1 VALUES LESS THAN('2021-04-01 00:00:00'),
PARTITION sales_table3_season2 VALUES LESS THAN('2021-07-01 00:00:00'),
PARTITION sales_table3_season3 VALUES LESS THAN('2021-10-01 00:00:00'),
PARTITION sales_table3_season4 VALUES LESS THAN(MAXVALUE)
);
SELECT n.nspname, c.relname, p.relname AS partition_name
FROM pg_class c, pg_namespace n, pg_partition p
WHERE n.oid = c.relnamespace and c.oid = p.parentid and c.relname like '%sales_table%' ORDER BY 1, 2, 3;
nspname | relname | partition_name
---------+--------------+----------------------
test1 | sales_table1 | sales_table1
test1 | sales_table1 | sales_table1_season1
test1 | sales_table1 | sales_table1_season2
test1 | sales_table1 | sales_table1_season3
test1 | sales_table1 | sales_table1_season4
test1 | sales_table2 | sales_table2
test1 | sales_table2 | sales_table2_season1
test1 | sales_table2 | sales_table2_season2
test1 | sales_table2 | sales_table2_season3
test1 | sales_table2 | sales_table2_season4
test1 | sales_table3 | sales_table3
test1 | sales_table3 | sales_table3_season1
test1 | sales_table3 | sales_table3_season2
test1 | sales_table3 | sales_table3_season3
test1 | sales_table3 | sales_table3_season4
(15 rows)
ALTER TABLE test1.sales_table1 RENAME TO test2.sales_table1;
ALTER TABLE test1.sales_table2 RENAME TO test2.sales_table3;
ALTER TABLE test1.sales_table3 RENAME TO test1.sales_table4;
SELECT n.nspname, c.relname, p.relname AS partition_name
FROM pg_class c, pg_namespace n, pg_partition p
WHERE n.oid = c.relnamespace and c.oid = p.parentid and c.relname like '%sales_table%' ORDER BY 1, 2, 3;
nspname | relname | partition_name
---------+--------------+----------------------
test1 | sales_table4 | sales_table3_season1
test1 | sales_table4 | sales_table3_season2
test1 | sales_table4 | sales_table3_season3
test1 | sales_table4 | sales_table3_season4
test1 | sales_table4 | sales_table4
test2 | sales_table1 | sales_table1
test2 | sales_table1 | sales_table1_season1
test2 | sales_table1 | sales_table1_season2
test2 | sales_table1 | sales_table1_season3
test2 | sales_table1 | sales_table1_season4
test2 | sales_table3 | sales_table2_season1
test2 | sales_table3 | sales_table2_season2
test2 | sales_table3 | sales_table2_season3
test2 | sales_table3 | sales_table2_season4
test2 | sales_table3 | sales_table3
(15 rows)
-- rename table with view or matview
CREATE TABLE test1.test_table_view1 (a int);
CREATE TABLE test1.test_table_view2 (a int);
CREATE TABLE test1.test_table_matview1 (a int);
CREATE TABLE test1.test_table_matview2 (a int);
CREATE VIEW test1.test_view1 AS SELECT * FROM test1.test_table_view1;
CREATE VIEW test1.test_view2 AS SELECT * FROM test1.test_table_view2;
CREATE MATERIALIZED VIEW test1.test_matview1 AS SELECT * FROM test1.test_table_matview1;
CREATE MATERIALIZED VIEW test1.test_matview2 AS SELECT * FROM test1.test_table_matview2;
ALTER TABLE test1.test_table_view1 RENAME TO test2.test_table_view1; -- just move to other schema
ALTER TABLE test1.test_table_view2 RENAME TO test2.test_table_view3; -- rename and move to other schema
SELECT * FROM test1.test_view1;
a
---
(0 rows)
SELECT pg_get_viewdef('test1.test_view1');
pg_get_viewdef
----------------------------------------
SELECT * FROM test2.test_table_view1;
(1 row)
SELECT * FROM test1.test_view2;
a
---
(0 rows)
SELECT pg_get_viewdef('test1.test_view2');
pg_get_viewdef
---------------------------------------------------------
SELECT * FROM test2.test_table_view3 test_table_view2;
(1 row)
ALTER TABLE test1.test_table_matview1 RENAME TO test2.test_table_matview1; -- just move to other schema
ALTER TABLE test1.test_table_matview2 RENAME TO test2.test_table_matview3; -- rename and move to other schema
SELECT * FROM test1.test_matview1;
a
---
(0 rows)
SELECT pg_get_viewdef('test1.test_matview1');
pg_get_viewdef
-------------------------------------------
SELECT * FROM test2.test_table_matview1;
(1 row)
SELECT * FROM test1.test_matview2;
a
---
(0 rows)
SELECT pg_get_viewdef('test1.test_matview2');
pg_get_viewdef
---------------------------------------------------------------
SELECT * FROM test2.test_table_matview3 test_table_matview2;
(1 row)
-- rename to a existed table
CREATE TABLE test1.name1 (a int);
CREATE TABLE test2.name1 (a int);
CREATE TABLE test2.name2 (a int);
ALTER TABLE test1.name1 RENAME TO test2.name1;
ERROR: relation "name1" already exists in schema "test2"
ALTER TABLE test1.name1 RENAME TO test2.name2;
ERROR: relation "name2" already exists in schema "test2"
ALTER TABLE test2.name1 RENAME TO test2.name2;
ERROR: relation "name2" already exists in schema "test2"
\c postgres
drop database test_first_after_B;

View File

@ -3256,5 +3256,133 @@ alter table t1 modify f1 int after f3, modify f5 bool first, modify f3 timestamp
SELECT pg_get_tabledef('t1');
drop table if exists t1 cascade;
-- test about setting schema by RenameStmt
CREATE SCHEMA test1;
CREATE SCHEMA test2;
CREATE TABLE test1.test(a int primary key, b int not null);
CREATE INDEX ON test1.test using btree(b);
INSERT INTO test1.test VALUES (1, 1);
\d+ test1.test
SELECT n.nspname, c.relname from pg_class c, pg_namespace n where n.oid = c.relnamespace and c.relname in ('test', 'test_pkey', 'test_b_idx', 'tttt');
SELECT * FROM test1.test;
-- check about type
SELECT n.nspname, t.typname FROM pg_type t, pg_namespace n where t.typnamespace = n.oid and t.typname in ('test','tttt');
ALTER TABLE test1.test RENAME TO test2.tttt;
\d+ test1.test
\d+ test2.tttt
SELECT n.nspname, c.relname from pg_class c, pg_namespace n where n.oid = c.relnamespace and c.relname in ('test', 'test_pkey', 'test_b_idx', 'tttt');
INSERT INTO test2.tttt VALUES (2, 2);
SELECT * FROM test1.test;
SELECT * FROM test2.tttt;
-- check about type
SELECT n.nspname, t.typname FROM pg_type t, pg_namespace n where t.typnamespace = n.oid and t.typname in ('test','tttt');
-- just rename
ALTER TABLE test2.tttt RENAME TO test2.ttt;
SELECT * FROM test2.tttt;
SELECT * FROM test2.ttt;
-- check about type
SELECT n.nspname, t.typname FROM pg_type t, pg_namespace n where t.typnamespace = n.oid and t.typname = 'ttt';
-- just move to other schema
CREATE TABLE test1.t1 (a int);
\d+ test1.t1
ALTER TABLE test1.t1 RENAME TO test2.t1;
\d+ test1.t1
\d+ test2.t1
-- check about type
SELECT n.nspname, t.typname FROM pg_type t, pg_namespace n where t.typnamespace = n.oid and t.typname = 't1';
-- test about partition table
CREATE TABLE test1.sales_table1
(
order_no INTEGER NOT NULL,
goods_name CHAR(20) NOT NULL,
sales_date DATE NOT NULL,
sales_volume INTEGER,
sales_store CHAR(20)
)
PARTITION BY RANGE(sales_date)
(
PARTITION sales_table1_season1 VALUES LESS THAN('2021-04-01 00:00:00'),
PARTITION sales_table1_season2 VALUES LESS THAN('2021-07-01 00:00:00'),
PARTITION sales_table1_season3 VALUES LESS THAN('2021-10-01 00:00:00'),
PARTITION sales_table1_season4 VALUES LESS THAN(MAXVALUE)
);
CREATE TABLE test1.sales_table2
(
order_no INTEGER NOT NULL,
goods_name CHAR(20) NOT NULL,
sales_date DATE NOT NULL,
sales_volume INTEGER,
sales_store CHAR(20)
)
PARTITION BY RANGE(sales_date)
(
PARTITION sales_table2_season1 VALUES LESS THAN('2021-04-01 00:00:00'),
PARTITION sales_table2_season2 VALUES LESS THAN('2021-07-01 00:00:00'),
PARTITION sales_table2_season3 VALUES LESS THAN('2021-10-01 00:00:00'),
PARTITION sales_table2_season4 VALUES LESS THAN(MAXVALUE)
);
CREATE TABLE test1.sales_table3
(
order_no INTEGER NOT NULL,
goods_name CHAR(20) NOT NULL,
sales_date DATE NOT NULL,
sales_volume INTEGER,
sales_store CHAR(20)
)
PARTITION BY RANGE(sales_date)
(
PARTITION sales_table3_season1 VALUES LESS THAN('2021-04-01 00:00:00'),
PARTITION sales_table3_season2 VALUES LESS THAN('2021-07-01 00:00:00'),
PARTITION sales_table3_season3 VALUES LESS THAN('2021-10-01 00:00:00'),
PARTITION sales_table3_season4 VALUES LESS THAN(MAXVALUE)
);
SELECT n.nspname, c.relname, p.relname AS partition_name
FROM pg_class c, pg_namespace n, pg_partition p
WHERE n.oid = c.relnamespace and c.oid = p.parentid and c.relname like '%sales_table%' ORDER BY 1, 2, 3;
ALTER TABLE test1.sales_table1 RENAME TO test2.sales_table1;
ALTER TABLE test1.sales_table2 RENAME TO test2.sales_table3;
ALTER TABLE test1.sales_table3 RENAME TO test1.sales_table4;
SELECT n.nspname, c.relname, p.relname AS partition_name
FROM pg_class c, pg_namespace n, pg_partition p
WHERE n.oid = c.relnamespace and c.oid = p.parentid and c.relname like '%sales_table%' ORDER BY 1, 2, 3;
-- rename table with view or matview
CREATE TABLE test1.test_table_view1 (a int);
CREATE TABLE test1.test_table_view2 (a int);
CREATE TABLE test1.test_table_matview1 (a int);
CREATE TABLE test1.test_table_matview2 (a int);
CREATE VIEW test1.test_view1 AS SELECT * FROM test1.test_table_view1;
CREATE VIEW test1.test_view2 AS SELECT * FROM test1.test_table_view2;
CREATE MATERIALIZED VIEW test1.test_matview1 AS SELECT * FROM test1.test_table_matview1;
CREATE MATERIALIZED VIEW test1.test_matview2 AS SELECT * FROM test1.test_table_matview2;
ALTER TABLE test1.test_table_view1 RENAME TO test2.test_table_view1; -- just move to other schema
ALTER TABLE test1.test_table_view2 RENAME TO test2.test_table_view3; -- rename and move to other schema
SELECT * FROM test1.test_view1;
SELECT pg_get_viewdef('test1.test_view1');
SELECT * FROM test1.test_view2;
SELECT pg_get_viewdef('test1.test_view2');
ALTER TABLE test1.test_table_matview1 RENAME TO test2.test_table_matview1; -- just move to other schema
ALTER TABLE test1.test_table_matview2 RENAME TO test2.test_table_matview3; -- rename and move to other schema
SELECT * FROM test1.test_matview1;
SELECT pg_get_viewdef('test1.test_matview1');
SELECT * FROM test1.test_matview2;
SELECT pg_get_viewdef('test1.test_matview2');
-- rename to a existed table
CREATE TABLE test1.name1 (a int);
CREATE TABLE test2.name1 (a int);
CREATE TABLE test2.name2 (a int);
ALTER TABLE test1.name1 RENAME TO test2.name1;
ALTER TABLE test1.name1 RENAME TO test2.name2;
ALTER TABLE test2.name1 RENAME TO test2.name2;
\c postgres
drop database test_first_after_B;