Join dvakrát té samé tabulky s aliasem

tkn
Člen | 12
+
0
-

Ahoj,

potřeboval bych poradit. Mám tabulku Lead, ve ktéré jsou sloupce id_user_create a id_user_update a v gridu se ji snažím napojit na tabulku users abych viděl jméno uživatele který záznam vytvořil i toho kdo záznam upravil.

$leads = $this->database->table('lead')
                ->select('lead.*, (uc.first_name || \' \' || uc.last_name) AS userCreate, (uu.first_name || \' \' || uu.last_name) AS userUpdate')
                ->alias('user', 'uc')
                ->joinWhere('uc', ['lead.id_user_create = uc.id'])
                ->alias('user', 'uu')
                ->joinWhere('uu', ['lead.id_user_update = uu.id']);

což mi generuje SQL

SELECT "lead".*, ("uc"."first_name" || ' ' || "uc"."last_name") AS "userCreate", ("uu"."first_name"
|| ' ' || "uu"."last_name") AS "userUpdate"
FROM "lead"
LEFT JOIN "public"."user" "uc" ON "lead"."id_user_create" = "uc"."id" AND ("lead"."id_user_create" =
"uc"."id")
LEFT JOIN "public"."user" "uu" ON "lead"."id_user_create" = "uu"."id" AND ("lead"."id_user_update" =
"uu"."id")
ORDER BY "id"
LIMIT 20

kde je problém s tou dvojitou podmínkou ON. Může mi někdo prosím vysvětlit, co dělám špatně?

DB je Postgre, Nette 2.4

CZechBoY
Člen | 3608
+
0
-

A jakej je problém s tou dvojitou podmínkou? Pokud tam nechceš dvakrát to stejný, tak zkus odebrat ty ->joinWhere.

tkn
Člen | 12
+
0
-

Když odeberu ->joinWhere

tak tam zbyde kod

$leads = $this->database->table('lead')
                ->select('lead.*, (uc.first_name || \' \' || uc.last_name) AS userCreate, (uu.first_name || \' \' || uu.last_name) AS userUpdate')
                ->alias('user', 'uc')
                ->alias('user', 'uu');

což generuje SQL

SELECT "lead".*, ("uc"."first_name" || ' ' || "uc"."last_name") AS "userCreate", ("uu"."first_name"
|| ' ' || "uu"."last_name") AS "userUpdate"
FROM "lead"
LEFT JOIN "public"."user" "uc" ON "lead"."id_user_create" = "uc"."id"
LEFT JOIN "public"."user" "uu" ON "lead"."id_user_create" = "uu"."id"
ORDER BY "id"
LIMIT 20

a to taky není to co potřebuju. To SQL v mém první příspěvku by bylo ok, kdyby tam zbyla jen ta podmínka ON, která je v závorce.

CZechBoY
Člen | 3608
+
+1
-

jo už to chápu – ty chceš join pomocí id_user_create a ještě k tomu další join pomocí id_user_update
Nejde do závorky označit přes jakej sloupec se má joinovat? Něco jako

$leads = $this->database->table('lead')
                ->select('lead.*, (uc.first_name || \' \' || uc.last_name) AS userCreate, (uu.first_name || \' \' || uu.last_name) AS userUpdate')
                ->alias('user(id_user_create)', 'uc')
                ->alias('user(id_user_update)', 'uu');

?

tkn
Člen | 12
+
0
-

To mi udělá dotaz, kde je zase to ON špatně:

SELECT "lead".*, ("uc"."first_name" || ' ' || "uc"."last_name") AS "userCreate", ("uu"."first_name"
|| ' ' || "uu"."last_name") AS "userUpdate"
FROM "lead"
LEFT JOIN "public"."user" "uc" ON "lead"."id_user_create" = "uc"."id"
LEFT JOIN "public"."user" "uu" ON "lead"."id_user_create" = "uu"."id"
ORDER BY "id"
LIMIT 20

Ale celé se to chová nějak divně, protože i když tam nechám jen tohle:

$leads = $this->database->table('lead')
                ->select('lead.*, (uu.first_name || \' \' || uu.last_name) AS userUpdate')
                ->alias('user(id_user_update)', 'uu');

tak mi to generuje tohle SQL a popravdě vůbec nechápu, proč to tam furt cpe id_user_create, když ho nikde nepoužívám

SELECT "lead".*, ("uu"."first_name" || ' ' || "uu"."last_name") AS "userUpdate"
FROM "lead"
LEFT JOIN "public"."user" "uu" ON "lead"."id_user_create" = "uu"."id"
ORDER BY "id"
LIMIT 20
tkn
Člen | 12
+
+1
-

Tak solved, nakonec jsem to udělal jinak bez těch aliasů, ale stejně moc nevím, proč to předtím nefungovalo :(

$leads = $this->database->table('lead')
                ->select('lead.*,(id_user_create.first_name || \' \' || id_user_create.last_name) AS cusername, (id_user_update.first_name || \' \' || id_user_update.last_name) AS uusername');
norbe
Backer | 405
+
0
-

Je to jednoduché, nette hledá cizí klíče dle názvu, který zadáš a vezme první který najde (tabulku, na kterou se to má najoinovat si to vezme z definice toho cizího klíče). Ty jsi předtím zadával user. To najde jak id_user_create, tak id_user_update…

Tzn. fungovalo by ti

$leads = $this->database->table('lead')
                ->select('lead.*, (uc.first_name || \' \' || uc.last_name) AS userCreate, (uu.first_name || \' \' || uu.last_name) AS userUpdate')
                ->alias('id_user_create', 'uc')
                ->alias('id_user_update', 'uu');