Home Explore Blog CI



postgresql

61th chunk of `doc/src/sgml/ddl.sgml`
9e0156021fa0873b815bf9a262ebd577efc452303a2c8a9f0000000100000fa2
   could do this with a more complex trigger function, for example:

<programlisting>
CREATE OR REPLACE FUNCTION measurement_insert_trigger()
RETURNS TRIGGER AS $$
BEGIN
    IF ( NEW.logdate &gt;= DATE '2006-02-01' AND
         NEW.logdate &lt; DATE '2006-03-01' ) THEN
        INSERT INTO measurement_y2006m02 VALUES (NEW.*);
    ELSIF ( NEW.logdate &gt;= DATE '2006-03-01' AND
            NEW.logdate &lt; DATE '2006-04-01' ) THEN
        INSERT INTO measurement_y2006m03 VALUES (NEW.*);
    ...
    ELSIF ( NEW.logdate &gt;= DATE '2008-01-01' AND
            NEW.logdate &lt; DATE '2008-02-01' ) THEN
        INSERT INTO measurement_y2008m01 VALUES (NEW.*);
    ELSE
        RAISE EXCEPTION 'Date out of range.  Fix the measurement_insert_trigger() function!';
    END IF;
    RETURN NULL;
END;
$$
LANGUAGE plpgsql;
</programlisting>

         The trigger definition is the same as before.
         Note that each <literal>IF</literal> test must exactly match the
         <literal>CHECK</literal> constraint for its child table.
        </para>

        <para>
         While this function is more complex than the single-month case,
         it doesn't need to be updated as often, since branches can be
         added in advance of being needed.
        </para>

        <note>
         <para>
          In practice, it might be best to check the newest child first,
          if most inserts go into that child.  For simplicity, we have
          shown the trigger's tests in the same order as in other parts
          of this example.
         </para>
        </note>

        <para>
         A different approach to redirecting inserts into the appropriate
         child table is to set up rules, instead of a trigger, on the
         root table.  For example:

<programlisting>
CREATE RULE measurement_insert_y2006m02 AS
ON INSERT TO measurement WHERE
    ( logdate &gt;= DATE '2006-02-01' AND logdate &lt; DATE '2006-03-01' )
DO INSTEAD
    INSERT INTO measurement_y2006m02 VALUES (NEW.*);
...
CREATE RULE measurement_insert_y2008m01 AS
ON INSERT TO measurement WHERE
    ( logdate &gt;= DATE '2008-01-01' AND logdate &lt; DATE '2008-02-01' )
DO INSTEAD
    INSERT INTO measurement_y2008m01 VALUES (NEW.*);
</programlisting>

         A rule has significantly more overhead than a trigger, but the
         overhead is paid once per query rather than once per row, so this
         method might be advantageous for bulk-insert situations.  In most
         cases, however, the trigger method will offer better performance.
        </para>

        <para>
         Be aware that <command>COPY</command> ignores rules.  If you want to
         use <command>COPY</command> to insert data, you'll need to copy into the
         correct child table rather than directly into the root. <command>COPY</command>
         does fire triggers, so you can use it normally if you use the trigger
         approach.
        </para>

        <para>
         Another disadvantage of the rule approach is that there is no simple
         way to force an error if the set of rules doesn't cover the insertion
         date; the data will silently go into the root table instead.
        </para>
       </listitem>

       <listitem>
        <para>
         Ensure that the <xref linkend="guc-constraint-exclusion"/>
         configuration parameter is not disabled in
         <filename>postgresql.conf</filename>; otherwise
         child tables may be accessed unnecessarily.
        </para>
       </listitem>
      </orderedlist>
     </para>

     <para>
      As we can see, a complex table hierarchy could require a
      substantial amount of DDL.  In the above example we would be creating
      a new child table each month, so it might be wise to write a script that
      generates the required DDL automatically.
     </para>
    </sect3>

    <sect3 id="ddl-partitioning-inheritance-maintenance">
     <title>Maintenance for Inheritance Partitioning</title>
     <para>
      To remove old data

Title: Partitioning Using Inheritance: Trigger and Rule Alternatives
Summary
This section discusses alternative approaches to redirecting inserts into child tables. It elaborates on the complex trigger function for automatic child table location and emphasizes matching `IF` tests to `CHECK` constraints. It also introduces using rules instead of triggers, comparing their overhead and suitability for different scenarios. The section also notes that `COPY` command ignores rules, and points out a disadvantage of the rule approach: data might silently go into the root table if no rule applies. Finally, it mentions the importance of constraint exclusion and the potential for scripting DDL generation for table hierarchies.