🐙
[Rails]通知機能①(ポリモーフィック関連,コールバック)
ポリモーフィック関連(Polymorphic Association)
1つのテーブルが複数の異なるテーブルと関連を持てる仕組み。
通知機能(Notification)の場合、通知の対象が「コメント」だったり、「投稿」だったり、色々なもので通知する。
コメントも投稿もいいねもフォローも、通知する可能性がある。
この場合、post_id
や comment_id
など、各テーブルごとにカラムを作成する必要があるがけど、ポリモーフィック関連を使えば1つのカラムで複数のテーブルに対応できる。
以下、実装手順。
1. モデルとマイグレーションの作成
通知(Notification)モデルを作成
rails g model Notification user:references notifiable:polymorphic read:boolean
マイグレーションファイル
class CreateNotifications < ActiveRecord::Migration[6.1]
def change
create_table :notifications do |t|
t.references :user, null: false, foreign_key: true
# 注目!
t.references :notifiable, polymorphic: true, null: false # ポリモーフィック関連
t.boolean :read, default: false, null: false
t.timestamps
end
end
end
t.references :notifiable, polymorphic: true
によって
notifiable_id
と notifiable_type
の2つのカラムが自動で作成される。
id | user_id | notifiable_id | notifiable_type | read |
---|---|---|---|---|
1 | 1 | 10 | "Post" | false |
2 | 2 | 5 | "Comment" | false |
t.integer :user_id
t.index :user_id
-
notifiable_id
: 関連するデータのID( Post や Comment の ID ) -
notifiable_type
: 関連するテーブル名("Post" や "Comment")(どのモデル(テーブル)のデータか )
2. モデルの設定
通知(Notification)モデル
class Notification < ApplicationRecord
belongs_to :user
belongs_to :notifiable, polymorphic: true
end
投稿(Post)モデル
class Post < ApplicationRecord
has_many :notifications, as: :notifiable, dependent: :destroy
end
コメント(Comment)モデル
class Comment < ApplicationRecord
has_many :notifications, as: :notifiable, dependent: :destroy
end
3. 通知の作成
コールバック(Callback)
ActiveRecord の特定のタイミングで自動的に処理を実行する仕組み。
レコードが作成・更新・削除された時、特定のメソッドを自動で実行できる。
コールバックは、ActiveRecordに元からある機能で、データを作成したり更新したりするタイミングで自動で行われる機能。
コールバックにはいくつか種類があって、それぞれ実行されるタイミングが異なる。
ActiveRecordとは
モデルは、ActiveRecord を継承している。
ActiveRecord
データベースとやりとりするための主要クラスで、以下の機能を持つ。
- データベースのCRUD操作(Create, Read, Update, Delete)
- SQL文の生成と実行
- バリデーションやコールバックのサポート
コールバックの種類
順序 | コールバック名 | 実行タイミング |
---|---|---|
1 | before_validation |
バリデーション実行前 |
2 | after_validation |
バリデーション実行後 |
3 | before_save |
保存処理の実行前 |
4 | around_save |
保存処理の実行前後 |
5 | before_create |
新規作成時の保存処理前 |
6 | around_create |
新規作成時の保存処理前後 |
7 | after_create |
新規作成時の保存処理後 |
8 | after_save |
保存処理後(作成と更新両方で実行) |
9a | after_commit |
保存処理後(作成と更新両方で実行・ロールバックしない) |
9b | after_rollback |
ロールバック時に実行 |
今回は「いいね(Favorite)されたときに通知を作成する」という処理なので、「作成時のみ実行される」 after_create
を使う。
下記は、本を作成したタイミングでフォローしているユーザーに通知するという流れ。
book.rb
after_create do
user.followers.each do |follower|
notifications.create(user_id: follower.id)
end
end
同時にいいね機能とフォロー・フォロワー機能の追加も進めてしまったので、今日はひとまずここまで!
参考文献
Discussion