Re: [HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-27 Thread Dean Rasheed
On 23 January 2012 20:14, Pavel Stehule pavel.steh...@gmail.com wrote:
 Hello

 2012/1/23 Robert Haas robertmh...@gmail.com:
 On Tue, Jan 3, 2012 at 2:49 PM, Pavel Stehule pavel.steh...@gmail.com 
 wrote:
 jup, we can continue in enhancing step by step.

 I change a patch and now ALTER TABLE, ALTER INDEX, ALTER SEQUENCE and
 ALTER VIEW has IF EXISTS clause

 ALTER FOREIGN TABLE should be parallel as well, I think.


 refreshed + ALTER FOREIGN TABLE IF EXISTS ... support


I just noticed this copy-and-paste error in the ALTER FOREIGN TABLE docs:

IF EXISTS:

  Do not throw an error if the sequence does not exist. A notice is issued
  in this case.

That should be foreign table not sequence.

Regards,
Dean

-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers


Re: [HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-27 Thread Heikki Linnakangas

On 27.01.2012 11:57, Dean Rasheed wrote:

I just noticed this copy-and-paste error in the ALTER FOREIGN TABLE docs:

IF EXISTS:

   Do not throw an error if the sequence does not exist. A notice is issued
   in this case.

That should be foreign table not sequence.


Thanks, fixed.

--
  Heikki Linnakangas
  EnterpriseDB   http://www.enterprisedb.com

--
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers


Re: [HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-23 Thread Simon Riggs
On Tue, Jan 3, 2012 at 7:49 PM, Pavel Stehule pavel.steh...@gmail.com wrote:

 I change a patch and now ALTER TABLE, ALTER INDEX, ALTER SEQUENCE and
 ALTER VIEW has IF EXISTS clause

Patch no longer applies. Pls update.

-- 
 Simon Riggs   http://www.2ndQuadrant.com/
 PostgreSQL Development, 24x7 Support, Training  Services

-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers


Re: [HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-23 Thread Robert Haas
On Tue, Jan 3, 2012 at 2:49 PM, Pavel Stehule pavel.steh...@gmail.com wrote:
 jup, we can continue in enhancing step by step.

 I change a patch and now ALTER TABLE, ALTER INDEX, ALTER SEQUENCE and
 ALTER VIEW has IF EXISTS clause

ALTER FOREIGN TABLE should be parallel as well, I think.

-- 
Robert Haas
EnterpriseDB: http://www.enterprisedb.com
The Enterprise PostgreSQL Company

-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers


Re: [HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-03 Thread Robert Haas
On Mon, Jan 2, 2012 at 12:01 PM, Pavel Stehule pavel.steh...@gmail.com wrote:
 here is updated patch

I think the comments in parse_utilcmd.c probably need a bit of adjustment.

-- 
Robert Haas
EnterpriseDB: http://www.enterprisedb.com
The Enterprise PostgreSQL Company

-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers


Re: [HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-03 Thread Pavel Stehule
Hello

2012/1/3 Robert Haas robertmh...@gmail.com:
 On Mon, Jan 2, 2012 at 12:01 PM, Pavel Stehule pavel.steh...@gmail.com 
 wrote:
 here is updated patch

 I think the comments in parse_utilcmd.c probably need a bit of adjustment.

I don't see it - there is only one comment and it is adjusted with
if statement.

please, show it

Regards

Pavel


 --
 Robert Haas
 EnterpriseDB: http://www.enterprisedb.com
 The Enterprise PostgreSQL Company

-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers


Re: [HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-03 Thread Robert Haas
On Tue, Jan 3, 2012 at 10:38 AM, Pavel Stehule pavel.steh...@gmail.com wrote:
 Hello

 2012/1/3 Robert Haas robertmh...@gmail.com:
 On Mon, Jan 2, 2012 at 12:01 PM, Pavel Stehule pavel.steh...@gmail.com 
 wrote:
 here is updated patch

 I think the comments in parse_utilcmd.c probably need a bit of adjustment.

 I don't see it - there is only one comment and it is adjusted with
 if statement.

 please, show it

Well, basically, the comment preceding the part you altered say the
lock level requested here, but here is getting spread out quite a
bit more with this code change.  Maybe that doesn't matter.

However, on further examination, this is a pretty awkward way to write
the code.  Why not something like this:

rel = relation_openrv_extended(stmt-relation, lockmode, stmt-missing_ok);
if (rel == NULL)
{
ereport(...);
return NIL;
}

Maybe the intent of sticking heap_openrv_extended() into the upper
branch of the if statement is to try to bounce relations that aren't
tables, but that's not actually what that function does (e.g. a
foreign table will slip through).  And I think if we're going to have
IF EXISTS support for ALTER TABLE at all, we ought to have it for the
whole family of related statements: ALTER VIEW, ALTER SEQUENCE, ALTER
FOREIGN TABLE, etc., not just ALTER TABLE itself.

-- 
Robert Haas
EnterpriseDB: http://www.enterprisedb.com
The Enterprise PostgreSQL Company

-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers


Re: [HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-03 Thread Pavel Stehule
Hello

2012/1/3 Robert Haas robertmh...@gmail.com:
 On Tue, Jan 3, 2012 at 10:38 AM, Pavel Stehule pavel.steh...@gmail.com 
 wrote:
 Hello

 2012/1/3 Robert Haas robertmh...@gmail.com:
 On Mon, Jan 2, 2012 at 12:01 PM, Pavel Stehule pavel.steh...@gmail.com 
 wrote:
 here is updated patch

 I think the comments in parse_utilcmd.c probably need a bit of adjustment.

 I don't see it - there is only one comment and it is adjusted with
 if statement.

 please, show it

 Well, basically, the comment preceding the part you altered say the
 lock level requested here, but here is getting spread out quite a
 bit more with this code change.  Maybe that doesn't matter.

 However, on further examination, this is a pretty awkward way to write
 the code.  Why not something like this:

 rel = relation_openrv_extended(stmt-relation, lockmode, stmt-missing_ok);
 if (rel == NULL)
 {
    ereport(...);
    return NIL;
 }

 Maybe the intent of sticking heap_openrv_extended() into the upper
 branch of the if statement is to try to bounce relations that aren't
 tables, but that's not actually what that function does (e.g. a
 foreign table will slip through).  And I think if we're going to have
 IF EXISTS support for ALTER TABLE at all, we ought to have it for the
 whole family of related statements: ALTER VIEW, ALTER SEQUENCE, ALTER
 FOREIGN TABLE, etc., not just ALTER TABLE itself.


jup, we can continue in enhancing step by step.

I change a patch and now ALTER TABLE, ALTER INDEX, ALTER SEQUENCE and
ALTER VIEW has IF EXISTS clause

Regards

Pavel


 --
 Robert Haas
 EnterpriseDB: http://www.enterprisedb.com
 The Enterprise PostgreSQL Company
*** ./doc/src/sgml/ref/alter_index.sgml.orig	2012-01-02 17:01:00.0 +0100
--- ./doc/src/sgml/ref/alter_index.sgml	2012-01-03 19:45:24.210189185 +0100
***
*** 21,30 
  
   refsynopsisdiv
  synopsis
! ALTER INDEX replaceable class=PARAMETERname/replaceable RENAME TO replaceable class=PARAMETERnew_name/replaceable
! ALTER INDEX replaceable class=PARAMETERname/replaceable SET TABLESPACE replaceable class=PARAMETERtablespace_name/replaceable
! ALTER INDEX replaceable class=PARAMETERname/replaceable SET ( replaceable class=PARAMETERstorage_parameter/replaceable = replaceable class=PARAMETERvalue/replaceable [, ... ] )
! ALTER INDEX replaceable class=PARAMETERname/replaceable RESET ( replaceable class=PARAMETERstorage_parameter/replaceable [, ... ] )
  /synopsis
   /refsynopsisdiv
  
--- 21,30 
  
   refsynopsisdiv
  synopsis
! ALTER INDEX [ IF EXISTS ] replaceable class=PARAMETERname/replaceable RENAME TO replaceable class=PARAMETERnew_name/replaceable
! ALTER INDEX [ IF EXISTS ] replaceable class=PARAMETERname/replaceable SET TABLESPACE replaceable class=PARAMETERtablespace_name/replaceable
! ALTER INDEX [ IF EXISTS ] replaceable class=PARAMETERname/replaceable SET ( replaceable class=PARAMETERstorage_parameter/replaceable = replaceable class=PARAMETERvalue/replaceable [, ... ] )
! ALTER INDEX [ IF EXISTS ] replaceable class=PARAMETERname/replaceable RESET ( replaceable class=PARAMETERstorage_parameter/replaceable [, ... ] )
  /synopsis
   /refsynopsisdiv
  
***
*** 38,43 
--- 38,53 
variablelist
  
 varlistentry
+ termliteralIF EXISTS/literal/term
+ listitem
+  para
+   Do not throw an error if the index does not exist. A notice is issued
+   in this case.
+  /para
+ /listitem
+/varlistentry
+ 
+varlistentry
  termliteralRENAME/literal/term
  listitem
   para
*** ./doc/src/sgml/ref/alter_sequence.sgml.orig	2012-01-02 17:01:00.0 +0100
--- ./doc/src/sgml/ref/alter_sequence.sgml	2012-01-03 18:44:14.397429013 +0100
***
*** 23,37 
  
   refsynopsisdiv
  synopsis
! ALTER SEQUENCE replaceable class=parametername/replaceable [ INCREMENT [ BY ] replaceable class=parameterincrement/replaceable ]
  [ MINVALUE replaceable class=parameterminvalue/replaceable | NO MINVALUE ] [ MAXVALUE replaceable class=parametermaxvalue/replaceable | NO MAXVALUE ]
  [ START [ WITH ] replaceable class=parameterstart/replaceable ]
  [ RESTART [ [ WITH ] replaceable class=parameterrestart/replaceable ] ]
  [ CACHE replaceable class=parametercache/replaceable ] [ [ NO ] CYCLE ]
  [ OWNED BY { replaceable class=parametertable/replaceable.replaceable class=parametercolumn/replaceable | NONE } ]
! ALTER SEQUENCE replaceable class=parametername/replaceable OWNER TO replaceable class=PARAMETERnew_owner/replaceable
! ALTER SEQUENCE replaceable class=parametername/replaceable RENAME TO replaceable class=parameternew_name/replaceable
! ALTER SEQUENCE replaceable class=parametername/replaceable SET SCHEMA replaceable class=parameternew_schema/replaceable
  /synopsis
   /refsynopsisdiv
  
--- 23,37 
  
   refsynopsisdiv
  synopsis
! ALTER SEQUENCE [ IF EXISTS ] replaceable class=parametername/replaceable [ INCREMENT [ BY ] replaceable class=parameterincrement/replaceable ]
  [ 

[HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-02 Thread Pavel Stehule
Hello

this is relative simple patch that add possibility to skip noexisting
tables. It is necessary for silent cleaning when dump is loaded.

Regards

Pavel Stehule
*** ./doc/src/sgml/ref/alter_table.sgml.orig	2011-12-01 22:47:20.0 +0100
--- ./doc/src/sgml/ref/alter_table.sgml	2012-01-02 13:59:16.390363069 +0100
***
*** 21,33 
  
   refsynopsisdiv
  synopsis
! ALTER TABLE [ ONLY ] replaceable class=PARAMETERname/replaceable [ * ]
  replaceable class=PARAMETERaction/replaceable [, ... ]
! ALTER TABLE [ ONLY ] replaceable class=PARAMETERname/replaceable [ * ]
  RENAME [ COLUMN ] replaceable class=PARAMETERcolumn/replaceable TO replaceable class=PARAMETERnew_column/replaceable
! ALTER TABLE replaceable class=PARAMETERname/replaceable
  RENAME TO replaceable class=PARAMETERnew_name/replaceable
! ALTER TABLE replaceable class=PARAMETERname/replaceable
  SET SCHEMA replaceable class=PARAMETERnew_schema/replaceable
  
  phrasewhere replaceable class=PARAMETERaction/replaceable is one of:/phrase
--- 21,33 
  
   refsynopsisdiv
  synopsis
! ALTER TABLE [ IF EXISTS ] [ ONLY ] replaceable class=PARAMETERname/replaceable [ * ]
  replaceable class=PARAMETERaction/replaceable [, ... ]
! ALTER TABLE [ IF EXISTS ] [ ONLY ] replaceable class=PARAMETERname/replaceable [ * ]
  RENAME [ COLUMN ] replaceable class=PARAMETERcolumn/replaceable TO replaceable class=PARAMETERnew_column/replaceable
! ALTER TABLE [ IF EXISTS ] replaceable class=PARAMETERname/replaceable
  RENAME TO replaceable class=PARAMETERnew_name/replaceable
! ALTER TABLE [ IF EXISTS ] replaceable class=PARAMETERname/replaceable
  SET SCHEMA replaceable class=PARAMETERnew_schema/replaceable
  
  phrasewhere replaceable class=PARAMETERaction/replaceable is one of:/phrase
*** ./src/backend/nodes/copyfuncs.c.orig	2011-12-01 22:47:20.0 +0100
--- ./src/backend/nodes/copyfuncs.c	2012-01-02 11:16:05.521002912 +0100
***
*** 2517,2522 
--- 2517,2523 
  	COPY_NODE_FIELD(relation);
  	COPY_NODE_FIELD(cmds);
  	COPY_SCALAR_FIELD(relkind);
+ 	COPY_SCALAR_FIELD(missing_ok);
  
  	return newnode;
  }
*** ./src/backend/nodes/equalfuncs.c.orig	2011-12-01 22:47:20.0 +0100
--- ./src/backend/nodes/equalfuncs.c	2012-01-02 11:16:33.871001059 +0100
***
*** 1009,1014 
--- 1009,1015 
  	COMPARE_NODE_FIELD(relation);
  	COMPARE_NODE_FIELD(cmds);
  	COMPARE_SCALAR_FIELD(relkind);
+ 	COMPARE_SCALAR_FIELD(missing_ok);
  
  	return true;
  }
*** ./src/backend/parser/gram.y.orig	2011-12-01 22:47:20.0 +0100
--- ./src/backend/parser/gram.y	2012-01-02 13:53:13.001386815 +0100
***
*** 1621,1626 
--- 1621,1636 
  	n-relation = $3;
  	n-cmds = $4;
  	n-relkind = OBJECT_TABLE;
+ 	n-missing_ok = false;
+ 	$$ = (Node *)n;
+ }
+ 		 |	ALTER TABLE IF_P EXISTS relation_expr alter_table_cmds
+ {
+ 	AlterTableStmt *n = makeNode(AlterTableStmt);
+ 	n-relation = $5;
+ 	n-cmds = $6;
+ 	n-relkind = OBJECT_TABLE;
+ 	n-missing_ok = true;
  	$$ = (Node *)n;
  }
  		|	ALTER INDEX qualified_name alter_table_cmds
***
*** 1629,1634 
--- 1639,1645 
  	n-relation = $3;
  	n-cmds = $4;
  	n-relkind = OBJECT_INDEX;
+ 	n-missing_ok = false;
  	$$ = (Node *)n;
  }
  		|	ALTER SEQUENCE qualified_name alter_table_cmds
***
*** 1637,1642 
--- 1648,1654 
  	n-relation = $3;
  	n-cmds = $4;
  	n-relkind = OBJECT_SEQUENCE;
+ 	n-missing_ok = false;
  	$$ = (Node *)n;
  }
  		|	ALTER VIEW qualified_name alter_table_cmds
***
*** 1645,1650 
--- 1657,1663 
  	n-relation = $3;
  	n-cmds = $4;
  	n-relkind = OBJECT_VIEW;
+ 	n-missing_ok = false;
  	$$ = (Node *)n;
  }
  		;
*** ./src/backend/parser/parse_utilcmd.c.orig	2011-12-01 22:47:20.0 +0100
--- ./src/backend/parser/parse_utilcmd.c	2012-01-02 13:47:11.937410429 +0100
***
*** 2256,2262 
  	 * new commands we add after this must not upgrade the lock level
  	 * requested here.
  	 */
! 	rel = relation_openrv(stmt-relation, lockmode);
  
  	/* Set up pstate and CreateStmtContext */
  	pstate = make_parsestate(NULL);
--- 2256,2278 
  	 * new commands we add after this must not upgrade the lock level
  	 * requested here.
  	 */
! 
! 	if (stmt-missing_ok)
! 	{
! 		rel = try_relation_openrv(stmt-relation, lockmode);
! 
! 		/* leave when relation doesn't exists */
! 		if (rel == NULL)
! 		{
! 			ereport(NOTICE,
! 	(errcode(ERRCODE_DUPLICATE_TABLE),
! 	 errmsg(table \%s\ does not exists, skipping,
! 			stmt-relation-relname)));
! 			return NIL;
! 		}
! 	}
! 	else
! 		rel = relation_openrv(stmt-relation, lockmode);
  
  	/* Set up pstate and CreateStmtContext */
  	pstate = make_parsestate(NULL);
*** ./src/include/nodes/parsenodes.h.orig	2011-12-01 22:47:20.0 +0100
--- ./src/include/nodes/parsenodes.h	2012-01-02 

Re: [HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-02 Thread Simon Riggs
On Mon, Jan 2, 2012 at 1:11 PM, Pavel Stehule pavel.steh...@gmail.com wrote:

 this is relative simple patch that add possibility to skip noexisting
 tables. It is necessary for silent cleaning when dump is loaded.

Agreed, nice simple and uncontentious patch.

All good apart from two minor things:

* doc page needs to explain what IF EXISTS does, like DROP TABLE, e.g.

IF EXISTS
Do not throw an error if the table does not exist. A notice is
issued in this case.

* the error message is does not exist rather than does not exists,
which means the code, a comment and a test need changing

Other than that, happy to apply as soon as you make those changes.

-- 
 Simon Riggs   http://www.2ndQuadrant.com/
 PostgreSQL Development, 24x7 Support, Training  Services

-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers


Re: [HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-02 Thread Tomas Vondra
On 2 Leden 2012, 14:11, Pavel Stehule wrote:
 Hello

 this is relative simple patch that add possibility to skip noexisting
 tables. It is necessary for silent cleaning when dump is loaded.

Just a curious question - what use case is solved by this? Under what
circumstances you get an ALTER TABLE without a preceding CREATE TABLE? I
can't think of such scenario ...

Or is this meant for scripts written manually so that it's possible to do
alter if the table already exists and create if it does not exist?

Tomas


-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers


Re: [HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-02 Thread Pavel Stehule
Hello

2012/1/2 Tomas Vondra t...@fuzzy.cz:
 On 2 Leden 2012, 14:11, Pavel Stehule wrote:
 Hello

 this is relative simple patch that add possibility to skip noexisting
 tables. It is necessary for silent cleaning when dump is loaded.

 Just a curious question - what use case is solved by this? Under what
 circumstances you get an ALTER TABLE without a preceding CREATE TABLE? I
 can't think of such scenario ...

 Or is this meant for scripts written manually so that it's possible to do
 alter if the table already exists and create if it does not exist?

this is necessary for silent cleaning in pg_dump

this is fragment of dump with -c option

ALTER TABLE ONLY public.b DROP CONSTRAINT b_b_fkey;
DROP INDEX public.a_a_idx;
ALTER TABLE ONLY public.a DROP CONSTRAINT a_pkey;
DROP TABLE public.b;
DROP TABLE public.a;
DROP EXTENSION plpgsql;
DROP SCHEMA public;

I am working on silent cleaning and I am able generate a sequence of
statements:

ALTER TABLE IF EXISTS ONLY public.b DROP CONSTRAINT b_b_fkey;
DROP INDEX IF EXISTS public.a_a_idx;
ALTER TABLE IF EXISTS ONLY public.a DROP CONSTRAINT a_pkey;
DROP TABLE IF EXISTS public.b;
DROP TABLE IF EXISTS public.a;
DROP EXTENSION IF EXISTS plpgsql;
DROP SCHEMA IF EXISTS public;

constraint  b_b_fkey should be removed before dropping index a_a_idx

Now we have DROP .. IF EXISTS statements, but  ALTER TABLE .. IF EXISTS missing

Regards

Pavel

 Tomas


-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers


Re: [HACKERS] patch: ALTER TABLE IF EXISTS

2012-01-02 Thread Pavel Stehule
Hello

here is updated patch

Regards

Pavel


2012/1/2 Simon Riggs si...@2ndquadrant.com:
 On Mon, Jan 2, 2012 at 1:11 PM, Pavel Stehule pavel.steh...@gmail.com wrote:

 this is relative simple patch that add possibility to skip noexisting
 tables. It is necessary for silent cleaning when dump is loaded.

 Agreed, nice simple and uncontentious patch.

 All good apart from two minor things:

 * doc page needs to explain what IF EXISTS does, like DROP TABLE, e.g.

 IF EXISTS
    Do not throw an error if the table does not exist. A notice is
 issued in this case.

 * the error message is does not exist rather than does not exists,
 which means the code, a comment and a test need changing

 Other than that, happy to apply as soon as you make those changes.

 --
  Simon Riggs   http://www.2ndQuadrant.com/
  PostgreSQL Development, 24x7 Support, Training  Services
*** ./doc/src/sgml/ref/alter_table.sgml.orig	2012-01-02 17:04:00.295638725 +0100
--- ./doc/src/sgml/ref/alter_table.sgml	2012-01-02 17:52:24.153449002 +0100
***
*** 21,33 
  
   refsynopsisdiv
  synopsis
! ALTER TABLE [ ONLY ] replaceable class=PARAMETERname/replaceable [ * ]
  replaceable class=PARAMETERaction/replaceable [, ... ]
! ALTER TABLE [ ONLY ] replaceable class=PARAMETERname/replaceable [ * ]
  RENAME [ COLUMN ] replaceable class=PARAMETERcolumn/replaceable TO replaceable class=PARAMETERnew_column/replaceable
! ALTER TABLE replaceable class=PARAMETERname/replaceable
  RENAME TO replaceable class=PARAMETERnew_name/replaceable
! ALTER TABLE replaceable class=PARAMETERname/replaceable
  SET SCHEMA replaceable class=PARAMETERnew_schema/replaceable
  
  phrasewhere replaceable class=PARAMETERaction/replaceable is one of:/phrase
--- 21,33 
  
   refsynopsisdiv
  synopsis
! ALTER TABLE [ IF EXISTS ] [ ONLY ] replaceable class=PARAMETERname/replaceable [ * ]
  replaceable class=PARAMETERaction/replaceable [, ... ]
! ALTER TABLE [ IF EXISTS ] [ ONLY ] replaceable class=PARAMETERname/replaceable [ * ]
  RENAME [ COLUMN ] replaceable class=PARAMETERcolumn/replaceable TO replaceable class=PARAMETERnew_column/replaceable
! ALTER TABLE [ IF EXISTS ] replaceable class=PARAMETERname/replaceable
  RENAME TO replaceable class=PARAMETERnew_name/replaceable
! ALTER TABLE [ IF EXISTS ] replaceable class=PARAMETERname/replaceable
  SET SCHEMA replaceable class=PARAMETERnew_schema/replaceable
  
  phrasewhere replaceable class=PARAMETERaction/replaceable is one of:/phrase
***
*** 110,115 
--- 110,125 
 /varlistentry
  
 varlistentry
+ termliteralIF EXISTS/literal/term
+ listitem
+  para
+   Do not throw an error if the table does not exist. A notice is issued
+   in this case.
+  /para
+ /listitem
+/varlistentry
+ 
+varlistentry
  termliteralSET DATA TYPE/literal/term
  listitem
   para
*** ./src/backend/nodes/copyfuncs.c.orig	2012-01-02 17:01:00.373650482 +0100
--- ./src/backend/nodes/copyfuncs.c	2012-01-02 17:04:12.472637933 +0100
***
*** 2540,2545 
--- 2540,2546 
  	COPY_NODE_FIELD(relation);
  	COPY_NODE_FIELD(cmds);
  	COPY_SCALAR_FIELD(relkind);
+ 	COPY_SCALAR_FIELD(missing_ok);
  
  	return newnode;
  }
*** ./src/backend/nodes/equalfuncs.c.orig	2012-01-02 17:01:00.374650482 +0100
--- ./src/backend/nodes/equalfuncs.c	2012-01-02 17:04:12.474637924 +0100
***
*** 1010,1015 
--- 1010,1016 
  	COMPARE_NODE_FIELD(relation);
  	COMPARE_NODE_FIELD(cmds);
  	COMPARE_SCALAR_FIELD(relkind);
+ 	COMPARE_SCALAR_FIELD(missing_ok);
  
  	return true;
  }
*** ./src/backend/parser/gram.y.orig	2012-01-02 17:01:00.391650482 +0100
--- ./src/backend/parser/gram.y	2012-01-02 17:04:12.517637925 +0100
***
*** 1629,1634 
--- 1629,1644 
  	n-relation = $3;
  	n-cmds = $4;
  	n-relkind = OBJECT_TABLE;
+ 	n-missing_ok = false;
+ 	$$ = (Node *)n;
+ }
+ 		 |	ALTER TABLE IF_P EXISTS relation_expr alter_table_cmds
+ {
+ 	AlterTableStmt *n = makeNode(AlterTableStmt);
+ 	n-relation = $5;
+ 	n-cmds = $6;
+ 	n-relkind = OBJECT_TABLE;
+ 	n-missing_ok = true;
  	$$ = (Node *)n;
  }
  		|	ALTER INDEX qualified_name alter_table_cmds
***
*** 1637,1642 
--- 1647,1653 
  	n-relation = $3;
  	n-cmds = $4;
  	n-relkind = OBJECT_INDEX;
+ 	n-missing_ok = false;
  	$$ = (Node *)n;
  }
  		|	ALTER SEQUENCE qualified_name alter_table_cmds
***
*** 1645,1650 
--- 1656,1662 
  	n-relation = $3;
  	n-cmds = $4;
  	n-relkind = OBJECT_SEQUENCE;
+ 	n-missing_ok = false;
  	$$ = (Node *)n;
  }
  		|	ALTER VIEW qualified_name alter_table_cmds
***
*** 1653,1658 
--- 1665,1671 
  	n-relation = $3;
  	n-cmds = $4;
  	n-relkind = OBJECT_VIEW;
+ 	n-missing_ok = false;
  	$$ = (Node *)n;
  }
  		;
***