1
0
mirror of https://github.com/postgres/postgres.git synced 2025-11-07 19:06:32 +03:00

Add INSERT/UPDATE/DELETE RETURNING, with basic docs and regression tests.

plpgsql support to come later.  Along the way, convert execMain's
SELECT INTO support into a DestReceiver, in order to eliminate some ugly
special cases.

Jonah Harris and Tom Lane
This commit is contained in:
Tom Lane
2006-08-12 02:52:06 +00:00
parent 5c9e9c0c42
commit 7a3e30e608
35 changed files with 1472 additions and 422 deletions

View File

@@ -15,7 +15,7 @@
*
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/optimizer/prep/prepjointree.c,v 1.40 2006/08/10 02:36:28 tgl Exp $
* $PostgreSQL: pgsql/src/backend/optimizer/prep/prepjointree.c,v 1.41 2006/08/12 02:52:05 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -372,6 +372,10 @@ pull_up_simple_subquery(PlannerInfo *root, Node *jtnode, RangeTblEntry *rte,
ResolveNew((Node *) parse->targetList,
varno, 0, rte,
subtlist, CMD_SELECT, 0);
parse->returningList = (List *)
ResolveNew((Node *) parse->returningList,
varno, 0, rte,
subtlist, CMD_SELECT, 0);
resolvenew_in_jointree((Node *) parse->jointree, varno,
rte, subtlist);
Assert(parse->setOperations == NULL);

View File

@@ -9,13 +9,14 @@
* relation in the correct order. For both UPDATE and DELETE queries,
* we need a junk targetlist entry holding the CTID attribute --- the
* executor relies on this to find the tuple to be replaced/deleted.
* We may also need junk tlist entries for Vars used in the RETURNING list.
*
*
* Portions Copyright (c) 1996-2006, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/optimizer/prep/preptlist.c,v 1.82 2006/04/30 18:30:39 tgl Exp $
* $PostgreSQL: pgsql/src/backend/optimizer/prep/preptlist.c,v 1.83 2006/08/12 02:52:05 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -27,6 +28,8 @@
#include "nodes/makefuncs.h"
#include "optimizer/prep.h"
#include "optimizer/subselect.h"
#include "optimizer/tlist.h"
#include "optimizer/var.h"
#include "parser/analyze.h"
#include "parser/parsetree.h"
#include "parser/parse_coerce.h"
@@ -151,6 +154,40 @@ preprocess_targetlist(PlannerInfo *root, List *tlist)
}
}
/*
* If the query has a RETURNING list, add resjunk entries for any Vars
* used in RETURNING that belong to other relations. We need to do this
* to make these Vars available for the RETURNING calculation. Vars
* that belong to the result rel don't need to be added, because they
* will be made to refer to the actual heap tuple.
*/
if (parse->returningList && list_length(parse->rtable) > 1)
{
List *vars;
ListCell *l;
vars = pull_var_clause((Node *) parse->returningList, false);
foreach(l, vars)
{
Var *var = (Var *) lfirst(l);
TargetEntry *tle;
if (var->varno == result_relation)
continue; /* don't need it */
if (tlist_member((Node *) var, tlist))
continue; /* already got it */
tle = makeTargetEntry((Expr *) var,
list_length(tlist) + 1,
NULL,
true);
tlist = lappend(tlist, tle);
}
list_free(vars);
}
return tlist;
}