2010-09-20 22:08:53 +02:00
<!-- doc/src/sgml/hstore.sgml -->
2007-12-06 05:12:10 +01:00
2011-05-08 04:29:20 +02:00
<sect1 id="hstore" xreflabel="hstore">
2007-11-11 00:30:46 +01:00
<title>hstore</title>
2007-12-06 05:12:10 +01:00
2007-11-11 00:30:46 +01:00
<indexterm zone="hstore">
<primary>hstore</primary>
</indexterm>
<para>
2017-10-09 03:44:17 +02:00
This module implements the <type>hstore</type> data type for storing sets of
key/value pairs within a single <productname>PostgreSQL</productname> value.
2007-12-06 05:12:10 +01:00
This can be useful in various scenarios, such as rows with many attributes
2009-09-30 21:50:22 +02:00
that are rarely examined, or semi-structured data. Keys and values are
2009-11-30 18:56:09 +01:00
simply text strings.
2009-03-15 23:05:17 +01:00
</para>
2007-11-11 00:30:46 +01:00
<sect2>
2017-10-09 03:44:17 +02:00
<title><type>hstore</type> External Representation</title>
2007-12-06 05:12:10 +01:00
<para>
2009-11-30 18:56:09 +01:00
2017-10-09 03:44:17 +02:00
The text representation of an <type>hstore</type>, used for input and output,
includes zero or more <replaceable>key</replaceable> <literal>=></literal>
<replaceable>value</replaceable> pairs separated by commas. Some examples:
2007-12-06 05:12:10 +01:00
2010-07-29 21:34:41 +02:00
<synopsis>
k => v
foo => bar, baz => whatever
"1-a" => "anything at all"
</synopsis>
2007-12-06 05:12:10 +01:00
2009-11-30 18:56:09 +01:00
The order of the pairs is not significant (and may not be reproduced on
2017-10-09 03:44:17 +02:00
output). Whitespace between pairs or around the <literal>=></literal> sign is
2009-11-30 18:56:09 +01:00
ignored. Double-quote keys and values that include whitespace, commas,
2017-10-09 03:44:17 +02:00
<literal>=</literal>s or <literal>></literal>s. To include a double quote or a
2009-11-30 18:56:09 +01:00
backslash in a key or value, escape it with a backslash.
</para>
<para>
2017-10-09 03:44:17 +02:00
Each key in an <type>hstore</type> is unique. If you declare an <type>hstore</type>
with duplicate keys, only one will be stored in the <type>hstore</type> and
2009-11-30 18:56:09 +01:00
there is no guarantee as to which will be kept:
2010-07-29 21:34:41 +02:00
<programlisting>
SELECT 'a=>1,a=>2'::hstore;
2009-11-30 18:56:09 +01:00
hstore
----------
"a"=>"1"
2010-07-29 21:34:41 +02:00
</programlisting>
2007-12-06 05:12:10 +01:00
</para>
<para>
2017-10-09 03:44:17 +02:00
A value (but not a key) can be an SQL <literal>NULL</literal>. For example:
2007-12-06 05:12:10 +01:00
2010-07-29 21:34:41 +02:00
<programlisting>
key => NULL
</programlisting>
2007-12-06 05:12:10 +01:00
2017-10-09 03:44:17 +02:00
The <literal>NULL</literal> keyword is case-insensitive. Double-quote the
<literal>NULL</literal> to treat it as the ordinary string <quote>NULL</quote>.
2007-12-06 05:12:10 +01:00
</para>
2009-09-30 21:50:22 +02:00
<note>
<para>
2017-10-09 03:44:17 +02:00
Keep in mind that the <type>hstore</type> text format, when used for input,
applies <emphasis>before</emphasis> any required quoting or escaping. If you are
passing an <type>hstore</type> literal via a parameter, then no additional
2009-11-30 18:56:09 +01:00
processing is needed. But if you're passing it as a quoted literal
constant, then any single-quote characters and (depending on the setting of
2017-10-09 03:44:17 +02:00
the <varname>standard_conforming_strings</varname> configuration parameter)
2009-11-30 18:56:09 +01:00
backslash characters need to be escaped correctly. See
2017-11-23 15:39:47 +01:00
<xref linkend="sql-syntax-strings"/> for more on the handling of string
2009-11-30 18:56:09 +01:00
constants.
2009-09-30 21:50:22 +02:00
</para>
</note>
2007-12-06 05:12:10 +01:00
<para>
2009-11-30 18:56:09 +01:00
On output, double quotes always surround keys and values, even when it's
not strictly necessary.
2007-12-06 05:12:10 +01:00
</para>
2007-11-11 00:30:46 +01:00
</sect2>
<sect2>
2017-10-09 03:44:17 +02:00
<title><type>hstore</type> Operators and Functions</title>
2007-12-06 05:12:10 +01:00
2011-05-04 19:24:07 +02:00
<para>
The operators provided by the <literal>hstore</literal> module are
2017-11-23 15:39:47 +01:00
shown in <xref linkend="hstore-op-table"/>, the functions
in <xref linkend="hstore-func-table"/>.
2011-05-04 19:24:07 +02:00
</para>
2007-12-06 05:12:10 +01:00
<table id="hstore-op-table">
2017-10-09 03:44:17 +02:00
<title><type>hstore</type> Operators</title>
2007-12-06 05:12:10 +01:00
<tgroup cols="4">
<thead>
<row>
<entry>Operator</entry>
<entry>Description</entry>
<entry>Example</entry>
<entry>Result</entry>
</row>
</thead>
<tbody>
<row>
2017-10-09 03:44:17 +02:00
<entry><type>hstore</type> <literal>-></literal> <type>text</type></entry>
<entry>get value for key (<literal>NULL</literal> if not present)</entry>
2007-12-06 05:12:10 +01:00
<entry><literal>'a=>x, b=>y'::hstore -> 'a'</literal></entry>
<entry><literal>x</literal></entry>
</row>
2009-09-30 21:50:22 +02:00
<row>
2017-10-09 03:44:17 +02:00
<entry><type>hstore</type> <literal>-></literal> <type>text[]</type></entry>
<entry>get values for keys (<literal>NULL</literal> if not present)</entry>
2009-09-30 21:50:22 +02:00
<entry><literal>'a=>x, b=>y, c=>z'::hstore -> ARRAY['c','a']</literal></entry>
<entry><literal>{"z","x"}</literal></entry>
</row>
2007-12-06 05:12:10 +01:00
<row>
2017-10-09 03:44:17 +02:00
<entry><type>hstore</type> <literal>||</literal> <type>hstore</type></entry>
<entry>concatenate <type>hstore</type>s</entry>
2007-12-06 05:12:10 +01:00
<entry><literal>'a=>b, c=>d'::hstore || 'c=>x, d=>q'::hstore</literal></entry>
<entry><literal>"a"=>"b", "c"=>"x", "d"=>"q"</literal></entry>
</row>
<row>
2017-10-09 03:44:17 +02:00
<entry><type>hstore</type> <literal>?</literal> <type>text</type></entry>
<entry>does <type>hstore</type> contain key?</entry>
2007-12-06 05:12:10 +01:00
<entry><literal>'a=>1'::hstore ? 'a'</literal></entry>
<entry><literal>t</literal></entry>
</row>
2009-09-30 21:50:22 +02:00
<row>
2017-10-09 03:44:17 +02:00
<entry><type>hstore</type> <literal>?&</literal> <type>text[]</type></entry>
<entry>does <type>hstore</type> contain all specified keys?</entry>
2009-09-30 21:50:22 +02:00
<entry><literal>'a=>1,b=>2'::hstore ?& ARRAY['a','b']</literal></entry>
<entry><literal>t</literal></entry>
</row>
<row>
2017-10-09 03:44:17 +02:00
<entry><type>hstore</type> <literal>?|</literal> <type>text[]</type></entry>
<entry>does <type>hstore</type> contain any of the specified keys?</entry>
2009-09-30 21:50:22 +02:00
<entry><literal>'a=>1,b=>2'::hstore ?| ARRAY['b','c']</literal></entry>
<entry><literal>t</literal></entry>
</row>
2007-12-06 05:12:10 +01:00
<row>
2017-10-09 03:44:17 +02:00
<entry><type>hstore</type> <literal>@></literal> <type>hstore</type></entry>
2007-12-06 05:12:10 +01:00
<entry>does left operand contain right?</entry>
<entry><literal>'a=>b, b=>1, c=>NULL'::hstore @> 'b=>1'</literal></entry>
<entry><literal>t</literal></entry>
</row>
<row>
2017-10-09 03:44:17 +02:00
<entry><type>hstore</type> <literal><@</literal> <type>hstore</type></entry>
2007-12-06 05:12:10 +01:00
<entry>is left operand contained in right?</entry>
<entry><literal>'a=>c'::hstore <@ 'a=>b, b=>1, c=>NULL'</literal></entry>
<entry><literal>f</literal></entry>
</row>
2009-09-30 21:50:22 +02:00
<row>
2017-10-09 03:44:17 +02:00
<entry><type>hstore</type> <literal>-</literal> <type>text</type></entry>
2009-09-30 21:50:22 +02:00
<entry>delete key from left operand</entry>
<entry><literal>'a=>1, b=>2, c=>3'::hstore - 'b'::text</literal></entry>
<entry><literal>"a"=>"1", "c"=>"3"</literal></entry>
</row>
<row>
2017-10-09 03:44:17 +02:00
<entry><type>hstore</type> <literal>-</literal> <type>text[]</type></entry>
2009-09-30 21:50:22 +02:00
<entry>delete keys from left operand</entry>
<entry><literal>'a=>1, b=>2, c=>3'::hstore - ARRAY['a','b']</literal></entry>
<entry><literal>"c"=>"3"</literal></entry>
</row>
<row>
2017-10-09 03:44:17 +02:00
<entry><type>hstore</type> <literal>-</literal> <type>hstore</type></entry>
2009-11-30 18:56:09 +01:00
<entry>delete matching pairs from left operand</entry>
2009-09-30 21:50:22 +02:00
<entry><literal>'a=>1, b=>2, c=>3'::hstore - 'a=>4, b=>2'::hstore</literal></entry>
<entry><literal>"a"=>"1", "c"=>"3"</literal></entry>
</row>
<row>
2017-10-09 03:44:17 +02:00
<entry><type>record</type> <literal>#=</literal> <type>hstore</type></entry>
<entry>replace fields in <type>record</type> with matching values from <type>hstore</type></entry>
2009-09-30 21:50:22 +02:00
<entry>see Examples section</entry>
<entry></entry>
</row>
<row>
2017-10-09 03:44:17 +02:00
<entry><literal>%%</literal> <type>hstore</type></entry>
<entry>convert <type>hstore</type> to array of alternating keys and values</entry>
2009-09-30 21:50:22 +02:00
<entry><literal>%% 'a=>foo, b=>bar'::hstore</literal></entry>
<entry><literal>{a,foo,b,bar}</literal></entry>
</row>
<row>
2017-10-09 03:44:17 +02:00
<entry><literal>%#</literal> <type>hstore</type></entry>
<entry>convert <type>hstore</type> to two-dimensional key/value array</entry>
2009-09-30 21:50:22 +02:00
<entry><literal>%# 'a=>foo, b=>bar'::hstore</literal></entry>
<entry><literal>{{a,foo},{b,bar}}</literal></entry>
</row>
2007-12-06 05:12:10 +01:00
</tbody>
</tgroup>
</table>
2009-11-30 18:56:09 +01:00
<note>
2007-12-06 05:12:10 +01:00
<para>
2017-10-09 03:44:17 +02:00
Prior to PostgreSQL 8.2, the containment operators <literal>@></literal>
and <literal><@</literal> were called <literal>@</literal> and <literal>~</literal>,
2009-11-30 18:56:09 +01:00
respectively. These names are still available, but are deprecated and will
eventually be removed. Notice that the old names are reversed from the
2010-08-17 06:37:21 +02:00
convention formerly followed by the core geometric data types!
2009-11-30 18:56:09 +01:00
</para>
</note>
2007-12-06 05:12:10 +01:00
<table id="hstore-func-table">
2017-10-09 03:44:17 +02:00
<title><type>hstore</type> Functions</title>
2007-12-06 05:12:10 +01:00
<tgroup cols="5">
<thead>
<row>
<entry>Function</entry>
<entry>Return Type</entry>
<entry>Description</entry>
<entry>Example</entry>
<entry>Result</entry>
</row>
</thead>
<tbody>
2009-09-30 21:50:22 +02:00
<row>
2013-07-04 17:33:08 +02:00
<entry><function>hstore(record)</function><indexterm><primary>hstore</primary></indexterm></entry>
2009-09-30 21:50:22 +02:00
<entry><type>hstore</type></entry>
2017-10-09 03:44:17 +02:00
<entry>construct an <type>hstore</type> from a record or row</entry>
2009-09-30 21:50:22 +02:00
<entry><literal>hstore(ROW(1,2))</literal></entry>
<entry><literal>f1=>1,f2=>2</literal></entry>
</row>
<row>
<entry><function>hstore(text[])</function></entry>
<entry><type>hstore</type></entry>
2017-10-09 03:44:17 +02:00
<entry>construct an <type>hstore</type> from an array, which may be either
2009-09-30 21:50:22 +02:00
a key/value array, or a two-dimensional array</entry>
<entry><literal>hstore(ARRAY['a','1','b','2']) || hstore(ARRAY[['c','3'],['d','4']])</literal></entry>
<entry><literal>a=>1, b=>2, c=>3, d=>4</literal></entry>
</row>
2010-06-15 21:48:30 +02:00
<row>
<entry><function>hstore(text[], text[])</function></entry>
<entry><type>hstore</type></entry>
2017-10-09 03:44:17 +02:00
<entry>construct an <type>hstore</type> from separate key and value arrays</entry>
2010-06-15 21:48:30 +02:00
<entry><literal>hstore(ARRAY['a','b'], ARRAY['1','2'])</literal></entry>
<entry><literal>"a"=>"1","b"=>"2"</literal></entry>
</row>
2010-06-22 13:36:16 +02:00
<row>
<entry><function>hstore(text, text)</function></entry>
<entry><type>hstore</type></entry>
2017-10-09 03:44:17 +02:00
<entry>make single-item <type>hstore</type></entry>
2010-06-22 13:36:16 +02:00
<entry><literal>hstore('a', 'b')</literal></entry>
<entry><literal>"a"=>"b"</literal></entry>
</row>
2007-12-06 05:12:10 +01:00
<row>
2013-07-04 17:33:08 +02:00
<entry><function>akeys(hstore)</function><indexterm><primary>akeys</primary></indexterm></entry>
2007-12-06 05:12:10 +01:00
<entry><type>text[]</type></entry>
2017-10-09 03:44:17 +02:00
<entry>get <type>hstore</type>'s keys as an array</entry>
2007-12-06 05:12:10 +01:00
<entry><literal>akeys('a=>1,b=>2')</literal></entry>
<entry><literal>{a,b}</literal></entry>
</row>
<row>
2013-07-04 17:33:08 +02:00
<entry><function>skeys(hstore)</function><indexterm><primary>skeys</primary></indexterm></entry>
2007-12-06 05:12:10 +01:00
<entry><type>setof text</type></entry>
2017-10-09 03:44:17 +02:00
<entry>get <type>hstore</type>'s keys as a set</entry>
2007-12-06 05:12:10 +01:00
<entry><literal>skeys('a=>1,b=>2')</literal></entry>
<entry>
2009-12-16 20:38:54 +01:00
<programlisting>
2007-12-06 05:12:10 +01:00
a
b
</programlisting></entry>
</row>
<row>
2013-07-04 17:33:08 +02:00
<entry><function>avals(hstore)</function><indexterm><primary>avals</primary></indexterm></entry>
2007-12-06 05:12:10 +01:00
<entry><type>text[]</type></entry>
2017-10-09 03:44:17 +02:00
<entry>get <type>hstore</type>'s values as an array</entry>
2007-12-06 05:12:10 +01:00
<entry><literal>avals('a=>1,b=>2')</literal></entry>
<entry><literal>{1,2}</literal></entry>
</row>
<row>
2013-07-04 17:33:08 +02:00
<entry><function>svals(hstore)</function><indexterm><primary>svals</primary></indexterm></entry>
2007-12-06 05:12:10 +01:00
<entry><type>setof text</type></entry>
2017-10-09 03:44:17 +02:00
<entry>get <type>hstore</type>'s values as a set</entry>
2007-12-06 05:12:10 +01:00
<entry><literal>svals('a=>1,b=>2')</literal></entry>
<entry>
<programlisting>
1
2
</programlisting></entry>
</row>
2009-09-30 21:50:22 +02:00
<row>
2013-07-04 17:33:08 +02:00
<entry><function>hstore_to_array(hstore)</function><indexterm><primary>hstore_to_array</primary></indexterm></entry>
2009-09-30 21:50:22 +02:00
<entry><type>text[]</type></entry>
2017-10-09 03:44:17 +02:00
<entry>get <type>hstore</type>'s keys and values as an array of alternating
2009-09-30 21:50:22 +02:00
keys and values</entry>
<entry><literal>hstore_to_array('a=>1,b=>2')</literal></entry>
<entry><literal>{a,1,b,2}</literal></entry>
</row>
<row>
2013-07-04 17:33:08 +02:00
<entry><function>hstore_to_matrix(hstore)</function><indexterm><primary>hstore_to_matrix</primary></indexterm></entry>
2009-09-30 21:50:22 +02:00
<entry><type>text[]</type></entry>
2017-10-09 03:44:17 +02:00
<entry>get <type>hstore</type>'s keys and values as a two-dimensional array</entry>
2009-09-30 21:50:22 +02:00
<entry><literal>hstore_to_matrix('a=>1,b=>2')</literal></entry>
<entry><literal>{{a,1},{b,2}}</literal></entry>
</row>
2013-03-10 22:35:36 +01:00
<row>
2013-07-04 17:33:08 +02:00
<entry><function>hstore_to_json(hstore)</function><indexterm><primary>hstore_to_json</primary></indexterm></entry>
2013-03-10 22:35:36 +01:00
<entry><type>json</type></entry>
2016-02-03 18:56:40 +01:00
<entry>get <type>hstore</type> as a <type>json</type> value, converting
all non-null values to JSON strings</entry>
2013-03-10 22:35:36 +01:00
<entry><literal>hstore_to_json('"a key"=>1, b=>t, c=>null, d=>12345, e=>012345, f=>1.234, g=>2.345e+4')</literal></entry>
<entry><literal>{"a key": "1", "b": "t", "c": null, "d": "12345", "e": "012345", "f": "1.234", "g": "2.345e+4"}</literal></entry>
</row>
2016-02-03 18:56:40 +01:00
<row>
<entry><function>hstore_to_jsonb(hstore)</function><indexterm><primary>hstore_to_jsonb</primary></indexterm></entry>
<entry><type>jsonb</type></entry>
<entry>get <type>hstore</type> as a <type>jsonb</type> value, converting
all non-null values to JSON strings</entry>
<entry><literal>hstore_to_jsonb('"a key"=>1, b=>t, c=>null, d=>12345, e=>012345, f=>1.234, g=>2.345e+4')</literal></entry>
<entry><literal>{"a key": "1", "b": "t", "c": null, "d": "12345", "e": "012345", "f": "1.234", "g": "2.345e+4"}</literal></entry>
</row>
2013-03-10 22:35:36 +01:00
<row>
2013-07-04 17:33:08 +02:00
<entry><function>hstore_to_json_loose(hstore)</function><indexterm><primary>hstore_to_json_loose</primary></indexterm></entry>
2013-03-10 22:35:36 +01:00
<entry><type>json</type></entry>
2013-10-03 01:25:24 +02:00
<entry>get <type>hstore</type> as a <type>json</type> value, but attempt to distinguish numerical and Boolean values so they are unquoted in the JSON</entry>
2013-04-10 15:26:46 +02:00
<entry><literal>hstore_to_json_loose('"a key"=>1, b=>t, c=>null, d=>12345, e=>012345, f=>1.234, g=>2.345e+4')</literal></entry>
2013-03-10 22:35:36 +01:00
<entry><literal>{"a key": 1, "b": true, "c": null, "d": 12345, "e": "012345", "f": 1.234, "g": 2.345e+4}</literal></entry>
</row>
2016-02-03 18:56:40 +01:00
<row>
<entry><function>hstore_to_jsonb_loose(hstore)</function><indexterm><primary>hstore_to_jsonb_loose</primary></indexterm></entry>
<entry><type>jsonb</type></entry>
<entry>get <type>hstore</type> as a <type>jsonb</type> value, but attempt to distinguish numerical and Boolean values so they are unquoted in the JSON</entry>
<entry><literal>hstore_to_jsonb_loose('"a key"=>1, b=>t, c=>null, d=>12345, e=>012345, f=>1.234, g=>2.345e+4')</literal></entry>
<entry><literal>{"a key": 1, "b": true, "c": null, "d": 12345, "e": "012345", "f": 1.234, "g": 2.345e+4}</literal></entry>
</row>
2010-07-02 22:36:49 +02:00
<row>
2013-07-04 17:33:08 +02:00
<entry><function>slice(hstore, text[])</function><indexterm><primary>slice</primary></indexterm></entry>
2010-07-02 22:36:49 +02:00
<entry><type>hstore</type></entry>
2017-10-09 03:44:17 +02:00
<entry>extract a subset of an <type>hstore</type></entry>
2010-07-02 22:36:49 +02:00
<entry><literal>slice('a=>1,b=>2,c=>3'::hstore, ARRAY['b','c','x'])</literal></entry>
<entry><literal>"b"=>"2", "c"=>"3"</literal></entry>
</row>
2007-12-06 05:12:10 +01:00
<row>
2013-07-04 17:33:08 +02:00
<entry><function>each(hstore)</function><indexterm><primary>each</primary></indexterm></entry>
2009-11-30 18:56:09 +01:00
<entry><type>setof(key text, value text)</type></entry>
2017-10-09 03:44:17 +02:00
<entry>get <type>hstore</type>'s keys and values as a set</entry>
2007-12-06 05:12:10 +01:00
<entry><literal>select * from each('a=>1,b=>2')</literal></entry>
<entry>
<programlisting>
key | value
2007-11-11 00:30:46 +01:00
-----+-------
a | 1
b | 2
2007-12-06 05:12:10 +01:00
</programlisting></entry>
</row>
<row>
2013-07-04 17:33:08 +02:00
<entry><function>exist(hstore,text)</function><indexterm><primary>exist</primary></indexterm></entry>
2007-12-06 05:12:10 +01:00
<entry><type>boolean</type></entry>
2017-10-09 03:44:17 +02:00
<entry>does <type>hstore</type> contain key?</entry>
2007-12-06 05:12:10 +01:00
<entry><literal>exist('a=>1','a')</literal></entry>
<entry><literal>t</literal></entry>
</row>
<row>
2013-07-04 17:33:08 +02:00
<entry><function>defined(hstore,text)</function><indexterm><primary>defined</primary></indexterm></entry>
2007-12-06 05:12:10 +01:00
<entry><type>boolean</type></entry>
2017-10-09 03:44:17 +02:00
<entry>does <type>hstore</type> contain non-<literal>NULL</literal> value for key?</entry>
2007-12-06 05:12:10 +01:00
<entry><literal>defined('a=>NULL','a')</literal></entry>
<entry><literal>f</literal></entry>
</row>
<row>
2013-07-04 17:33:08 +02:00
<entry><function>delete(hstore,text)</function><indexterm><primary>delete</primary></indexterm></entry>
2007-12-06 05:12:10 +01:00
<entry><type>hstore</type></entry>
2009-11-30 18:56:09 +01:00
<entry>delete pair with matching key</entry>
2007-12-06 05:12:10 +01:00
<entry><literal>delete('a=>1,b=>2','b')</literal></entry>
2015-08-06 05:03:45 +02:00
<entry><literal>"a"=>"1"</literal></entry>
2007-12-06 05:12:10 +01:00
</row>
2009-09-30 21:50:22 +02:00
<row>
<entry><function>delete(hstore,text[])</function></entry>
<entry><type>hstore</type></entry>
2009-11-30 18:56:09 +01:00
<entry>delete pairs with matching keys</entry>
2009-09-30 21:50:22 +02:00
<entry><literal>delete('a=>1,b=>2,c=>3',ARRAY['a','b'])</literal></entry>
2015-08-06 05:03:45 +02:00
<entry><literal>"c"=>"3"</literal></entry>
2009-09-30 21:50:22 +02:00
</row>
<row>
<entry><function>delete(hstore,hstore)</function></entry>
<entry><type>hstore</type></entry>
2009-11-30 18:56:09 +01:00
<entry>delete pairs matching those in the second argument</entry>
2009-09-30 21:50:22 +02:00
<entry><literal>delete('a=>1,b=>2','a=>4,b=>2'::hstore)</literal></entry>
2015-08-06 05:03:45 +02:00
<entry><literal>"a"=>"1"</literal></entry>
2009-09-30 21:50:22 +02:00
</row>
<row>
2013-07-04 17:33:08 +02:00
<entry><function>populate_record(record,hstore)</function><indexterm><primary>populate_record</primary></indexterm></entry>
2009-09-30 21:50:22 +02:00
<entry><type>record</type></entry>
2017-10-09 03:44:17 +02:00
<entry>replace fields in <type>record</type> with matching values from <type>hstore</type></entry>
2009-09-30 21:50:22 +02:00
<entry>see Examples section</entry>
<entry></entry>
</row>
2007-12-06 05:12:10 +01:00
</tbody>
</tgroup>
</table>
2009-09-30 21:50:22 +02:00
2013-03-10 22:35:36 +01:00
<note>
<para>
2016-02-03 18:56:40 +01:00
The function <function>hstore_to_json</function> is used when
an <type>hstore</type> value is cast to <type>json</type>.
Likewise, <function>hstore_to_jsonb</function> is used when
an <type>hstore</type> value is cast to <type>jsonb</type>.
2013-03-10 22:35:36 +01:00
</para>
</note>
2009-09-30 21:50:22 +02:00
<note>
<para>
The function <function>populate_record</function> is actually declared
2017-10-09 03:44:17 +02:00
with <type>anyelement</type>, not <type>record</type>, as its first argument,
2010-08-17 06:37:21 +02:00
but it will reject non-record types with a run-time error.
2009-09-30 21:50:22 +02:00
</para>
</note>
2007-11-11 00:30:46 +01:00
</sect2>
<sect2>
2007-12-06 05:12:10 +01:00
<title>Indexes</title>
2007-11-11 00:30:46 +01:00
<para>
2017-10-09 03:44:17 +02:00
<type>hstore</type> has GiST and GIN index support for the <literal>@></literal>,
<literal>?</literal>, <literal>?&</literal> and <literal>?|</literal> operators. For example:
2007-11-11 00:30:46 +01:00
</para>
2010-07-29 21:34:41 +02:00
<programlisting>
2009-09-30 21:50:22 +02:00
CREATE INDEX hidx ON testhstore USING GIST (h);
2007-12-06 05:12:10 +01:00
2009-09-30 21:50:22 +02:00
CREATE INDEX hidx ON testhstore USING GIN (h);
2010-07-29 21:34:41 +02:00
</programlisting>
2009-09-30 21:50:22 +02:00
<para>
2017-10-09 03:44:17 +02:00
<type>hstore</type> also supports <type>btree</type> or <type>hash</type> indexes for
the <literal>=</literal> operator. This allows <type>hstore</type> columns to be
declared <literal>UNIQUE</literal>, or to be used in <literal>GROUP BY</literal>,
<literal>ORDER BY</literal> or <literal>DISTINCT</literal> expressions. The sort ordering
for <type>hstore</type> values is not particularly useful, but these indexes
may be useful for equivalence lookups. Create indexes for <literal>=</literal>
2009-11-30 18:56:09 +01:00
comparisons as follows:
2009-09-30 21:50:22 +02:00
</para>
2010-07-29 21:34:41 +02:00
<programlisting>
2009-09-30 21:50:22 +02:00
CREATE INDEX hidx ON testhstore USING BTREE (h);
CREATE INDEX hidx ON testhstore USING HASH (h);
2010-07-29 21:34:41 +02:00
</programlisting>
2007-11-11 00:30:46 +01:00
</sect2>
<sect2>
<title>Examples</title>
<para>
2007-12-06 05:12:10 +01:00
Add a key, or update an existing key with a new value:
2010-07-29 21:34:41 +02:00
<programlisting>
2011-11-08 03:47:45 +01:00
UPDATE tab SET h = h || hstore('c', '3');
2010-07-29 21:34:41 +02:00
</programlisting>
</para>
2007-12-06 05:12:10 +01:00
2007-11-11 00:30:46 +01:00
<para>
Delete a key:
2010-07-29 21:34:41 +02:00
<programlisting>
2007-12-06 05:12:10 +01:00
UPDATE tab SET h = delete(h, 'k1');
2010-07-29 21:34:41 +02:00
</programlisting>
</para>
2009-09-30 21:50:22 +02:00
<para>
2017-10-09 03:44:17 +02:00
Convert a <type>record</type> to an <type>hstore</type>:
2010-07-29 21:34:41 +02:00
<programlisting>
2009-09-30 21:50:22 +02:00
CREATE TABLE test (col1 integer, col2 text, col3 text);
INSERT INTO test VALUES (123, 'foo', 'bar');
SELECT hstore(t) FROM test AS t;
hstore
---------------------------------------------
2009-11-30 18:56:09 +01:00
"col1"=>"123", "col2"=>"foo", "col3"=>"bar"
2009-09-30 21:50:22 +02:00
(1 row)
2010-07-29 21:34:41 +02:00
</programlisting>
</para>
2009-09-30 21:50:22 +02:00
<para>
2017-10-09 03:44:17 +02:00
Convert an <type>hstore</type> to a predefined <type>record</type> type:
2010-07-29 21:34:41 +02:00
<programlisting>
2009-09-30 21:50:22 +02:00
CREATE TABLE test (col1 integer, col2 text, col3 text);
SELECT * FROM populate_record(null::test,
2009-11-30 18:56:09 +01:00
'"col1"=>"456", "col2"=>"zzz"');
2009-09-30 21:50:22 +02:00
col1 | col2 | col3
------+------+------
456 | zzz |
(1 row)
2010-07-29 21:34:41 +02:00
</programlisting>
</para>
2009-09-30 21:50:22 +02:00
<para>
2017-10-09 03:44:17 +02:00
Modify an existing record using the values from an <type>hstore</type>:
2010-07-29 21:34:41 +02:00
<programlisting>
2009-09-30 21:50:22 +02:00
CREATE TABLE test (col1 integer, col2 text, col3 text);
INSERT INTO test VALUES (123, 'foo', 'bar');
2009-11-30 18:56:09 +01:00
SELECT (r).* FROM (SELECT t #= '"col3"=>"baz"' AS r FROM test t) s;
2009-09-30 21:50:22 +02:00
col1 | col2 | col3
------+------+------
123 | foo | baz
(1 row)
2010-07-29 21:34:41 +02:00
</programlisting>
</para>
2007-11-11 00:30:46 +01:00
</sect2>
<sect2>
<title>Statistics</title>
2007-12-06 05:12:10 +01:00
2007-11-11 00:30:46 +01:00
<para>
2017-10-09 03:44:17 +02:00
The <type>hstore</type> type, because of its intrinsic liberality, could
2007-12-06 05:12:10 +01:00
contain a lot of different keys. Checking for valid keys is the task of the
2009-11-30 18:56:09 +01:00
application. The following examples demonstrate several techniques for
checking keys and obtaining statistics.
2007-11-11 00:30:46 +01:00
</para>
<para>
2007-12-06 05:12:10 +01:00
Simple example:
2010-07-29 21:34:41 +02:00
<programlisting>
2009-11-30 18:56:09 +01:00
SELECT * FROM each('aaa=>bq, b=>NULL, ""=>1');
2010-07-29 21:34:41 +02:00
</programlisting>
</para>
2007-11-11 00:30:46 +01:00
<para>
2007-12-06 05:12:10 +01:00
Using a table:
2010-07-29 21:34:41 +02:00
<programlisting>
2007-12-06 05:12:10 +01:00
SELECT (each(h)).key, (each(h)).value INTO stat FROM testhstore;
2010-07-29 21:34:41 +02:00
</programlisting>
</para>
2007-11-11 00:30:46 +01:00
2007-12-06 05:12:10 +01:00
<para>
Online statistics:
2010-07-29 21:34:41 +02:00
<programlisting>
2007-12-06 05:12:10 +01:00
SELECT key, count(*) FROM
(SELECT (each(h)).key FROM testhstore) AS stat
GROUP BY key
ORDER BY count DESC, key;
key | count
2007-11-11 00:30:46 +01:00
-----------+-------
line | 883
query | 207
pos | 203
node | 202
space | 197
status | 195
public | 194
title | 190
org | 189
...................
2010-07-29 21:34:41 +02:00
</programlisting>
</para>
2007-11-11 00:30:46 +01:00
</sect2>
2009-09-30 21:50:22 +02:00
<sect2>
<title>Compatibility</title>
<para>
2017-10-09 03:44:17 +02:00
As of PostgreSQL 9.0, <type>hstore</type> uses a different internal
2009-09-30 21:50:22 +02:00
representation than previous versions. This presents no obstacle for
dump/restore upgrades since the text representation (used in the dump) is
unchanged.
</para>
<para>
2009-11-30 18:56:09 +01:00
In the event of a binary upgrade, upward compatibility is maintained by
having the new code recognize old-format data. This will entail a slight
performance penalty when processing data that has not yet been modified by
the new code. It is possible to force an upgrade of all values in a table
2017-10-09 03:44:17 +02:00
column by doing an <literal>UPDATE</literal> statement as follows:
2010-07-29 21:34:41 +02:00
<programlisting>
2009-09-30 21:50:22 +02:00
UPDATE tablename SET hstorecol = hstorecol || '';
2010-07-29 21:34:41 +02:00
</programlisting>
</para>
2009-09-30 21:50:22 +02:00
<para>
Another way to do it is:
2010-07-29 21:34:41 +02:00
<programlisting>
2009-09-30 21:50:22 +02:00
ALTER TABLE tablename ALTER hstorecol TYPE hstore USING hstorecol || '';
2010-07-29 21:34:41 +02:00
</programlisting>
2017-10-09 03:44:17 +02:00
The <command>ALTER TABLE</command> method requires an exclusive lock on the table,
2009-09-30 21:50:22 +02:00
but does not result in bloating the table with old row versions.
</para>
</sect2>
2015-04-26 16:33:14 +02:00
<sect2>
<title>Transforms</title>
<para>
Additional extensions are available that implement transforms for
the <type>hstore</type> type for the languages PL/Perl and PL/Python. The
extensions for PL/Perl are called <literal>hstore_plperl</literal>
and <literal>hstore_plperlu</literal>, for trusted and untrusted PL/Perl.
If you install these transforms and specify them when creating a
function, <type>hstore</type> values are mapped to Perl hashes. The
extensions for PL/Python are
called <literal>hstore_plpythonu</literal>, <literal>hstore_plpython2u</literal>,
and <literal>hstore_plpython3u</literal>
2017-11-23 15:39:47 +01:00
(see <xref linkend="plpython-python23"/> for the PL/Python naming
2015-04-26 16:33:14 +02:00
convention). If you use them, <type>hstore</type> values are mapped to
Python dictionaries.
</para>
</sect2>
2007-11-11 00:30:46 +01:00
<sect2>
<title>Authors</title>
2007-12-06 05:12:10 +01:00
2007-11-11 00:30:46 +01:00
<para>
Oleg Bartunov <email>oleg@sai.msu.su</email>, Moscow, Moscow University, Russia
</para>
2007-12-06 05:12:10 +01:00
2007-11-11 00:30:46 +01:00
<para>
2007-12-06 05:12:10 +01:00
Teodor Sigaev <email>teodor@sigaev.ru</email>, Moscow, Delta-Soft Ltd., Russia
2007-11-11 00:30:46 +01:00
</para>
2009-09-30 21:50:22 +02:00
<para>
2009-11-30 18:56:09 +01:00
Additional enhancements by Andrew Gierth <email>andrew@tao11.riddles.org.uk</email>,
United Kingdom
2009-09-30 21:50:22 +02:00
</para>
2007-11-11 00:30:46 +01:00
</sect2>
2007-12-06 05:12:10 +01:00
</sect1>