気軽に楽しくプログラムと遊ぶ

自分が興味があってためになるかもって思う情報を提供しています。

Rails ユーザーと投稿を結びつける

今回はプロゲートの中級 4章「ユーザーをscaffoldしよう」、5章「ユーザーと投稿を結びつけよう」をやっていきます。

ユーザーをscaffoldする

$ rails g scafolld User name:string email:string
$ rake db:migrate

Userのカラムはカンマなどの区切りなしに列挙していく。
migrateで作成モデルをDBへ反映する。

migration

テーブルやカラムの構造を変更できる仕組みをmigrationと呼ぶ

下記のコマンドでmigrationファイルが作成される。

$ rails g migration add_user_id_to_notes user_id:integer

下記のようなファイルが生成される。 20151129025836_add_user_id_to_notes.rb

class AddUserIdToNotes < ActiveRecord::Migrate
  def change
    add_column :notes, :user_id, :integer
  end
end

上記migrationファイルは下記コマンドで反映させる。

rake db:migrate

Noteモデルにユーザーを紐付ける

以前作成したNoteモデル(記事)作成時にユーザーIDでユーザーを記事に紐付ける。

ユーザーモデルを作成する

rails g migration add_user_id_to_notes user_id:integer

記事作成時に登録ユーザーIDを選択できるようにする

<%= form_for @note do |f| %>
  ユーザーID
  <%= f.collection_select :user_id, User.all, :id, :id %>
<% end %>

ユーザーIDを保存できるようにする

notes_controller.rb

・
・
  def note_params
    # ストロングパラメータへuser_idを許可する設定を追記
    params.requier(:note).permit(:title, :content, :user_id)
  end
end

バリデーションも追加する。

class Note < Activerecord::Base
  ・
  ・
  validates :user, presence:true
end

ユーザーのnote一覧を表示する

ユーザープロフィール画面に投稿したnote一覧を表示する。

class UsersController < ApplicationController
  ・
  ・
  def show
    @user = User.find(params[:id])
    # モデルクラスのwhereメソッドへ検索カラムと値を渡すと合致するモデルを配列形式で返却
    @notes = Note.where(:user_id, @user.id)
  end
  ・
  ・
end

viewの記述を修正する。

<% @notes.each do |note| %>
  <li><%= link_to note.title, note %></li>
<% end %>

一対多

userとnoteを関連付ける仕組みを学んで行く。

has_many

userは複数のnote(記事)を保持する。この関係をモデルに記載すると関連記事を取得可能となる。

class User < Activerecord::Base
  has_many :notes #noteを複数保持するので複数系で記載
end

notesを取得する処理は下記のとおりに書き換えることができる。
user_controller.rb

def show
 #@user = User.find(params[:id])
 #@notes = Note.where(:user_id, @user.id)
 # ↓

 # has_many :notesの記述でユーザーに関連するnoteをすべて取得できる。
 @notes = @user.notes
end

belongs_to

note(記事)は1ユーザーに所属する。この関係をモデルに記載すると所属ユーザーが取得可能となる。

class Note < Activerecord::Base
  belong_to :user #記事が所属するユーザーは1人なので単数形
end

note情報を表示する際に、所属しているユーザー情報も同時に取得可能となる。
notes/index.rb

<% @notes.each do |note| %>
  <%= note.user.name %>
<% end %>