2
1

More than 1 year has passed since last update.

投稿に別のテーブルの情報を紐づける

Last updated at Posted at 2022-12-23

タグ機能をCRUD2つ実装して実現しているイメージです。
「授業に受講している学生を登録したい」「コーディネートに洋服の情報を紐づけたい」「タグ機能をseedファイルを使わずに実装したい」etc...
こういったモデルの多対多の関連付けをした投稿を実装したい方は一度読んでみてください。

【 目次 】

  1. 開発環境と前提
  2. 概要と方針
  3. 実装するコード

【 開発環境と前提 】

< 開発環境 >
・ruby 3.0.4
・rails 6.1.6

< 前提 >
・Studentモデル、コントローラーのCRUD機能実装済み
 ・カラムはname/string型


【 概要と方針 】

< 概要 >
・lesson投稿時に、登録されている学生を複数選択して投稿できるようにする。

< 方針 >
・Lessonモデル、コントローラーのCRUD実装
 ・カラムはname/string型
・中間テーブルの作成
・アソシエーションの記述
・viewの記述

< 完成図 >
※また貼っときます。


【 実装するコード 】

lessonモデルとlesson-studentの中間テーブルを作成。

terminal
$rails g model Lesson name:string
$rails g model Lesson_student_relation student:references lesson:references
$rails db:migrate

アソシエーションを記述する。

lesson_student_relation.rb
class LessonStudentRelation < ApplicationRecord
  belongs_to :student
  belongs_to :lesson
end
student.rb
class Student < ApplicationRecord
    #nameカラムが空でないことを指定
    validates :name, presence: true

    #studentsテーブルから中間テーブルに対する関連付け
    has_many :lesson_student_relations, dependent: :destroy
    #studentsテーブルから中間テーブルを介してLessonsテーブルへの関連付け
    has_many :lessons, through: :lesson_student_relations, dependent: :destroy
end
lesson.rb
class Lesson < ApplicationRecord
    #nameカラムが空でないことを指定
    validates :name, presence: true
    
    #Lessonsテーブルから中間テーブルに対する関連付け
    has_many :lesson_student_relations, dependent: :destroy
    #Lessonsテーブルから中間テーブルを介してStudentsテーブルへの関連付け
    has_many :students, through: :lesson_student_relations, dependent: :destroy
end

lessonsコントローラーの作成。

terminal
rails g controller lessons

コントローラーの中身を記述。

lessons_controller.rb
class LessonsController < ApplicationController
    
    def index
        @lessons = Lesson.all
    end

    def new
        @lesson = Lesson.new
    end

    def create
        lesson = Lesson.new(lesson_params)

        if lesson.save
            redirect_to :action => "index"
        else
            redirect_to :action => "new"
        end
    end

    def show
        @lesson = Lesson.find(params[:id])
    end

    def edit
        @lesson = Lesson.find(params[:id])
    end

    def update
        lesson = Lesson.find(params[:id])
        if lesson.update(lesson_params)
          redirect_to :action => "show", :id => lesson.id
        else
          redirect_to :action => "new"
        end
    end

    def destroy
        lesson = Lesson.find(params[:id])
        lesson.destroy
        redirect_to action: :index
    end

    private
    def lesson_params
        params.require(:lesson).permit(:name, student_ids: [])
    end
end

ルートの記述

routes.rb
Rails.application.routes.draw do
  # ~中略~
  resources :students
  resources :lessons
  # ~中略~
end

viewの記述。授業投稿ページ。editも同様に書いてください。

views/lessons/new.html.erb
<%= form_for @lesson do |f| %>
    <%= f.label :name %>
    <%= f.text_field :name, :size => 140 %>
    <div class='form-group'>
        <%= f.collection_check_boxes(:student_ids, Student.all, :id, :name) do |student| %>
            <div class='form-check'>
                <%= student.label class: 'form-check-label' do %>
                    <%= student.check_box class: 'form-check-input' %>
                    <%= student.text %>
                <% end %>
            </div>
        <% end %>
    </div>
    <%= f.submit '登録' %>
<% end %>

<%= link_to "授業一覧へ", lessons_path %>

授業一覧ページ。

views/lessons/index.html.erb
<%= link_to "生徒一覧へ", students_path %>
<%= link_to "新規授業登録する", new_lesson_path %>
<br>
<% @lessons.each do |l| %>
  <%= l.name %>
  <%= link_to "詳細", lesson_path(l.id) %>
  <%= link_to "編集", edit_lesson_path(l.id) %>
  <%= button_to "削除", lesson_path(l.id), method: :delete %>
<% end %>

授業詳細ページ。

views/lessons/show.html.erb
<h4><%= @lesson.name %></h4>
<% @lesson.students.each do |s| %>
  <span><%= s.name %></span>
<% end %>

<%= link_to "編集する", edit_lesson_path(@lesson.id) %>
<%= link_to "授業一覧へ", lessons_path %>

生徒の詳細ページに参加授業一覧を表示。

views/students/show.html.erb
<h3>Student詳細</h3>

 <%# ~中略~ %>

  <h5>参加授業</h5>
  <% @student.lessons.each do |l| %>
    <p><%= l.name %><p>
  <% end %>

 <%# ~中略~ %>

一旦以上です。ちょっと爆速で書いたので、抜けもれ・エラーがあれば遠慮なくFBください。

2
1
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
2
1