Объединять таблицы в столбцах составного внешнего / первичного ключа в запросе

CREATE TABLE subscription (
   magazine_id bigint,
   user_id     bigint,
   PRIMARY KEY (magazine_id, user_id)
)

CREATE TABLE delivery (
   magazine_id bigint,
   user_id     bigint,
   FOREIGN KEY (subscription) REFERENCES subscription (magazine_id, user_id)
)

Что такое хороший способ запросить доставку по конкретной подписке? Есть ли способ присвоения имени столбцу PRIMARY KEY (magazine_id, user_id) и соответствующий внешний ключ, чтобы я мог запросить вот так

SELECT *
FROM subscription
JOIN delivery ON (delivery.subscription_fk = delivery.subscription_pk)

Примечание: я могу написать что-то вроде этого:

SELECT *
FROM subscription
JOIN delivery ON (delivery.magazine_id = subscription.magazine_id
              AND delivery.user_id = subscription.user_id)

Однако у меня сложилось впечатление, что для этого есть менее многословный способ.

2 ответа

Решение

E сть NATURAL JOIN:

SELECT *
FROM subscription NATURAL JOIN delivery

Цитирование руководства поSELECT:

NATURAL

NATURAL это стенография для USING список, в котором упоминаются все столбцы в двух таблицах с одинаковыми именами.

Это будет работать для вашей тестовой установки, но не будет строго выполнять то, что вы просите. Соединение основано на всех столбцах с одинаковым именем. Внешние ключи не рассматриваются.

Упростите код / ​​меньше подробностей

Для начала, вы можете использовать псевдонимы таблиц и вам не нужны круглые скобки вокруг условий соединения с ON (в отличие от USING):

SELECT *
FROM   subscription s
JOIN   delivery     d ON d.magazine_id = s.magazine_id
                     AND d.user_id = s.user_id;

Поскольку имена столбцов в условиях объединения идентичны, вы можете еще больше упростить USING:

SELECT *
FROM   subscription s
JOIN   delivery     d USING (magazine_id, user_id);

Не существует синтаксического варианта создания соединений на основе ограничений внешнего ключа автоматически. Вам придется запросить системные каталоги и динамически построить SQL для этого...

Не delivery имеет два столбца, представляющих внешний ключ? Тогда он должен работать как с некомпозитным первичным ключом SELECT * FROM subscription JOIN delivery ON (delivery.magazine_id = subscription.magazine_id AND delivery.user_id = subscription.user_id),

Другие вопросы по тегам