Você pode usar um CTE para recuperar o valor da sequência uma vez e usá-lo repetidamente :
WITH cte AS (
SELECT nextval('foo_id_seq') AS id
)
INSERT INTO foo (id, ltree)
SELECT id, '1.' || id
FROM cte;
O CTE com um comando de modificação de dados requer o Postgres 9.1 ou posterior.
Se você não tiver certeza sobre o nome da sequência, use
pg_get_serial_sequence()
em vez de:WITH i AS (
SELECT nextval(pg_get_serial_sequence('foo', 'id')) AS id
)
INSERT INTO foo (id, ltree)
SELECT id, '1.' || id
FROM i;
Se o nome da tabela "foo" não for exclusivo em todos os esquemas no banco de dados, qualifique-o pelo esquema. E se a ortografia de qualquer nome não for padrão, você deve usar aspas duplas:
pg_get_serial_sequence('"My_odd_Schema".foo', 'id')
Testes rápidos indicaram a ideia de @Mark com
lastval()
pode trabalhar também:INSERT INTO foo (ltree) VALUES ('1.' || lastval());
-
Você pode simplesmente deixarid
fora da consulta, oserial
coluna será atribuída automaticamente. Não faz diferença.
-
Não deve haver uma condição de corrida entre as linhas. Cito o manual:
currval
Retorna o valor obtido mais recentemente pornextval
para esta sequência na sessão atual. (Um erro é relatado senextval
nunca foi chamado para esta sequência nesta sessão.) Como isso está retornando um valor de sessão local, ele fornece uma resposta previsível se outras sessões executaram ou nãonextval
desde a sessão atual.
Esta função requerUSAGE
ouSELECT
privilégio na sequência.
lastval
Retorna o valor retornado mais recentemente pornextval
na sessão atual. Esta função é idêntica acurrval
, exceto que ao invés de tomar o nome da sequência como um argumento ele se refere a qualquer sequêncianextval
foi aplicado mais recentemente na sessão atual. É um erro chamarlastval
senextval
ainda não foi chamado na sessão atual.
Esta função requerUSAGE
ouSELECT
privilégio na última sequência usada.
Minha ênfase em negrito.
Mas , como @Bernard comentou, ele pode falhar afinal:não há garantia de que o valor padrão seja preenchido (e
nextval()
chamado no processo) antes lastval()
é chamado para preencher a 2ª coluna ltree
. Então fique com a primeira solução e nextval()
para ter certeza.