#pragma section-numbers 2

= PL/Proxy =

[[TableOfContents]]

== Overview ==

PL/Proxy is a proxy language used for remote database procedure calls
and data partitioning between databases based on hashing field values.

Main idea is that proxy function will be created with same
signature as remote function to be called, so only destination
info needs to be specified inside proxy function body.

Downloads: http://pgfoundry.org/projects/plproxy

Detailed info: ./LanguageSyntax  ./ClusterConfig

== Short intro ==

=== Simple remote function call ===

Connect to `dbname=users` and run following SQL there: `SELECT * from get_user_email($1);`

{{{
CREATE FUNCTION get_user_email(username text)
RETURNS text AS $$
    CONNECT 'dbname=users';
$$ LANGUAGE plproxy;
}}}

=== Partitioned remote call ===

Users are spread over several databases,
partition number is aquired by taking hashtext(username).  This
needs also configuring the cluster, described later.  After this
is done, actual proxy function looks following:

{{{
CREATE FUNCTION get_user_email(username text)
RETURNS text AS $$
    CLUSTER 'userdb';
    RUN ON hashtext(username);
$$ LANGUAGE plproxy;
}}}

=== Run user-specified SELECT statement remotely ===

{{{
CREATE FUNCTION get_user_location(text) RETURNS text AS $$
    CLUSTER 'userdb';
    RUN ON hashtext($1);
    SELECT email FROM users WHERE user = $1;
$$ LANGUAGE plproxy;
}}}



== Restrictions ==

 * All SELECTs/functions are run in autocommit mode on the remote server

 * Only one SELECT statement is allowed, if you need to do more, then you have to 
 write a pl function on remote side

 * PL/Proxy launches connections into each part from each backend, so in
 heavy-duty environment it is useful to put pooler between PL/Proxy
 and partitions.  We have specially for that developed ../PgBouncer
 which pooler that can do statement-based pooling - release server
 after each SQL statement.
