Skip to content

Commit 5e7c0a0

Browse files
committed
From: Darren King <aixssd!darrenk@abs.net>
Subject: [PATCHES] DROP AGGREGATE patch/fix. Here's a patch that fixes the DROP AGGREGATE command to delete the desired aggregate for a specific type.
1 parent 021ccf0 commit 5e7c0a0

File tree

13 files changed

+202
-49
lines changed

13 files changed

+202
-49
lines changed

src/backend/commands/remove.c

Lines changed: 67 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
*
88
*
99
* IDENTIFICATION
10-
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/remove.c,v 1.7 1996/11/30 18:06:10 momjian Exp $
10+
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/remove.c,v 1.8 1997/05/22 00:14:32 scrappy Exp $
1111
*
1212
*-------------------------------------------------------------------------
1313
*/
@@ -403,27 +403,78 @@ RemoveFunction(char *functionName, /* function name to be removed */
403403
}
404404

405405
void
406-
RemoveAggregate(char *aggName)
406+
RemoveAggregate(char *aggName, char *aggType)
407407
{
408-
Relation relation;
409-
HeapScanDesc scan;
410-
HeapTuple tup;
411-
ItemPointerData itemPointerData;
412-
static ScanKeyData key[3] = {
413-
{ 0, Anum_pg_aggregate_aggname, NameEqualRegProcedure }
414-
};
408+
Relation relation;
409+
HeapScanDesc scan;
410+
HeapTuple tup;
411+
ItemPointerData itemPointerData;
412+
char *userName;
413+
char *typename;
414+
Oid basetypeID = InvalidOid;
415+
bool defined;
416+
ScanKeyData aggregateKey[3];
417+
418+
419+
/*
420+
* if a basetype is passed in, then attempt to find an aggregate for that
421+
* specific type.
422+
*
423+
* else if the basetype is blank, then attempt to find an aggregate with a
424+
* basetype of zero. This is valid. It means that the aggregate is to apply
425+
* to all basetypes. ie, a counter of some sort.
426+
*
427+
*/
428+
429+
if (aggType) {
430+
basetypeID = TypeGet(aggType, &defined);
431+
if (!OidIsValid(basetypeID)) {
432+
elog(WARN, "RemoveAggregate: type '%s' does not exist", aggType);
433+
}
434+
} else {
435+
basetypeID = 0;
436+
}
437+
438+
/*
439+
#ifndef NO_SECURITY
440+
*/
441+
userName = GetPgUserName();
442+
if (!pg_aggr_ownercheck(userName, aggName, basetypeID)) {
443+
if (aggType) {
444+
elog(WARN, "RemoveAggregate: aggregate '%s' on type '%s': permission denied",
445+
aggName, aggType);
446+
} else {
447+
elog(WARN, "RemoveAggregate: aggregate '%s': permission denied",
448+
aggName);
449+
}
450+
}
451+
/*
452+
#endif
453+
*/
454+
455+
ScanKeyEntryInitialize(&aggregateKey[0], 0x0,
456+
Anum_pg_aggregate_aggname,
457+
NameEqualRegProcedure,
458+
PointerGetDatum(aggName));
415459

416-
key[0].sk_argument = PointerGetDatum(aggName);
460+
ScanKeyEntryInitialize(&aggregateKey[1], 0x0,
461+
Anum_pg_aggregate_aggbasetype,
462+
ObjectIdEqualRegProcedure,
463+
ObjectIdGetDatum(basetypeID));
417464

418-
fmgr_info(key[0].sk_procedure, &key[0].sk_func, &key[0].sk_nargs);
419465
relation = heap_openr(AggregateRelationName);
420-
scan = heap_beginscan(relation, 0, NowTimeQual, 1, key);
466+
scan = heap_beginscan(relation, 0, NowTimeQual, 2, aggregateKey);
421467
tup = heap_getnext(scan, 0, (Buffer *) 0);
422468
if (!HeapTupleIsValid(tup)) {
423-
heap_endscan(scan);
424-
heap_close(relation);
425-
elog(WARN, "RemoveAggregate: aggregate '%s' does not exist",
426-
aggName);
469+
heap_endscan(scan);
470+
heap_close(relation);
471+
if (aggType) {
472+
elog(WARN, "RemoveAggregate: aggregate '%s' for '%s' does not exist",
473+
aggName, aggType);
474+
} else {
475+
elog(WARN, "RemoveAggregate: aggregate '%s' for all types does not exist",
476+
aggName);
477+
}
427478
}
428479
ItemPointerCopy(&tup->t_ctid, &itemPointerData);
429480
heap_delete(relation, &itemPointerData);

src/backend/parser/catalog_utils.c

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
*
77
*
88
* IDENTIFICATION
9-
* $Header: /cvsroot/pgsql/src/backend/parser/Attic/catalog_utils.c,v 1.17 1997/03/02 01:03:00 momjian Exp $
9+
* $Header: /cvsroot/pgsql/src/backend/parser/Attic/catalog_utils.c,v 1.18 1997/05/22 00:14:41 scrappy Exp $
1010
*
1111
*-------------------------------------------------------------------------
1212
*/
@@ -1499,3 +1499,19 @@ func_error(char *caller, char *funcname, int nargs, Oid *argtypes)
14991499
elog(WARN, "%s: function %s(%s) does not exist", caller, funcname, p);
15001500
}
15011501

1502+
/*
1503+
* Error message when aggregate lookup fails that gives details of the
1504+
* basetype
1505+
*/
1506+
void
1507+
agg_error(char *caller, char *aggname, Oid basetypeID)
1508+
{
1509+
/* basetypeID that is Invalid (zero) means aggregate over all types. (count) */
1510+
1511+
if (basetypeID == InvalidOid) {
1512+
elog(WARN, "%s: aggregate '%s' for all types does not exist", caller, aggname);
1513+
} else {
1514+
elog(WARN, "%s: aggregate '%s' for '%s' does not exist", caller, aggname,
1515+
tname(get_id_type(basetypeID)));
1516+
}
1517+
}

src/backend/parser/gram.y

Lines changed: 25 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010
*
1111
*
1212
* IDENTIFICATION
13-
* $Header: /cvsroot/pgsql/src/backend/parser/gram.y,v 1.32 1997/04/23 06:04:42 vadim Exp $
13+
* $Header: /cvsroot/pgsql/src/backend/parser/gram.y,v 1.33 1997/05/22 00:14:52 scrappy Exp $
1414
*
1515
* HISTORY
1616
* AUTHOR DATE MAJOR EVENT
@@ -104,16 +104,16 @@ static Node *makeA_Expr(int oper, char *opname, Node *lexpr, Node *rexpr);
104104
ExtendStmt, FetchStmt, GrantStmt,
105105
IndexStmt, MoveStmt, ListenStmt, OptimizableStmt,
106106
ProcedureStmt, PurgeStmt,
107-
RecipeStmt, RemoveOperStmt, RemoveFuncStmt, RemoveStmt, RenameStmt,
108-
RevokeStmt, RuleStmt, TransactionStmt, ViewStmt, LoadStmt,
107+
RecipeStmt, RemoveAggrStmt, RemoveOperStmt, RemoveFuncStmt, RemoveStmt,
108+
RenameStmt, RevokeStmt, RuleStmt, TransactionStmt, ViewStmt, LoadStmt,
109109
CreatedbStmt, DestroydbStmt, VacuumStmt, RetrieveStmt, CursorStmt,
110110
ReplaceStmt, AppendStmt, NotifyStmt, DeleteStmt, ClusterStmt,
111111
ExplainStmt, VariableSetStmt, VariableShowStmt, VariableResetStmt
112112

113113
%type <str> relation_name, copy_file_name, copy_delimiter, def_name,
114114
database_name, access_method_clause, access_method, attr_name,
115115
class, index_name, name, file_name, recipe_name,
116-
var_name
116+
var_name, aggr_argtype
117117

118118
%type <str> opt_id, opt_portal_name,
119119
before_clause, after_clause, all_Op, MathOp, opt_name, opt_unique,
@@ -126,7 +126,7 @@ static Node *makeA_Expr(int oper, char *opname, Node *lexpr, Node *rexpr);
126126
%type <list> stmtblock, stmtmulti,
127127
relation_name_list, OptTableElementList,
128128
tableElementList, OptInherit, definition,
129-
opt_with, def_args, def_name_list, func_argtypes,
129+
opt_with, def_args, def_name_list, func_argtypes
130130
oper_argtypes, OptStmtList, OptStmtBlock, OptStmtMulti,
131131
opt_column_list, columnList, opt_va_list, va_list,
132132
sort_clause, sortby_list, index_params, index_list,
@@ -262,6 +262,7 @@ stmt : AddAttrStmt
262262
| ProcedureStmt
263263
| PurgeStmt
264264
| RecipeStmt
265+
| RemoveAggrStmt
265266
| RemoveOperStmt
266267
| RemoveFuncStmt
267268
| RemoveStmt
@@ -921,6 +922,8 @@ after_clause: AFTER date { $$ = $2; }
921922
*
922923
* remove function <funcname>
923924
* (REMOVE FUNCTION "funcname" (arg1, arg2, ...))
925+
* remove aggregate <aggname>
926+
* (REMOVE AGGREGATE "aggname" "aggtype")
924927
* remove operator <opname>
925928
* (REMOVE OPERATOR "opname" (leftoperand_typ rightoperand_typ))
926929
* remove type <typename>
@@ -939,13 +942,25 @@ RemoveStmt: DROP remove_type name
939942
}
940943
;
941944

942-
remove_type: AGGREGATE { $$ = AGGREGATE; }
943-
| Type { $$ = P_TYPE; }
944-
| INDEX { $$ = INDEX; }
945-
| RULE { $$ = RULE; }
946-
| VIEW { $$ = VIEW; }
945+
remove_type: Type { $$ = P_TYPE; }
946+
| INDEX { $$ = INDEX; }
947+
| RULE { $$ = RULE; }
948+
| VIEW { $$ = VIEW; }
947949
;
948950

951+
RemoveAggrStmt: DROP AGGREGATE name aggr_argtype
952+
{
953+
RemoveAggrStmt *n = makeNode(RemoveAggrStmt);
954+
n->aggname = $3;
955+
n->aggtype = $4;
956+
$$ = (Node *)n;
957+
}
958+
;
959+
960+
aggr_argtype: name { $$ = $1; }
961+
| '*' { $$ = NULL; }
962+
;
963+
949964
RemoveFuncStmt: DROP FUNCTION name '(' func_argtypes ')'
950965
{
951966
RemoveFuncStmt *n = makeNode(RemoveFuncStmt);

src/backend/tcop/aclchk.c

Lines changed: 42 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
*
88
*
99
* IDENTIFICATION
10-
* $Header: /cvsroot/pgsql/src/backend/tcop/Attic/aclchk.c,v 1.9 1997/04/03 21:31:47 scrappy Exp $
10+
* $Header: /cvsroot/pgsql/src/backend/tcop/Attic/aclchk.c,v 1.10 1997/05/22 00:15:21 scrappy Exp $
1111
*
1212
* NOTES
1313
* See acl.h.
@@ -29,6 +29,7 @@
2929
#include "catalog/catname.h"
3030
#include "catalog/pg_group.h"
3131
#include "catalog/pg_operator.h"
32+
#include "catalog/pg_aggregate.h"
3233
#include "catalog/pg_proc.h"
3334
#include "catalog/pg_user.h"
3435
#include "utils/syscache.h"
@@ -561,3 +562,43 @@ pg_func_ownercheck(char *usename,
561562

562563
return(user_id == owner_id);
563564
}
565+
566+
int32
567+
pg_aggr_ownercheck(char *usename,
568+
char *aggname,
569+
Oid basetypeID)
570+
{
571+
HeapTuple htp;
572+
AclId user_id, owner_id;
573+
574+
htp = SearchSysCacheTuple(USENAME, PointerGetDatum(usename),
575+
0,0,0);
576+
if (!HeapTupleIsValid(htp))
577+
elog(WARN, "pg_aggr_ownercheck: user \"%-.*s\" not found",
578+
NAMEDATALEN, usename);
579+
user_id = (AclId) ((Form_pg_user) GETSTRUCT(htp))->usesysid;
580+
581+
/*
582+
* Superusers bypass all permission-checking.
583+
*/
584+
if (((Form_pg_user) GETSTRUCT(htp))->usesuper) {
585+
#ifdef ACLDEBUG_TRACE
586+
elog(DEBUG, "pg_aggr_ownercheck: user \"%-.*s\" is superuser",
587+
NAMEDATALEN, usename);
588+
#endif
589+
return(1);
590+
}
591+
592+
htp = SearchSysCacheTuple(AGGNAME,
593+
PointerGetDatum(aggname),
594+
PointerGetDatum(basetypeID),
595+
0,
596+
0);
597+
598+
if (!HeapTupleIsValid(htp))
599+
agg_error("pg_aggr_ownercheck", aggname, basetypeID);
600+
601+
owner_id = ((Form_pg_aggregate) GETSTRUCT(htp))->aggowner;
602+
603+
return(user_id == owner_id);
604+
}

src/backend/tcop/utility.c

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99
*
1010
*
1111
* IDENTIFICATION
12-
* $Header: /cvsroot/pgsql/src/backend/tcop/utility.c,v 1.16 1997/04/23 06:09:33 vadim Exp $
12+
* $Header: /cvsroot/pgsql/src/backend/tcop/utility.c,v 1.17 1997/05/22 00:15:36 scrappy Exp $
1313
*
1414
*-------------------------------------------------------------------------
1515
*/
@@ -440,9 +440,6 @@ ProcessUtility(Node *parsetree,
440440
CHECK_IF_ABORTED();
441441

442442
switch(stmt->removeType) {
443-
case AGGREGATE:
444-
RemoveAggregate(stmt->name);
445-
break;
446443
case INDEX:
447444
relname = stmt->name;
448445
if (IsSystemRelationName(relname))
@@ -496,6 +493,16 @@ ProcessUtility(Node *parsetree,
496493
break;
497494
}
498495
break;
496+
497+
case T_RemoveAggrStmt:
498+
{
499+
RemoveAggrStmt *stmt = (RemoveAggrStmt *)parsetree;
500+
commandTag = "DROP";
501+
CHECK_IF_ABORTED();
502+
RemoveAggregate(stmt->aggname, stmt->aggtype);
503+
}
504+
break;
505+
499506
case T_RemoveFuncStmt:
500507
{
501508
RemoveFuncStmt *stmt = (RemoveFuncStmt *)parsetree;

src/include/commands/defrem.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
*
77
* Copyright (c) 1994, Regents of the University of California
88
*
9-
* $Id: defrem.h,v 1.6 1996/11/13 20:51:18 scrappy Exp $
9+
* $Id: defrem.h,v 1.7 1997/05/22 00:15:47 scrappy Exp $
1010
*
1111
*-------------------------------------------------------------------------
1212
*/
@@ -48,6 +48,6 @@ extern void RemoveFunction(char *functionName, int nargs, List *argNameList);
4848
extern void RemoveOperator(char *operatorName,
4949
char *typeName1, char *typeName2);
5050
extern void RemoveType(char *typeName);
51-
extern void RemoveAggregate(char *aggName);
51+
extern void RemoveAggregate(char *aggName, char *aggType);
5252

5353
#endif /* DEFREM_H */

src/include/nodes/nodes.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
*
77
* Copyright (c) 1994, Regents of the University of California
88
*
9-
* $Id: nodes.h,v 1.8 1997/04/23 03:17:29 scrappy Exp $
9+
* $Id: nodes.h,v 1.9 1997/05/22 00:15:58 scrappy Exp $
1010
*
1111
*-------------------------------------------------------------------------
1212
*/
@@ -164,6 +164,7 @@ typedef enum NodeTag {
164164
T_ProcedureStmt,
165165
T_PurgeStmt,
166166
T_RecipeStmt,
167+
T_RemoveAggrStmt,
167168
T_RemoveFuncStmt,
168169
T_RemoveOperStmt,
169170
T_RemoveStmt,

src/include/nodes/parsenodes.h

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
*
77
* Copyright (c) 1994, Regents of the University of California
88
*
9-
* $Id: parsenodes.h,v 1.15 1997/04/29 04:28:59 vadim Exp $
9+
* $Id: parsenodes.h,v 1.16 1997/05/22 00:16:13 scrappy Exp $
1010
*
1111
*-------------------------------------------------------------------------
1212
*/
@@ -271,6 +271,16 @@ typedef struct PurgeStmt {
271271
char *afterDate; /* purge after this date */
272272
} PurgeStmt;
273273

274+
/* ----------------------
275+
* Drop Aggregate Statement
276+
* ----------------------
277+
*/
278+
typedef struct RemoveAggrStmt {
279+
NodeTag type;
280+
char *aggname; /* aggregate to drop */
281+
char *aggtype; /* for this type */
282+
} RemoveAggrStmt;
283+
274284
/* ----------------------
275285
* Drop Function Statement
276286
* ----------------------
@@ -292,12 +302,12 @@ typedef struct RemoveOperStmt {
292302
} RemoveOperStmt;
293303

294304
/* ----------------------
295-
* Drop {Aggregate|Type|Index|Rule|View} Statement
305+
* Drop {Type|Index|Rule|View} Statement
296306
* ----------------------
297307
*/
298308
typedef struct RemoveStmt {
299309
NodeTag type;
300-
int removeType; /* AGGREGATE|P_TYPE|INDEX|RULE|VIEW */
310+
int removeType; /* P_TYPE|INDEX|RULE|VIEW */
301311
char *name; /* name to drop */
302312
} RemoveStmt;
303313

0 commit comments

Comments
 (0)