Commit c4f2a045 authored by Tom Lane's avatar Tom Lane

Improve reporting of dependencies in DROP to work like the scheme that we

devised for pg_shdepend, namely the individual dependencies are reported as
DETAIL lines rather than coming out as separate NOTICEs.  The client-side
report is capped at 100 lines, but the server log always gets a full report.
parent ebff1d4d
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* IDENTIFICATION * IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/catalog/dependency.c,v 1.74 2008/06/08 22:41:04 tgl Exp $ * $PostgreSQL: pgsql/src/backend/catalog/dependency.c,v 1.75 2008/06/11 21:53:48 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -62,6 +62,7 @@ ...@@ -62,6 +62,7 @@
#include "storage/lmgr.h" #include "storage/lmgr.h"
#include "utils/builtins.h" #include "utils/builtins.h"
#include "utils/fmgroids.h" #include "utils/fmgroids.h"
#include "utils/guc.h"
#include "utils/lsyscache.h" #include "utils/lsyscache.h"
#include "utils/syscache.h" #include "utils/syscache.h"
#include "utils/tqual.h" #include "utils/tqual.h"
...@@ -752,7 +753,7 @@ findDependentObjects(const ObjectAddress *object, ...@@ -752,7 +753,7 @@ findDependentObjects(const ObjectAddress *object,
* *
* targetObjects: list of objects that are scheduled to be deleted * targetObjects: list of objects that are scheduled to be deleted
* behavior: RESTRICT or CASCADE * behavior: RESTRICT or CASCADE
* msglevel: elog level for non-debug notice messages * msglevel: elog level for non-error report messages
* origObject: base object of deletion, or NULL if not available * origObject: base object of deletion, or NULL if not available
* (the latter case occurs in DROP OWNED) * (the latter case occurs in DROP OWNED)
*/ */
...@@ -763,8 +764,36 @@ reportDependentObjects(const ObjectAddresses *targetObjects, ...@@ -763,8 +764,36 @@ reportDependentObjects(const ObjectAddresses *targetObjects,
const ObjectAddress *origObject) const ObjectAddress *origObject)
{ {
bool ok = true; bool ok = true;
StringInfoData clientdetail;
StringInfoData logdetail;
int numReportedClient = 0;
int numNotReportedClient = 0;
int i; int i;
/*
* If no error is to be thrown, and the msglevel is too low to be shown
* to either client or server log, there's no need to do any of the work.
*
* Note: this code doesn't know all there is to be known about elog
* levels, but it works for NOTICE and DEBUG2, which are the only values
* msglevel can currently have. We also assume we are running in a normal
* operating environment.
*/
if (behavior == DROP_CASCADE &&
msglevel < client_min_messages &&
(msglevel < log_min_messages || log_min_messages == LOG))
return;
/*
* We limit the number of dependencies reported to the client to
* MAX_REPORTED_DEPS, since client software may not deal well with
* enormous error strings. The server log always gets a full report.
*/
#define MAX_REPORTED_DEPS 100
initStringInfo(&clientdetail);
initStringInfo(&logdetail);
/* /*
* We process the list back to front (ie, in dependency order not deletion * We process the list back to front (ie, in dependency order not deletion
* order), since this makes for a more understandable display. * order), since this makes for a more understandable display.
...@@ -773,34 +802,82 @@ reportDependentObjects(const ObjectAddresses *targetObjects, ...@@ -773,34 +802,82 @@ reportDependentObjects(const ObjectAddresses *targetObjects,
{ {
const ObjectAddress *obj = &targetObjects->refs[i]; const ObjectAddress *obj = &targetObjects->refs[i];
const ObjectAddressExtra *extra = &targetObjects->extras[i]; const ObjectAddressExtra *extra = &targetObjects->extras[i];
char *objDesc;
/* Ignore the original deletion target(s) */ /* Ignore the original deletion target(s) */
if (extra->flags & DEPFLAG_ORIGINAL) if (extra->flags & DEPFLAG_ORIGINAL)
continue; continue;
objDesc = getObjectDescription(obj);
/* /*
* If, at any stage of the recursive search, we reached the object * If, at any stage of the recursive search, we reached the object
* via an AUTO or INTERNAL dependency, then it's okay to delete it * via an AUTO or INTERNAL dependency, then it's okay to delete it
* even in RESTRICT mode. * even in RESTRICT mode.
*/ */
if (extra->flags & (DEPFLAG_AUTO | DEPFLAG_INTERNAL)) if (extra->flags & (DEPFLAG_AUTO | DEPFLAG_INTERNAL))
{
/*
* auto-cascades are reported at DEBUG2, not msglevel. We
* don't try to combine them with the regular message because
* the results are too confusing when client_min_messages and
* log_min_messages are different.
*/
ereport(DEBUG2, ereport(DEBUG2,
(errmsg("drop auto-cascades to %s", (errmsg("drop auto-cascades to %s",
getObjectDescription(obj)))); objDesc)));
}
else if (behavior == DROP_RESTRICT) else if (behavior == DROP_RESTRICT)
{ {
ereport(msglevel, char *otherDesc = getObjectDescription(&extra->dependee);
(errmsg("%s depends on %s",
getObjectDescription(obj), if (numReportedClient < MAX_REPORTED_DEPS)
getObjectDescription(&extra->dependee)))); {
/* separate entries with a newline */
if (clientdetail.len != 0)
appendStringInfoChar(&clientdetail, '\n');
appendStringInfo(&clientdetail, _("%s depends on %s"),
objDesc, otherDesc);
numReportedClient++;
}
else
numNotReportedClient++;
/* separate entries with a newline */
if (logdetail.len != 0)
appendStringInfoChar(&logdetail, '\n');
appendStringInfo(&logdetail, _("%s depends on %s"),
objDesc, otherDesc);
pfree(otherDesc);
ok = false; ok = false;
} }
else else
ereport(msglevel, {
(errmsg("drop cascades to %s", if (numReportedClient < MAX_REPORTED_DEPS)
getObjectDescription(obj)))); {
/* separate entries with a newline */
if (clientdetail.len != 0)
appendStringInfoChar(&clientdetail, '\n');
appendStringInfo(&clientdetail, _("drop cascades to %s"),
objDesc);
numReportedClient++;
}
else
numNotReportedClient++;
/* separate entries with a newline */
if (logdetail.len != 0)
appendStringInfoChar(&logdetail, '\n');
appendStringInfo(&logdetail, _("drop cascades to %s"),
objDesc);
}
pfree(objDesc);
} }
if (numNotReportedClient > 0)
appendStringInfo(&clientdetail, _("\nand %d other objects "
"(see server log for list)"),
numNotReportedClient);
if (!ok) if (!ok)
{ {
if (origObject) if (origObject)
...@@ -808,13 +885,35 @@ reportDependentObjects(const ObjectAddresses *targetObjects, ...@@ -808,13 +885,35 @@ reportDependentObjects(const ObjectAddresses *targetObjects,
(errcode(ERRCODE_DEPENDENT_OBJECTS_STILL_EXIST), (errcode(ERRCODE_DEPENDENT_OBJECTS_STILL_EXIST),
errmsg("cannot drop %s because other objects depend on it", errmsg("cannot drop %s because other objects depend on it",
getObjectDescription(origObject)), getObjectDescription(origObject)),
errdetail("%s", clientdetail.data),
errdetail_log("%s", logdetail.data),
errhint("Use DROP ... CASCADE to drop the dependent objects too."))); errhint("Use DROP ... CASCADE to drop the dependent objects too.")));
else else
ereport(ERROR, ereport(ERROR,
(errcode(ERRCODE_DEPENDENT_OBJECTS_STILL_EXIST), (errcode(ERRCODE_DEPENDENT_OBJECTS_STILL_EXIST),
errmsg("cannot drop desired object(s) because other objects depend on them"), errmsg("cannot drop desired object(s) because other objects depend on them"),
errdetail("%s", clientdetail.data),
errdetail_log("%s", logdetail.data),
errhint("Use DROP ... CASCADE to drop the dependent objects too."))); errhint("Use DROP ... CASCADE to drop the dependent objects too.")));
} }
else if (numReportedClient > 1)
{
ereport(msglevel,
/* translator: %d always has a value larger than 1 */
(errmsg("drop cascades to %d other objects",
numReportedClient + numNotReportedClient),
errdetail("%s", clientdetail.data),
errdetail_log("%s", logdetail.data)));
}
else if (numReportedClient == 1)
{
/* we just use the single item as-is */
ereport(msglevel,
(errmsg_internal("%s", clientdetail.data)));
}
pfree(clientdetail.data);
pfree(logdetail.data);
} }
/* /*
......
...@@ -1161,8 +1161,9 @@ order by relname, attnum; ...@@ -1161,8 +1161,9 @@ order by relname, attnum;
(8 rows) (8 rows)
drop table p1, p2 cascade; drop table p1, p2 cascade;
NOTICE: drop cascades to table c1 NOTICE: drop cascades to 2 other objects
NOTICE: drop cascades to table gc1 DETAIL: drop cascades to table c1
drop cascades to table gc1
-- --
-- Test the ALTER TABLE WITHOUT OIDS command -- Test the ALTER TABLE WITHOUT OIDS command
-- --
...@@ -1469,8 +1470,9 @@ select alter2.plus1(41); ...@@ -1469,8 +1470,9 @@ select alter2.plus1(41);
-- clean up -- clean up
drop schema alter2 cascade; drop schema alter2 cascade;
NOTICE: drop cascades to table alter2.t1 NOTICE: drop cascades to 5 other objects
NOTICE: drop cascades to view alter2.v1 DETAIL: drop cascades to table alter2.t1
NOTICE: drop cascades to function alter2.plus1(integer) drop cascades to view alter2.v1
NOTICE: drop cascades to type alter2.posint drop cascades to function alter2.plus1(integer)
NOTICE: drop cascades to type alter2.ctype drop cascades to type alter2.posint
drop cascades to type alter2.ctype
...@@ -237,43 +237,45 @@ And relnamespace IN (SELECT OID FROM pg_namespace WHERE nspname LIKE 'pg_temp%') ...@@ -237,43 +237,45 @@ And relnamespace IN (SELECT OID FROM pg_namespace WHERE nspname LIKE 'pg_temp%')
(1 row) (1 row)
DROP SCHEMA temp_view_test CASCADE; DROP SCHEMA temp_view_test CASCADE;
NOTICE: drop cascades to table temp_view_test.base_table NOTICE: drop cascades to 22 other objects
NOTICE: drop cascades to view v7_temp DETAIL: drop cascades to table temp_view_test.base_table
NOTICE: drop cascades to view v10_temp drop cascades to view v7_temp
NOTICE: drop cascades to view v11_temp drop cascades to view v10_temp
NOTICE: drop cascades to view v12_temp drop cascades to view v11_temp
NOTICE: drop cascades to view v2_temp drop cascades to view v12_temp
NOTICE: drop cascades to view v4_temp drop cascades to view v2_temp
NOTICE: drop cascades to view v6_temp drop cascades to view v4_temp
NOTICE: drop cascades to view v8_temp drop cascades to view v6_temp
NOTICE: drop cascades to view v9_temp drop cascades to view v8_temp
NOTICE: drop cascades to table temp_view_test.base_table2 drop cascades to view v9_temp
NOTICE: drop cascades to view v5_temp drop cascades to table temp_view_test.base_table2
NOTICE: drop cascades to view temp_view_test.v1 drop cascades to view v5_temp
NOTICE: drop cascades to view temp_view_test.v2 drop cascades to view temp_view_test.v1
NOTICE: drop cascades to view temp_view_test.v3 drop cascades to view temp_view_test.v2
NOTICE: drop cascades to view temp_view_test.v4 drop cascades to view temp_view_test.v3
NOTICE: drop cascades to view temp_view_test.v5 drop cascades to view temp_view_test.v4
NOTICE: drop cascades to view temp_view_test.v6 drop cascades to view temp_view_test.v5
NOTICE: drop cascades to view temp_view_test.v7 drop cascades to view temp_view_test.v6
NOTICE: drop cascades to view temp_view_test.v8 drop cascades to view temp_view_test.v7
NOTICE: drop cascades to sequence temp_view_test.seq1 drop cascades to view temp_view_test.v8
NOTICE: drop cascades to view temp_view_test.v9 drop cascades to sequence temp_view_test.seq1
drop cascades to view temp_view_test.v9
DROP SCHEMA testviewschm2 CASCADE; DROP SCHEMA testviewschm2 CASCADE;
NOTICE: drop cascades to table t1 NOTICE: drop cascades to 16 other objects
NOTICE: drop cascades to view temporal1 DETAIL: drop cascades to table t1
NOTICE: drop cascades to view temporal2 drop cascades to view temporal1
NOTICE: drop cascades to view temporal3 drop cascades to view temporal2
NOTICE: drop cascades to view temporal4 drop cascades to view temporal3
NOTICE: drop cascades to table t2 drop cascades to view temporal4
NOTICE: drop cascades to view nontemp1 drop cascades to table t2
NOTICE: drop cascades to view nontemp2 drop cascades to view nontemp1
NOTICE: drop cascades to view nontemp3 drop cascades to view nontemp2
NOTICE: drop cascades to view nontemp4 drop cascades to view nontemp3
NOTICE: drop cascades to table tbl1 drop cascades to view nontemp4
NOTICE: drop cascades to table tbl2 drop cascades to table tbl1
NOTICE: drop cascades to table tbl3 drop cascades to table tbl2
NOTICE: drop cascades to table tbl4 drop cascades to table tbl3
NOTICE: drop cascades to view mytempview drop cascades to table tbl4
NOTICE: drop cascades to view pubview drop cascades to view mytempview
drop cascades to view pubview
SET search_path to public; SET search_path to public;
...@@ -7,8 +7,8 @@ comment on domain domaindroptest is 'About to drop this..'; ...@@ -7,8 +7,8 @@ comment on domain domaindroptest is 'About to drop this..';
create domain dependenttypetest domaindroptest; create domain dependenttypetest domaindroptest;
-- fail because of dependent type -- fail because of dependent type
drop domain domaindroptest; drop domain domaindroptest;
NOTICE: type dependenttypetest depends on type domaindroptest
ERROR: cannot drop type domaindroptest because other objects depend on it ERROR: cannot drop type domaindroptest because other objects depend on it
DETAIL: type dependenttypetest depends on type domaindroptest
HINT: Use DROP ... CASCADE to drop the dependent objects too. HINT: Use DROP ... CASCADE to drop the dependent objects too.
drop domain domaindroptest cascade; drop domain domaindroptest cascade;
NOTICE: drop cascades to type dependenttypetest NOTICE: drop cascades to type dependenttypetest
...@@ -266,8 +266,9 @@ ERROR: domain dnotnulltest does not allow null values ...@@ -266,8 +266,9 @@ ERROR: domain dnotnulltest does not allow null values
alter domain dnotnulltest drop not null; alter domain dnotnulltest drop not null;
update domnotnull set col1 = null; update domnotnull set col1 = null;
drop domain dnotnulltest cascade; drop domain dnotnulltest cascade;
NOTICE: drop cascades to table domnotnull column col1 NOTICE: drop cascades to 2 other objects
NOTICE: drop cascades to table domnotnull column col2 DETAIL: drop cascades to table domnotnull column col1
drop cascades to table domnotnull column col2
-- Test ALTER DOMAIN .. DEFAULT .. -- Test ALTER DOMAIN .. DEFAULT ..
create table domdeftest (col1 ddef1); create table domdeftest (col1 ddef1);
insert into domdeftest default values; insert into domdeftest default values;
...@@ -395,8 +396,9 @@ insert into dtest values('xz23'); -- fail ...@@ -395,8 +396,9 @@ insert into dtest values('xz23'); -- fail
ERROR: value for domain dtop violates check constraint "dtop_check" ERROR: value for domain dtop violates check constraint "dtop_check"
drop table dtest; drop table dtest;
drop domain vchar4 cascade; drop domain vchar4 cascade;
NOTICE: drop cascades to type dinter NOTICE: drop cascades to 2 other objects
NOTICE: drop cascades to type dtop DETAIL: drop cascades to type dinter
drop cascades to type dtop
-- Make sure that constraints of newly-added domain columns are -- Make sure that constraints of newly-added domain columns are
-- enforced correctly, even if there's no default value for the new -- enforced correctly, even if there's no default value for the new
-- column. Per bug #1433 -- column. Per bug #1433
......
...@@ -257,8 +257,8 @@ SELECT * FROM FKTABLE; ...@@ -257,8 +257,8 @@ SELECT * FROM FKTABLE;
-- this should fail for lack of CASCADE -- this should fail for lack of CASCADE
DROP TABLE PKTABLE; DROP TABLE PKTABLE;
NOTICE: constraint constrname2 on table fktable depends on table pktable
ERROR: cannot drop table pktable because other objects depend on it ERROR: cannot drop table pktable because other objects depend on it
DETAIL: constraint constrname2 on table fktable depends on table pktable
HINT: Use DROP ... CASCADE to drop the dependent objects too. HINT: Use DROP ... CASCADE to drop the dependent objects too.
DROP TABLE PKTABLE CASCADE; DROP TABLE PKTABLE CASCADE;
NOTICE: drop cascades to constraint constrname2 on table fktable NOTICE: drop cascades to constraint constrname2 on table fktable
...@@ -1157,15 +1157,16 @@ FOREIGN KEY (x2,x4,x1) REFERENCES pktable(id1,id3,id2); ...@@ -1157,15 +1157,16 @@ FOREIGN KEY (x2,x4,x1) REFERENCES pktable(id1,id3,id2);
ERROR: foreign key constraint "fk_241_132" cannot be implemented ERROR: foreign key constraint "fk_241_132" cannot be implemented
DETAIL: Key columns "x2" and "id1" are of incompatible types: character varying and integer. DETAIL: Key columns "x2" and "id1" are of incompatible types: character varying and integer.
DROP TABLE pktable, fktable CASCADE; DROP TABLE pktable, fktable CASCADE;
NOTICE: drop cascades to constraint fktable_x3_fkey on table fktable NOTICE: drop cascades to 9 other objects
NOTICE: drop cascades to constraint fk_1_3 on table fktable DETAIL: drop cascades to constraint fktable_x3_fkey on table fktable
NOTICE: drop cascades to constraint fktable_x2_fkey on table fktable drop cascades to constraint fk_1_3 on table fktable
NOTICE: drop cascades to constraint fk_4_2 on table fktable drop cascades to constraint fktable_x2_fkey on table fktable
NOTICE: drop cascades to constraint fktable_x1_fkey on table fktable drop cascades to constraint fk_4_2 on table fktable
NOTICE: drop cascades to constraint fk_5_1 on table fktable drop cascades to constraint fktable_x1_fkey on table fktable
NOTICE: drop cascades to constraint fk_123_123 on table fktable drop cascades to constraint fk_5_1 on table fktable
NOTICE: drop cascades to constraint fk_213_213 on table fktable drop cascades to constraint fk_123_123 on table fktable
NOTICE: drop cascades to constraint fk_253_213 on table fktable drop cascades to constraint fk_213_213 on table fktable
drop cascades to constraint fk_253_213 on table fktable
-- test a tricky case: we can elide firing the FK check trigger during -- test a tricky case: we can elide firing the FK check trigger during
-- an UPDATE if the UPDATE did not change the foreign key -- an UPDATE if the UPDATE did not change the foreign key
-- field. However, we can't do this if our transaction was the one that -- field. However, we can't do this if our transaction was the one that
......
...@@ -844,9 +844,10 @@ Inherits: c1, ...@@ -844,9 +844,10 @@ Inherits: c1,
c2 c2
drop table p1 cascade; drop table p1 cascade;
NOTICE: drop cascades to table c1 NOTICE: drop cascades to 3 other objects
NOTICE: drop cascades to table c2 DETAIL: drop cascades to table c1
NOTICE: drop cascades to table c3 drop cascades to table c2
drop cascades to table c3
drop table p2 cascade; drop table p2 cascade;
create table pp1 (f1 int); create table pp1 (f1 int);
create table cc1 (f2 text, f3 int) inherits (pp1); create table cc1 (f2 text, f3 int) inherits (pp1);
...@@ -900,5 +901,6 @@ Inherits: pp1, ...@@ -900,5 +901,6 @@ Inherits: pp1,
cc1 cc1
drop table pp1 cascade; drop table pp1 cascade;
NOTICE: drop cascades to table cc1 NOTICE: drop cascades to 2 other objects
NOTICE: drop cascades to table cc2 DETAIL: drop cascades to table cc1
drop cascades to table cc2
...@@ -39,8 +39,9 @@ SELECT * FROM test_schema_1.abc_view; ...@@ -39,8 +39,9 @@ SELECT * FROM test_schema_1.abc_view;
(3 rows) (3 rows)
DROP SCHEMA test_schema_1 CASCADE; DROP SCHEMA test_schema_1 CASCADE;
NOTICE: drop cascades to table test_schema_1.abc NOTICE: drop cascades to 2 other objects
NOTICE: drop cascades to view test_schema_1.abc_view DETAIL: drop cascades to table test_schema_1.abc
drop cascades to view test_schema_1.abc_view
-- verify that the objects were dropped -- verify that the objects were dropped
SELECT COUNT(*) FROM pg_class WHERE relnamespace = SELECT COUNT(*) FROM pg_class WHERE relnamespace =
(SELECT oid FROM pg_namespace WHERE nspname = 'test_schema_1'); (SELECT oid FROM pg_namespace WHERE nspname = 'test_schema_1');
......
...@@ -148,12 +148,12 @@ CREATE TEMP TABLE t1 ( ...@@ -148,12 +148,12 @@ CREATE TEMP TABLE t1 (
NOTICE: CREATE TABLE will create implicit sequence "t1_f1_seq" for serial column "t1.f1" NOTICE: CREATE TABLE will create implicit sequence "t1_f1_seq" for serial column "t1.f1"
-- Both drops should fail, but with different error messages: -- Both drops should fail, but with different error messages:
DROP SEQUENCE t1_f1_seq; DROP SEQUENCE t1_f1_seq;
NOTICE: default for table t1 column f1 depends on sequence t1_f1_seq
ERROR: cannot drop sequence t1_f1_seq because other objects depend on it ERROR: cannot drop sequence t1_f1_seq because other objects depend on it
DETAIL: default for table t1 column f1 depends on sequence t1_f1_seq
HINT: Use DROP ... CASCADE to drop the dependent objects too. HINT: Use DROP ... CASCADE to drop the dependent objects too.
DROP SEQUENCE myseq2; DROP SEQUENCE myseq2;
NOTICE: default for table t1 column f2 depends on sequence myseq2
ERROR: cannot drop sequence myseq2 because other objects depend on it ERROR: cannot drop sequence myseq2 because other objects depend on it
DETAIL: default for table t1 column f2 depends on sequence myseq2
HINT: Use DROP ... CASCADE to drop the dependent objects too. HINT: Use DROP ... CASCADE to drop the dependent objects too.
-- This however will work: -- This however will work:
DROP SEQUENCE myseq3; DROP SEQUENCE myseq3;
......
...@@ -141,10 +141,12 @@ SELECT * FROM trunc_e; ...@@ -141,10 +141,12 @@ SELECT * FROM trunc_e;
(0 rows) (0 rows)
DROP TABLE truncate_a,trunc_c,trunc_b,trunc_d,trunc_e CASCADE; DROP TABLE truncate_a,trunc_c,trunc_b,trunc_d,trunc_e CASCADE;
NOTICE: drop cascades to constraint trunc_b_a_fkey on table trunc_b NOTICE: drop cascades to 2 other objects
NOTICE: drop cascades to constraint trunc_e_a_fkey on table trunc_e DETAIL: drop cascades to constraint trunc_b_a_fkey on table trunc_b
NOTICE: drop cascades to constraint trunc_d_a_fkey on table trunc_d drop cascades to constraint trunc_e_a_fkey on table trunc_e
NOTICE: drop cascades to constraint trunc_e_b_fkey on table trunc_e NOTICE: drop cascades to 2 other objects
DETAIL: drop cascades to constraint trunc_d_a_fkey on table trunc_d
drop cascades to constraint trunc_e_b_fkey on table trunc_e
-- Test ON TRUNCATE triggers -- Test ON TRUNCATE triggers
CREATE TABLE trunc_trigger_test (f1 int, f2 text, f3 text); CREATE TABLE trunc_trigger_test (f1 int, f2 text, f3 text);
CREATE TABLE trunc_trigger_log (tgop text, tglevel text, tgwhen text, CREATE TABLE trunc_trigger_log (tgop text, tglevel text, tgwhen text,
......
...@@ -65,9 +65,10 @@ ERROR: tablespace "nosuchspace" does not exist ...@@ -65,9 +65,10 @@ ERROR: tablespace "nosuchspace" does not exist
DROP TABLESPACE testspace; DROP TABLESPACE testspace;
ERROR: tablespace "testspace" is not empty ERROR: tablespace "testspace" is not empty
DROP SCHEMA testschema CASCADE; DROP SCHEMA testschema CASCADE;
NOTICE: drop cascades to table testschema.foo NOTICE: drop cascades to 4 other objects
NOTICE: drop cascades to table testschema.asselect DETAIL: drop cascades to table testschema.foo
NOTICE: drop cascades to table testschema.asexecute drop cascades to table testschema.asselect
NOTICE: drop cascades to table testschema.atable drop cascades to table testschema.asexecute
drop cascades to table testschema.atable
-- Should succeed -- Should succeed
DROP TABLESPACE testspace; DROP TABLESPACE testspace;
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment