Open Minminzei opened 2 years ago
user has one phone
users | id | name |
---|---|---|
1 | 田中 |
phones | id | user_id | model |
---|---|---|---|
1 | 1 | iPhone |
query
// 田中さんはiPhoneを所有しています。
[ORM] User.find(1).phone;
[SQL] select * from users inner join phones on users.id = phones.user_id where users.id = 1;
phone belongs to user
// iPhoneは田中さんに所有されています。
[ORM] Phone.find(1).user;
[SQL] select * from phones inner join users on users.id = phones.user_id where phones.id = 1;
user has one phone through orders
users | id | name |
---|---|---|
1 | 田中 |
orders | id | user_id | phone_id | order_date |
---|---|---|---|---|
1 | 1 | 1 | 12/1 |
phones | id | model |
---|---|---|
1 | iPhone |
query
// 田中さんは注文No3を通して、12/1にiPhoneを買いました。
[ORM] User.find(1).phones
[SQL]
data = select * from users wehre name = "田中";
select * from orders
inner join phones on phones.id = orders.phone_id
where orders.user_id = data.id;
user has many orders
users | id | name |
---|---|---|
1 | 田中 |
orders | id | user_id | order_date |
---|---|---|---|
1 | 1 | 12/1 | |
2 | 1 | 12/3 |
query
// 田中さんは12/1,12/3に注文をしました。
[ORM] User.orders;
[SQL]
select * from users;
select * from orders where orders.user_id = 1;
select * from orders where orders.user_id = 2;
select * from orders where orders.user_id = 3;
[ORM] User.includes([:orders]).orders;
select * from users;
select * from orders where orders.user_id in (1, 2, 3);
user has many phones through orders
users | id | name |
---|---|---|
1 | 田中 |
orders | id | user_id | phone_id | order_date |
---|---|---|---|---|
1 | 1 | 1 | 12/1 | |
2 | 1 | 2 | 12/3 |
phones | id | model |
---|---|---|
1 | iPhone | |
2 | Android |
query
// 田中さんは12/1の注文でiPhoneを、12/3の注文でAndroidを買いました。
[ORM] User.find(1).phones
[SQL]
select * from users where users.id = 1;
select * from orders inner join phones on orders.phone_id = phones.id
where orders.user_id = 1;
user has many phones through orders, and phone has many users through orders.
users | id | name |
---|---|---|
1 | 田中 | |
2 | 佐藤 |
orders | id | user_id | phone_id | order_date |
---|---|---|---|---|
1 | 1 | 1 | 12/1 | |
2 | 1 | 2 | 12/1 | |
3 | 2 | 1 | 12/1 | |
4 | 2 | 2 | 12/1 |
phones | id | model |
---|---|---|
1 | iPhone | |
2 | Android |
query
[ORM] User.all.phones
[SQL]
select * from users;
select * from orders
inner join phones on phones.id = orders.phone_id
where orders.user_id In (1, 2);
多態性。類似のテーブルを1つにまとめ共通化する。**_id
と**_type
で関連付ける
polymorphic がない場合
users | id | name |
---|---|---|
1 | 田中 |
user_images | id | user_id | url |
---|---|---|---|
1 | 1 | https://image.com/user.png |
phones | id | model |
---|---|---|
1 | iPhone |
phone_images | id | phone_id | url |
---|---|---|---|
1 | 1 | https://image.com/phones.png |
user_images と phone_images が冗長なので images テーブルに共通化する。
images | id | imageable_id | imageable_type | url |
---|---|---|---|---|
1 | 1 | users | https://image.com/users.png | |
2 | 1 | phones | https://image.com/phones.png |
query
// 田中さんのアバターを取得。
select * from images inner join users on users.id = images.imageable_id and imageable_type = 'users' where users.id = 1;
単一テーブル継承。1つのテーブルを複数の model として運用する。
STI を使わない場合
offline_events | id | title | date | city |
---|---|---|---|---|
1 | リアルイベント! | 12/1 | 東京都渋谷区 |
online_events | id | title | date | platform |
---|---|---|---|---|
1 | オンラインイベント! | 12/2 | youtube |
STI を使う場合
events | id | type | title | date | city | platform |
---|---|---|---|---|---|---|
1 | offline | リアルイベント! | 12/1 | 東京都渋谷区 | null | |
2 | online | オンラインイベント! | 12/2 | null | youtube |
class CommonEvent {
id: number;
title: string;
date: Date;
}
class OfflineEvent extends CommonEvent {
city: string;
}
class OnlineEvent extends CommonEvent {
platform: "youtube" | "instagram";
}
Relayテスト!! Relayテスト!! Relayテスト!!