From 01038d4ad77eec8cdf16a39c69fc902bf30c4072 Mon Sep 17 00:00:00 2001 From: Heikki Linnakangas Date: Fri, 13 Nov 2009 19:48:20 +0000 Subject: [PATCH] A better fix for the "ARRAY[...]::domain" problem. The previous patch worked, but the transformed ArrayExpr claimed to have a return type of "domain", even though the domain constraint was only checked by the enclosing CoerceToDomain node. With this fix, the ArrayExpr is correctly labeled with the base type of the domain. Per gripe by Tom Lane. --- src/backend/parser/parse_expr.c | 40 +++++++++++++-------------------- 1 file changed, 16 insertions(+), 24 deletions(-) diff --git a/src/backend/parser/parse_expr.c b/src/backend/parser/parse_expr.c index 8e0172d256..8513102a9c 100644 --- a/src/backend/parser/parse_expr.c +++ b/src/backend/parser/parse_expr.c @@ -8,7 +8,7 @@ * * * IDENTIFICATION - * $PostgreSQL: pgsql/src/backend/parser/parse_expr.c,v 1.249 2009/11/13 16:09:10 heikki Exp $ + * $PostgreSQL: pgsql/src/backend/parser/parse_expr.c,v 1.250 2009/11/13 19:48:20 heikki Exp $ * *------------------------------------------------------------------------- */ @@ -164,32 +164,23 @@ transformExpr(ParseState *pstate, Node *expr) elementType = get_element_type(targetType); if (OidIsValid(elementType)) { - result = transformArrayExpr(pstate, - (A_ArrayExpr *) tc->arg, - targetType, - elementType, - targetTypmod); - /* - * If the target array type is a domain, we still need - * to check the domain constraint. (coerce_to_domain - * is a no-op if targetType is not a domain) + * tranformArrayExpr doesn't know how to check domain + * constraints, so ask it to return the base type + * instead. transformTypeCast below will cast it to + * the domain. In the usual case that the target is + * not a domain, transformTypeCast is a no-op. */ - result = coerce_to_domain(result, - InvalidOid, - -1, - targetType, - COERCE_IMPLICIT_CAST, - tc->location, - false, - true); - break; + targetType = getBaseTypeAndTypmod(targetType, + &targetTypmod); + + tc = copyObject(tc); + tc->arg = transformArrayExpr(pstate, + (A_ArrayExpr *) tc->arg, + targetType, + elementType, + targetTypmod); } - - /* - * Corner case: ARRAY[] cast to a non-array type. Fall - * through to do it the standard way. - */ } result = transformTypeCast(pstate, tc); @@ -324,6 +315,7 @@ transformExpr(ParseState *pstate, Node *expr) case T_ArrayCoerceExpr: case T_ConvertRowtypeExpr: case T_CaseTestExpr: + case T_ArrayExpr: case T_CoerceToDomain: case T_CoerceToDomainValue: case T_SetToDefault: