Re: Altering array(composite-types) without breaking code when inserting them and similar questions

From: Dorian Hoxha <dorian(dot)hoxha(at)gmail(dot)com>
To: Merlin Moncure <mmoncure(at)gmail(dot)com>
Cc: Rob Sargentg <robjsargent(at)gmail(dot)com>, Fede Martinez <federicoemartinez(at)gmail(dot)com>, PostgreSql-general <pgsql-general(at)postgresql(dot)org>
Subject: Re: Altering array(composite-types) without breaking code when inserting them and similar questions
Date: 2014-04-29 19:40:08
Message-ID: CANsFX04CUZHXhsfDFhQR7K3jYpo+GH5UMiPkn3Z7h_Vy3sFrxQ@mail.gmail.com
Views: Raw Message | Whole Thread | Download mbox | Resend email
Thread:
Lists: pgsql-general

So :

1. drop function
2. alter type: add column
3. create again function with new default argument in a transaction ?

On Tue, Apr 29, 2014 at 4:22 PM, Merlin Moncure <mmoncure(at)gmail(dot)com> wrote:

> On Sun, Apr 27, 2014 at 4:57 PM, Dorian Hoxha <dorian(dot)hoxha(at)gmail(dot)com>
> wrote:
> > Since my alternative is using json, that is heavier (need to store keys
> in
> > every row) than composite-types.
> > Updating an element on a specific composite_type inside an array of them
> is
> > done by UPDATE table SET composite[2].x = 24;
> >
> > So last standing question, is it possible to insert an array of
> > composite_types by not specifying all of the columns for each
> composite_type
> > ?
> > So if i later add other columns to the composite_type, the insert query
> > doesn't break ?
>
> One way to do it is via 'type constructor function'.
>
> postgres=# create type foo_t as (a int, b int);
> postgres=# create function foo_t(a int, b int) returns foo_t as $$
> select row(a,b)::foo_t; $$ language sql stable;
> postgres=# create table bar(f foo_t);
> postgres=# insert into bar VALUES ((1,2)::foo_t); -- not tolerant to
> changes
> postgres=# insert into bar VALUES (foo_t(1,2)); -- works fine
>
> now, to extend the field, we can overload the function making sure to
> default the 3rd argument.
> alter type foo_t add attribute c text;
> drop function foo_t(int, int); -- must do this to make function unambiguous
> create function foo_t(a int, b int, c text = null) returns foo_t as $$
> select row(a,b,c)::foo_t; $$ language sql stable;
>
> postgres=# INSERT INTO bar VALUES ((1,2)::foo_t);
> postgres=# insert into bar VALUES (foo_t(1,2,'test')); -- works fine
>
> This technique is somewhat dubious, but if for whatever reason you
> absolutely must preserve client sql in the face of server changes it
> might work.
>
> merlin
>

In response to

Responses

Browse pgsql-general by date

  From Date Subject
Next Message Stephen Frost 2014-04-29 20:53:21 Re: Planned downtime @ Rackspace - 2014-04-29 2100-2200 UTC
Previous Message Vick Khera 2014-04-29 18:36:59 Re: reindexdb