Anda dapat menggunakan CTE untuk mengambil nilai dari urutan sekali dan gunakan berulang kali :
WITH cte AS (
SELECT nextval('foo_id_seq') AS id
)
INSERT INTO foo (id, ltree)
SELECT id, '1.' || id
FROM cte;
CTE dengan perintah pengubah data memerlukan Postgres 9.1 atau yang lebih baru.
Jika Anda tidak yakin dengan nama urutannya, gunakanpg_get_serial_sequence()
sebagai gantinya:
WITH i AS (
SELECT nextval(pg_get_serial_sequence('foo', 'id')) AS id
)
INSERT INTO foo (id, ltree)
SELECT id, '1.' || id
FROM i;
Jika nama tabel "foo" mungkin tidak unik di semua skema di DB, buat kualifikasi skema. Dan jika ejaan nama apa pun tidak standar, Anda harus mengutip dua kali:
pg_get_serial_sequence('"My_odd_Schema".foo', 'id')
Tes cepat menunjukkan ide @ Mark dengan lastval()
mungkin bekerja juga:
INSERT INTO foo (ltree) VALUES ('1.' || lastval());
-
Anda bisa meninggalkan
id
dari kueri,serial
kolom akan ditetapkan secara otomatis. Tidak ada bedanya. -
Seharusnya tidak ada kondisi balapan di antara baris. Saya mengutip manualnya:
currval
Kembalikan nilai yang paling baru diperoleh oleh
nextval
untuk urutan ini di sesi saat ini. (Kesalahan dilaporkan jikanextval
belum pernah dipanggil untuk urutan ini dalam sesi ini.) Karena ini mengembalikan nilai sesi-lokal, ini memberikan jawaban yang dapat diprediksi apakah sesi lain telah mengeksekusinextval
sejak sesi saat ini.Fungsi ini membutuhkan
USAGE
atauSELECT
hak istimewa pada urutan.
lastval
Kembalikan nilai yang paling baru dikembalikan oleh
nextval
dalam sesi saat ini. Fungsi ini identik dengancurrval
, kecuali bahwa alih-alih mengambil nama urutan sebagai argumen, itu merujuk ke urutan mananextval
baru saja diterapkan pada sesi saat ini. Ini adalah kesalahan untuk memanggillastval
jikanextval
belum dipanggil dalam sesi saat ini.Fungsi ini membutuhkan
USAGE
atauSELECT
hak istimewa pada urutan yang terakhir digunakan.
Penekanan saya yang berani.
Tapi , seperti yang dikomentari @Bernard, bagaimanapun juga bisa gagal:tidak ada jaminan bahwa nilai default terisi (dan nextval()
dipanggil dalam proses) sebelum lastval()
dipanggil untuk mengisi kolom ke-2 ltree
. Jadi tetap dengan solusi pertama dan nextval()
untuk memastikannya.