Home Explore Blog CI



postgresql

4th chunk of `doc/src/sgml/pltcl.sgml`
75a6553282c4cf9d788510a200d376bcafc08e66c793c9e70000000100000fa4
 <literal>return_next</literal> commands will accept
     any string that is acceptable input format for the function's declared
     result type, or for the specified column of a composite result type.
    </para>

   </sect1>

   <sect1 id="pltcl-global">
    <title>Global Data in PL/Tcl</title>

    <indexterm zone="pltcl-global">
     <primary>global data</primary>
     <secondary>in PL/Tcl</secondary>
    </indexterm>

    <para>
     Sometimes it
     is useful to have some global data that is held between two
     calls to a function or is shared between different functions.
     This is easily done in PL/Tcl, but there are some restrictions that
     must be understood.
    </para>

    <para>
     For security reasons, PL/Tcl executes functions called by any one SQL
     role in a separate Tcl interpreter for that role.  This prevents
     accidental or malicious interference by one user with the behavior of
     another user's PL/Tcl functions.  Each such interpreter will have its own
     values for any <quote>global</quote> Tcl variables.  Thus, two PL/Tcl
     functions will share the same global variables if and only if they are
     executed by the same SQL role.  In an application wherein a single
     session executes code under multiple SQL roles (via <literal>SECURITY
     DEFINER</literal> functions, use of <command>SET ROLE</command>, etc.) you may need to
     take explicit steps to ensure that PL/Tcl functions can share data.  To
     do that, make sure that functions that should communicate are owned by
     the same user, and mark them <literal>SECURITY DEFINER</literal>.  You must of
     course take care that such functions can't be used to do anything
     unintended.
    </para>

    <para>
     All PL/TclU functions used in a session execute in the same Tcl
     interpreter, which of course is distinct from the interpreter(s)
     used for PL/Tcl functions.  So global data is automatically shared
     between PL/TclU functions.  This is not considered a security risk
     because all PL/TclU functions execute at the same trust level,
     namely that of a database superuser.
    </para>

    <para>
     To help protect PL/Tcl functions from unintentionally interfering
     with each other, a global
     array is made available to each function via the <function>upvar</function>
     command. The global name of this variable is the function's internal
     name, and the local name is <literal>GD</literal>.  It is recommended that
     <literal>GD</literal> be used
     for persistent private data of a function.  Use regular Tcl global
     variables only for values that you specifically intend to be shared among
     multiple functions.  (Note that the <literal>GD</literal> arrays are only
     global within a particular interpreter, so they do not bypass the
     security restrictions mentioned above.)
    </para>

    <para>
     An example of using <literal>GD</literal> appears in the
     <function>spi_execp</function> example below.
    </para>
   </sect1>

   <sect1 id="pltcl-dbaccess">
    <title>Database Access from PL/Tcl</title>

    <para>
     In this section, we follow the usual Tcl convention of using question
     marks, rather than brackets, to indicate an optional element in a
     syntax synopsis.  The following commands are available to access
     the database from the body of a PL/Tcl function:

    <variablelist>

     <varlistentry>
      <term><literal><function>spi_exec</function> <optional role="tcl">-count <replaceable>n</replaceable></optional> <optional role="tcl">-array <replaceable>name</replaceable></optional> <replaceable>command</replaceable> <optional role="tcl"><replaceable>loop-body</replaceable></optional></literal></term>
      <listitem>
       <para>
        Executes an SQL command given as a string.  An error in the command
        causes an error to be raised.  Otherwise, the return value of <function>spi_exec</function>
        is the number of rows processed

Title: PL/Tcl: Global Data and Database Access
Summary
This section discusses global data in PL/Tcl, emphasizing the security measures that isolate functions called by different SQL roles in separate Tcl interpreters. It explains how to share data between functions owned by the same user with `SECURITY DEFINER`. It also introduces the `GD` global array for private function data and describes commands like `spi_exec` for database access from within PL/Tcl functions.