240240
241241 <para>
242242 There are five user-defined methods that an index operator class for
243- <acronym>SP-GiST</acronym> must provide. All five follow the convention
244- of accepting two <type>internal</type> arguments, the first of which is a
245- pointer to a C struct containing input values for the support method,
246- while the second argument is a pointer to a C struct where output values
247- must be placed. Four of the methods just return <type>void</type>, since
248- all their results appear in the output struct; but
243+ <acronym>SP-GiST</acronym> must provide, and one is optional. All five
244+ mandatory methods follow the convention of accepting two <type>internal</type>
245+ arguments, the first of which is a pointer to a C struct containing input
246+ values for the support method, while the second argument is a pointer to a
247+ C struct where output values must be placed. Four of the mandatory methods just
248+ return <type>void</type>, since all their results appear in the output struct; but
249249 <function>leaf_consistent</function> additionally returns a <type>boolean</type> result.
250250 The methods must not modify any fields of their input structs. In all
251251 cases, the output struct is initialized to zeroes before calling the
252- user-defined method.
252+ user-defined method. Optional sixth method <function>compress</function>
253+ accepts datum to be indexed as the only argument and returns value suitable
254+ for physical storage in leaf tuple.
253255 </para>
254256
255257 <para>
256- The five user-defined methods are:
258+ The five mandatory user-defined methods are:
257259 </para>
258260
259261 <variablelist>
@@ -283,6 +285,7 @@ typedef struct spgConfigOut
283285{
284286 Oid prefixType; /* Data type of inner-tuple prefixes */
285287 Oid labelType; /* Data type of inner-tuple node labels */
288+ Oid leafType; /* Data type of leaf-tuple values */
286289 bool canReturnData; /* Opclass can reconstruct original data */
287290 bool longValuesOK; /* Opclass can cope with values > 1 page */
288291} spgConfigOut;
@@ -305,6 +308,22 @@ typedef struct spgConfigOut
305308 class is capable of segmenting long values by repeated suffixing
306309 (see <xref linkend="spgist-limits"/>).
307310 </para>
311+
312+ <para>
313+ <structfield>leafType</structfield> is typically the same as
314+ <structfield>attType</structfield>. For the reasons of backward
315+ compatibility, method <function>config</function> can
316+ leave <structfield>leafType</structfield> uninitialized; that would
317+ give the same effect as setting <structfield>leafType</structfield> equal
318+ to <structfield>attType</structfield>. When <structfield>attType</structfield>
319+ and <structfield>leafType</structfield> are different, then optional
320+ method <function>compress</function> must be provided.
321+ Method <function>compress</function> is responsible
322+ for transformation of datums to be indexed from <structfield>attType</structfield>
323+ to <structfield>leafType</structfield>.
324+ Note: both consistent functions will get <structfield>scankeys</structfield>
325+ unchanged, without transformation using <function>compress</function>.
326+ </para>
308327 </listitem>
309328 </varlistentry>
310329
@@ -380,10 +399,16 @@ typedef struct spgChooseOut
380399} spgChooseOut;
381400</programlisting>
382401
383- <structfield>datum</structfield> is the original datum that was to be inserted
384- into the index.
385- <structfield>leafDatum</structfield> is initially the same as
386- <structfield>datum</structfield>, but can change at lower levels of the tree
402+ <structfield>datum</structfield> is the original datum of
403+ <structname>spgConfigIn</structname>.<structfield>attType</structfield>
404+ type that was to be inserted into the index.
405+ <structfield>leafDatum</structfield> is a value of
406+ <structname>spgConfigOut</structname>.<structfield>leafType</structfield>
407+ type which is initially an result of method
408+ <function>compress</function> applied to <structfield>datum</structfield>
409+ when method <function>compress</function> is provided, or same value as
410+ <structfield>datum</structfield> otherwise.
411+ <structfield>leafDatum</structfield> can change at lower levels of the tree
387412 if the <function>choose</function> or <function>picksplit</function>
388413 methods change it. When the insertion search reaches a leaf page,
389414 the current value of <structfield>leafDatum</structfield> is what will be stored
@@ -418,7 +443,7 @@ typedef struct spgChooseOut
418443 Set <structfield>levelAdd</structfield> to the increment in
419444 <structfield>level</structfield> caused by descending through that node,
420445 or leave it as zero if the operator class does not use levels.
421- Set <structfield>restDatum</structfield> to equal <structfield>datum </structfield>
446+ Set <structfield>restDatum</structfield> to equal <structfield>leafDatum </structfield>
422447 if the operator class does not modify datums from one level to the
423448 next, or otherwise set it to the modified value to be used as
424449 <structfield>leafDatum</structfield> at the next level.
@@ -509,7 +534,9 @@ typedef struct spgPickSplitOut
509534</programlisting>
510535
511536 <structfield>nTuples</structfield> is the number of leaf tuples provided.
512- <structfield>datums</structfield> is an array of their datum values.
537+ <structfield>datums</structfield> is an array of their datum values of
538+ <structname>spgConfigOut</structname>.<structfield>leafType</structfield>
539+ type.
513540 <structfield>level</structfield> is the current level that all the leaf tuples
514541 share, which will become the level of the new inner tuple.
515542 </para>
@@ -624,7 +651,8 @@ typedef struct spgInnerConsistentOut
624651 <structfield>reconstructedValue</structfield> is the value reconstructed for the
625652 parent tuple; it is <literal>(Datum) 0</literal> at the root level or if the
626653 <function>inner_consistent</function> function did not provide a value at the
627- parent level.
654+ parent level. <structfield>reconstructedValue</structfield> is always of
655+ <structname>spgConfigOut</structname>.<structfield>leafType</structfield> type.
628656 <structfield>traversalValue</structfield> is a pointer to any traverse data
629657 passed down from the previous call of <function>inner_consistent</function>
630658 on the parent index tuple, or NULL at the root level.
@@ -659,6 +687,7 @@ typedef struct spgInnerConsistentOut
659687 necessarily so, so an array is used.)
660688 If value reconstruction is needed, set
661689 <structfield>reconstructedValues</structfield> to an array of the values
690+ of <structname>spgConfigOut</structname>.<structfield>leafType</structfield> type
662691 reconstructed for each child node to be visited; otherwise, leave
663692 <structfield>reconstructedValues</structfield> as NULL.
664693 If it is desired to pass down additional out-of-band information
@@ -730,7 +759,8 @@ typedef struct spgLeafConsistentOut
730759 <structfield>reconstructedValue</structfield> is the value reconstructed for the
731760 parent tuple; it is <literal>(Datum) 0</literal> at the root level or if the
732761 <function>inner_consistent</function> function did not provide a value at the
733- parent level.
762+ parent level. <structfield>reconstructedValue</structfield> is always of
763+ <structname>spgConfigOut</structname>.<structfield>leafType</structfield> type.
734764 <structfield>traversalValue</structfield> is a pointer to any traverse data
735765 passed down from the previous call of <function>inner_consistent</function>
736766 on the parent index tuple, or NULL at the root level.
@@ -739,16 +769,18 @@ typedef struct spgLeafConsistentOut
739769 <structfield>returnData</structfield> is <literal>true</literal> if reconstructed data is
740770 required for this query; this will only be so if the
741771 <function>config</function> function asserted <structfield>canReturnData</structfield>.
742- <structfield>leafDatum</structfield> is the key value stored in the current
743- leaf tuple.
772+ <structfield>leafDatum</structfield> is the key value of
773+ <structname>spgConfigOut</structname>.<structfield>leafType</structfield>
774+ stored in the current leaf tuple.
744775 </para>
745776
746777 <para>
747778 The function must return <literal>true</literal> if the leaf tuple matches the
748779 query, or <literal>false</literal> if not. In the <literal>true</literal> case,
749780 if <structfield>returnData</structfield> is <literal>true</literal> then
750- <structfield>leafValue</structfield> must be set to the value originally supplied
751- to be indexed for this leaf tuple. Also,
781+ <structfield>leafValue</structfield> must be set to the value of
782+ <structname>spgConfigIn</structname>.<structfield>attType</structfield> type
783+ originally supplied to be indexed for this leaf tuple. Also,
752784 <structfield>recheck</structfield> may be set to <literal>true</literal> if the match
753785 is uncertain and so the operator(s) must be re-applied to the actual
754786 heap tuple to verify the match.
@@ -757,6 +789,26 @@ typedef struct spgLeafConsistentOut
757789 </varlistentry>
758790 </variablelist>
759791
792+ <para>
793+ The optional user-defined method is:
794+ </para>
795+
796+ <variablelist>
797+ <varlistentry>
798+ <term><function>Datum compress(Datum in)</function></term>
799+ <listitem>
800+ <para>
801+ Converts the data item into a format suitable for physical storage in
802+ a leaf tuple of index page. It accepts
803+ <structname>spgConfigIn</structname>.<structfield>attType</structfield>
804+ value and return
805+ <structname>spgConfigOut</structname>.<structfield>leafType</structfield>
806+ value. Output value should not be toasted.
807+ </para>
808+ </listitem>
809+ </varlistentry>
810+ </variablelist>
811+
760812 <para>
761813 All the SP-GiST support methods are normally called in a short-lived
762814 memory context; that is, <varname>CurrentMemoryContext</varname> will be reset
0 commit comments