PL/Perl 是一种可装载的过程语言,通过它我们可以 用 Perl 编程语言写 PostgreSQL 函数.
要在特定数据库里安装 PL/Perl,使用 createlang plperl dbname.
窍门: 如果某种编程语言安装到乐 template1,那么所有随后创建 的数据库都会自动安装这种语言。
注意: 使用源码包的用户必须在安装过程中特别打开 PL/Perl 的制作 (请参考安装指导获取更多信息)。二进制包的用户可能会在 一些独立的子包中找到 PL/Perl。
要用 PL/Perl 语言创建一个函数,可以使用标准的语法
CREATE FUNCTION funcname (argument-types) RETURNS return-type AS ' # PL/Perl function body ' LANGUAGE plperl;
函数体是普通的 Perl 代码。
参数和结果都是和任何其它 Perl 子过程 里那样处理的∶参数是放在 @_ 里传递的, 结果值是用 return 返回或者作为函数中最后计算的表达式 的值返回.比如,一个返回两个整数中较大值的函数可以这么写∶
CREATE FUNCTION perl_max (integer, integer) RETURNS integer AS ' if ($_[0] > $_[1]) { return $_[0]; } return $_[1]; ' LANGUAGE plperl;
如果给函数传递一个 SQL null 那么其参数值将以 Perl 中 "undefined" 的形式出现.上面的函数定义在输入为 null 时的行为不是很正常(实际上, 它将表现得好像它们都是零一样).我们可以给函数定义增加 STRICT,让 PostgreSQL 做一些更合理的事情∶如果传递进来一个 NULL,那么该函数则根本不会被 调用,而只是自动返回一个 NULL结果.另外,我们可以在函数体里检查 未定义(undefined)的输入.比如,假设我们想收到一个 null 和一个非 null 参数的 perl_max 返回非 null 的参数,而不是 null 值∶
CREATE FUNCTION perl_max (integer, integer) RETURNS integer AS ' my ($a,$b) = @_; if (! defined $a) { if (! defined $b) { return undef; } return $b; } if (! defined $b) { return $a; } if ($a > $b) { return $a; } return $b; ' LANGUAGE plperl;
如上所述,要从 PL/Perl 函数中返回一个 SQL null,我们可以返回一个 未定义(undef)的数值.不管该函数是否严格,我们都可以这么做.
复合类型的参数是当做指向散列的引用传递给函数的. 散列的键字是复合类型的属性名.下面是一个例子∶
CREATE TABLE employee ( name text, basesalary integer, bonus integer ); CREATE FUNCTION empcomp(employee) RETURNS integer AS ' my ($emp) = @_; return $emp->{''basesalary''} + $emp->{''bonus''}; ' LANGUAGE plperl; SELECT name, empcomp(employee) FROM employee;
目前还没有任何形式的返回一个复合类型返回值的支持.
窍门: 因为函数体是以一个 SQL 字串文本的形式传递给 CREATE FUNCTION 的,你必须在你的 Perl 源码内部 逃逸单引号和反斜扛.通常就是象上面例子显示的那样写双份。 另外一个可能的途径是用 Perl 的扩展引起函数 (q[],qq[], qw[])来避免使用单引号.