问题
This is a two-part question. Attached is a diagram for a PostgreSQL database table design. There are four tables. Table Main
has a one-to-many relationship with table Submain
. Table Submain
has a one-many relationship with table Subsub
. The primary keys for all four tables are serial NOT NULL (so they auto-increment). Each table has multiple attributes that are not shown here.
Question 1. Multiple users will access this application and database. When a user accesses an application that uses this database, some of their information will be stored in table Main
. Subsequent information (provided by the user and other results based on the user's input) will be stored in tables Submain
and Subsub
. My thinking is as follows:
- User submits information via a form.
- A
MainId
primary key will be automatically generated and some of the user information will be placed in tableMain
. - A record will be inserted into table
Submain
based on the user's input (items inMain
). How can I determine what the user's primary keyMainId
is so that I can insert it intoSubmain.MainId [FK]
for the new record? - A record will also be inserted into
Subsub
and that information will be based on information in tableSubmain
. Similarly, how can I determineSubmain.Submain [PK]
so that I can use it as the foreign key inSubsub.Submain [FK]
?
Question 2. There is a many-to-many relationship between Main
and Other
(I left out the associative table). However, in order to insert a record into table Other
, information is required from Subsub
. There will be a one-to-one mapping between Subsub
and Other
. Do I need to draw out that one-to-one relationship OR can table Other
be populated based on a complex SELECT/JOIN
statement from table Main
down to table Subsub
? This might be a bad question, but I think that I need to draw a one-to-one relationship and insert a foreign key SubsubId [FK]
into Other
instead of trying a complicated SQL statement.
回答1:
Answer to Q1: Use data-modifying CTEs and return the serial PK with the RETURNING
clause:
WITH ins_main AS (
INSERT INTO main(col1)
VALUES ('some value 1')
RETURNING main_id
)
, ins_submain AS (
INSERT INTO submain (main_id, col2)
SELECT main_id, 'some value 2'
FROM ins_main
RETURNING submain_id
)
INSERT INTO subsub (submain_id, col3)
SELECT submain_id, 'some value 3'
FROM ins_submain;
Requires Postgres 9.1 or later.
Related answers with explanation and links:
- Insert data in 3 tables at a time using Postgres
- PostgreSQL store value returned by RETURNING
来源:https://stackoverflow.com/questions/35906925/how-to-determine-the-auto-generated-primary-key-used-as-a-foreign-key-for-anothe