]> granicus.if.org Git - postgresql/commit
Use standard casting mechanism to convert types in plpgsql, when possible.
authorTom Lane <tgl@sss.pgh.pa.us>
Wed, 4 Mar 2015 16:04:30 +0000 (11:04 -0500)
committerTom Lane <tgl@sss.pgh.pa.us>
Wed, 4 Mar 2015 16:04:30 +0000 (11:04 -0500)
commit1345cc67bbb014209714af32b5681b1e11eaf964
tree5ded223b7f2a5d1e9a7ea408d8b904a341edc328
parentb9896198cfbc1b0cd0c631d2af72ffe34bd4c7e5
Use standard casting mechanism to convert types in plpgsql, when possible.

plpgsql's historical method for converting datatypes during assignments was
to apply the source type's output function and then the destination type's
input function.  Aside from being miserably inefficient in most cases, this
method failed outright in many cases where a user might expect it to work;
an example is that "declare x int; ... x := 3.9;" would fail, not round the
value to 4.

Instead, let's convert by applying the appropriate assignment cast whenever
there is one.  To avoid breaking compatibility unnecessarily, fall back to
the I/O conversion method if there is no assignment cast.

So far as I can tell, there is just one case where this method produces a
different result than the old code in a case where the old code would not
have thrown an error.  That is assignment of a boolean value to a string
variable (type text, varchar, or bpchar); the old way gave boolean's output
representation, ie 't'/'f', while the new way follows the behavior of the
bool-to-text cast and so gives 'true' or 'false'.  This will need to be
called out as an incompatibility in the 9.5 release notes.

Aside from handling many conversion cases more sanely, this method is
often significantly faster than the old way.  In part that's because
of more effective caching of the conversion info.
doc/src/sgml/plpgsql.sgml
doc/src/sgml/typeconv.sgml
src/pl/plpgsql/src/pl_comp.c
src/pl/plpgsql/src/pl_exec.c
src/pl/plpgsql/src/plpgsql.h