メインコンテンツまでスキップ

リレーション定義

複数のシート間のリレーション(関連)を定義することで、include によるリレーション先データの取得や、where でのリレーション条件フィルタが可能になります。

説明例用のシート

以降のリレーションドキュメントでは、以下のシートを例として使用します。

Users シート

idnameemail
1Alicealice@example.com
2Bobbob@example.com
3Charliecharlie@example.com

Posts シート

idtitleauthorIdpublished
1初めての投稿1true
2GAS の使い方1true
3下書き記事2false

Profiles シート

iduserIdbio
11エンジニアです
22デザイナーです

Tags シート

idname
1GAS
2JavaScript

PostTags シート(中間テーブル)

postIdtagId
11
12
21

基本的な定義方法

GassmaClient のコンストラクタに relations オプションを渡すことで、シート間のリレーションを定義できます。

const gassma = new Gassma.GassmaClient({
relations: {
// シート名(スプレッドシート上の実際のシート名と一致させる)
Users: {
// リレーション名(自由な名前を付けられます。include や where で使用するキー名になります)
posts: {
type: "oneToMany",
to: "Posts",
field: "id",
reference: "authorId",
},
},
},
});

スプレッドシート ID を指定する場合は id も一緒に渡します。

const gassma = new Gassma.GassmaClient({
id: "XXXXXXXXXXXXXXXXXXX",
relations: {
// ...
},
});

リレーション定義のキー

キー名内容省略備考
typeリレーションの種類不可oneToMany / oneToOne / manyToOne / manyToMany
to関連先のシート名不可
field自シート側のカラム名不可FK または PK
reference関連先シート側のカラム名不可
through中間テーブルの設定manyToMany の場合は必須
onDelete削除時のアクションCascade / SetNull / Restrict / NoAction

リレーションの種類

oneToMany(1 対 多)

1 つの親レコードに対して、複数の子レコードが紐づく関係です。

例:1 人のユーザーが複数の投稿を持つ

relations: {
Users: {
posts: {
type: "oneToMany",
to: "Posts",
field: "id", // Users の PK
reference: "authorId", // Posts の FK
},
},
}

include で取得すると配列が返ります。

manyToOne(多 対 1)

oneToMany の逆方向です。子レコードから親レコードへの参照を定義します。

例:投稿から著者(ユーザー)を取得

relations: {
Posts: {
author: {
type: "manyToOne",
to: "Users",
field: "authorId", // Posts の FK
reference: "id", // Users の PK
},
},
}

include で取得すると単一オブジェクトまたは null が返ります。

oneToOne(1 対 1)

1 つのレコードに対して、1 つだけ紐づくレコードがある関係です。

例:ユーザーとプロフィール

relations: {
Users: {
profile: {
type: "oneToOne",
to: "Profiles",
field: "id", // Users の PK
reference: "userId", // Profiles の FK
},
},
}

include で取得すると単一オブジェクトまたは null が返ります。同じ reference 値を持つレコードが複数存在する場合はエラーとなります。

manyToMany(多 対 多)

中間テーブルを経由して、多対多の関係を定義します。

例:投稿とタグ

relations: {
Posts: {
tags: {
type: "manyToMany",
to: "Tags",
field: "id", // Posts の PK
reference: "id", // Tags の PK
through: {
sheet: "PostTags", // 中間テーブルのシート名
field: "postId", // 中間テーブルにおける Posts 側の FK
reference: "tagId", // 中間テーブルにおける Tags 側の FK
},
},
},
}

include で取得すると配列が返ります。

複数リレーションの定義

1 つのシートに複数のリレーションを定義できます。また、複数シートにまたがって定義することもできます。

const gassma = new Gassma.GassmaClient({
relations: {
Users: {
posts: {
type: "oneToMany",
to: "Posts",
field: "id",
reference: "authorId",
},
profile: {
type: "oneToOne",
to: "Profiles",
field: "id",
reference: "userId",
},
},
Posts: {
author: {
type: "manyToOne",
to: "Users",
field: "authorId",
reference: "id",
},
tags: {
type: "manyToMany",
to: "Tags",
field: "id",
reference: "id",
through: {
sheet: "PostTags",
field: "postId",
reference: "tagId",
},
},
},
},
});

バリデーション

リレーション定義に誤りがある場合、GassmaClient のインスタンス生成時にエラーがスローされます。

エラー原因
RelationSheetNotFoundErrorrelations のキー、tothrough.sheet に指定したシート名が存在しない
RelationMissingPropertyErrortype / to / field / reference が欠けている。manyToMany で through が欠けている
RelationInvalidPropertyTypeErrorプロパティの型が string でない
RelationInvalidTypeErrortype が 4 種類のいずれでもない
RelationInvalidOnDeleteErroronDelete が 4 種類のいずれでもない
RelationColumnNotFoundErrorfield / reference に指定したカラムがシート上に存在しない