LoginSignup
42
21

More than 3 years have passed since last update.

Railsで別名の外部キーを設定する方法

Posted at

Railsで別名の外部キーを設定する方法

1対多のリレーションで別名の外部キーのカラム名を設定した記録です。

背景

通常、1対多のリレーションではTeamモデルにはuserと書くことが多いが、
Teamの所有者であることを強調したいので別名カラムownerを設定する必要がありました。

image.png

目次


動作環境

OS : macOS Mojave 10.14.6
ruby : 2.6.3p62
rails : 5.2.4

結論

以下のステップで実現できました。

STEP1.別名カラムをTeamsモデルに作成

マイグレーション

1. 新規テーブルの場合

migrationfile1.rb
class CreateTeams < ActiveRecord::Migration[5.2]
  def change
    create_table :teams do |t|
      t.string :name
      t.integer :owner_id, index: true

      t.timestamps
    end
    add_foreign_key :teams, :users, column: :owner_id
  end
end

2. 既存テーブルに追加する場合

migrationfile.rb
class AddUserRefToTeams < ActiveRecord::Migration[5.2]
  def change
    add_reference :teams, :owner, foreign_key: { to_table: :users }
  end
end

マイグレーションの実行

rails db:migrate
schema
  create_table "teams", force: :cascade do |t|
    t.string "name"
    t.integer "owner_id"
    t.datetime "created_at", null: false
    t.datetime "updated_at", null: false
    t.string "icon"
    t.index ["owner_id"], name: "index_teams_on_owner_id"
  end

  add_foreign_key "teams", "users", column: "owner_id"

STEP2.UserモデルとTeamモデルにリレーションを設定

user.rb
class User < ApplicationRecord
  has_many :teams, foreign_key: :owner_id
end
team.rb
class Team < ApplicationRecord
  belongs_to :owner, class_name: 'User', foreign_key: :owner_id
end

結果

以下のようにteam.ownerでチーム所有者のuser情報が取り出せています。
image.png

ポイント

リレーションにクラス名をつけること

userカラムの場合はteamモデルにclass_nameはつけませんが、
別名の場合はclass_nameをつけないとエラーになってしまいました。

belongs_to :owner, class_name: 'User', foreign_key: :owner_id

おわりに

今回の件で以下のことを学びました。
別名外部キーの設定方法

42
21
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
42
21