Penso che il problema qui sia che l'hstore che hai è nullo e null OR qualche hstore è nullo.
La migliore soluzione che ho, che probabilmente non è la soluzione migliore, è creare la tabella con un hstore vuoto predefinito anziché consentire null. Quindi i tuoi esempi funzionano come vorresti:
postgres=# create table htest (t text, h hstore default hstore(array[]::varchar[]));
CREATE TABLE
postgres=# insert into htest (t) values ('key');
INSERT 0 1
postgres=# update htest set h = h || ('foo'=>'bar') where t='key';
UPDATE 1
postgres=# select * from htest;
t | h
-----+--------------
key | "foo"=>"bar"
(1 row)
Sfortunatamente non vedo un modo più pulito per creare un hstore vuoto rispetto a hstore(array[]::varchar[])
ma questo non significa che non ci sia un modo migliore. Potresti incorporarlo nel tuo aggiornamento hstore di prima in questo modo:
update htest set h = coalesce(h, hstore(array[]::varchar[])) || ('foo'=>'bar') where t='key';
In questo modo non è necessario ricreare la tabella. Lo trovo abbastanza grossolano però. Spero che questo aiuti.