index 91fadb0f14d8802dbff7dabbb5b455b1ad22fc0c..f008e937eefcbe9487c1b298ef11c467e7e591f6 100644 (file)
Inside the format string, <literal>%</literal> is replaced by the
string representation of the next optional argument's value. Write
<literal>%%</literal> to emit a literal <literal>%</literal>.
+ The number of arguments must match the number of <literal>%</>
+ placeholders in the format string, or an error is raised during
+ the compilation of the function.
</para>
<para>
index 69d1965253d878b1ba3946334973679dd6913e63..11cb47b5225d987b815d652adc77247b63e2022c 100644 (file)
@@ -2939,10 +2939,9 @@ exec_stmt_raise(PLpgSQL_execstate *estate, PLpgSQL_stmt_raise *stmt)
continue;
}
+ /* should have been checked at compile time */
if (current_param == NULL)
- ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
- errmsg("too few parameters specified for RAISE")));
+ elog(ERROR, "unexpected RAISE parameter list length");
paramvalue = exec_eval_expr(estate,
(PLpgSQL_expr *) lfirst(current_param),
@@ -2963,14 +2962,9 @@ exec_stmt_raise(PLpgSQL_execstate *estate, PLpgSQL_stmt_raise *stmt)
appendStringInfoChar(&ds, cp[0]);
}
- /*
- * If more parameters were specified than were required to process the
- * format string, throw an error
- */
+ /* should have been checked at compile time */
if (current_param != NULL)
- ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
- errmsg("too many parameters specified for RAISE")));
+ elog(ERROR, "unexpected RAISE parameter list length");
err_message = ds.data;
/* No pfree(ds.data), the pfree(err_message) does it */
index e3a992cf0ff57fc1e2cfc455fd4c2390f666ed1c..893f3a486f52366af9302cf31c4cf132977cb695 100644 (file)
@@ -106,6 +106,7 @@ static void check_labels(const char *start_label,
static PLpgSQL_expr *read_cursor_args(PLpgSQL_var *cursor,
int until, const char *expected);
static List *read_raise_options(void);
+static void check_raise_parameters(PLpgSQL_stmt_raise *stmt);
%}
new->options = read_raise_options();
}
+ check_raise_parameters(new);
+
$$ = (PLpgSQL_stmt *)new;
}
;
return result;
}
+/*
+ * Check that the number of parameter placeholders in the message matches the
+ * number of parameters passed to it, if a message was given.
+ */
+static void
+check_raise_parameters(PLpgSQL_stmt_raise *stmt)
+{
+ char *cp;
+ int expected_nparams = 0;
+
+ if (stmt->message == NULL)
+ return;
+
+ for (cp = stmt->message; *cp; cp++)
+ {
+ if (cp[0] == '%')
+ {
+ /* ignore literal % characters */
+ if (cp[1] == '%')
+ cp++;
+ else
+ expected_nparams++;
+ }
+ }
+
+ if (expected_nparams < list_length(stmt->params))
+ ereport(ERROR,
+ (errcode(ERRCODE_SYNTAX_ERROR),
+ errmsg("too many parameters specified for RAISE")));
+ if (expected_nparams > list_length(stmt->params))
+ ereport(ERROR,
+ (errcode(ERRCODE_SYNTAX_ERROR),
+ errmsg("too few parameters specified for RAISE")));
+}
+
/*
* Fix up CASE statement
*/
index 8892bb417d39a020c14b4f4d550f1bfa0c9597a3..983f1b8b5a4e65713c4d01d9bebfa9b7bcfe1633 100644 (file)
return 1ドル;
end;
$$ language plpgsql;
-select raise_test1(5);
ERROR: too many parameters specified for RAISE
-CONTEXT: PL/pgSQL function raise_test1(integer) line 3 at RAISE
+CONTEXT: compilation of PL/pgSQL function "raise_test1" near line 3
create function raise_test2(int) returns int as $$
begin
raise notice 'This message has too few parameters: %, %, %', 1,ドル 1ドル;
return 1ドル;
end;
$$ language plpgsql;
-select raise_test2(10);
ERROR: too few parameters specified for RAISE
-CONTEXT: PL/pgSQL function raise_test2(integer) line 3 at RAISE
+CONTEXT: compilation of PL/pgSQL function "raise_test2" near line 3
+create function raise_test3(int) returns int as $$
+begin
+ raise notice 'This message has no parameters (despite having %% signs in it)!';
+ return 1ドル;
+end;
+$$ language plpgsql;
+select raise_test3(1);
+NOTICE: This message has no parameters (despite having % signs in it)!
+ raise_test3
+-------------
+ 1
+(1 row)
+
-- Test re-RAISE inside a nested exception block. This case is allowed
-- by Oracle's PL/SQL but was handled differently by PG before 9.1.
CREATE FUNCTION reraise_test() RETURNS void AS $$
index c5616ee8fc638b68fa6bc60a4d9fcc6ac7cec11e..2abcbc8d3cd9b2dce3aba2251584e25d10f8c8f4 100644 (file)
end;
$$ language plpgsql;
-select raise_test1(5);
-
create function raise_test2(int) returns int as $$
begin
raise notice 'This message has too few parameters: %, %, %', 1,ドル 1ドル;
end;
$$ language plpgsql;
-select raise_test2(10);
+create function raise_test3(int) returns int as $$
+begin
+ raise notice 'This message has no parameters (despite having %% signs in it)!';
+ return 1ドル;
+end;
+$$ language plpgsql;
+
+select raise_test3(1);
-- Test re-RAISE inside a nested exception block. This case is allowed
-- by Oracle's PL/SQL but was handled differently by PG before 9.1.