44日目 入力コメントをajaxで送信①(コントローラーへのアクション追加)

おはようございます。今日も少しずつ開発を積み重ねていきます。
今までの進捗をまとめたものがこちらになります。

現在、以下のように、入力テキストボックスと縦線の区切りが表示されている見た目の画面のみ用意しています。

今回は入力テキストボックスに何らかの文字列を入力してEnterを押したら、Railsのデータベースへ「Comment」モデルのデータとして登録できるものを作ろうと考えており、その際にはajaxを利用しようと思います。

ajaxとは、Javascriptによる非同期通信を用いてページ全体を読み込まずにページの一部だけ更新できる仕組みであり、詳しくは以下の記事がわかりやすいと思います。

ajaxを利用する際、まずは入力テキストエリアで入力したコメント内容をデータとして登録するために、Ruby側(サーバー側)にてデータベースの「Comment」モデルへ登録可能なメソッドを作ろうと思います。ajaxを用いてそのメソッドを呼び出すことによって、入力テキストボックスから入力した内容がデータベースの「Comment」モデルとして登録できるようにします。

今日は、そのデータベースの「Comment」モデルへ登録可能なメソッドのみ作成します。具体的なコードの作成(変更)内容は以下の通りです。

コード作成内容

chat_controller.rb

chatコントローラー(chat_controller.rb)を作成済でしたので、以下のように変更します。

変更前

1  class ChatController < ApplicationController
2    def index
3    end
4  end

変更後(5~30行目にcreate等、2つのメソッド追加)

1  class ChatController < ApplicationController
2    def index
3    end
4
5    def create
6      @comment = Comment.new(comment_params)
7      if @comment.user_id.blank?
8        # ユーザーIDが存在しない場合
9        # 必須パラメータが欠けていると判断
10       response_bad_request
11     else
12       if @comment.save
13         respond_to do |format|
14           format.html { redirect_to root_path } # htmlならルートパスへリダイレクト
15           format.json { 
16             # ユーザ登録成功
17             response_success(:comment, :create)
18           }
19         end
20       else
21         # 何らかの理由で失敗
22         response_internal_server_error
23       end
24     end
25   end
26 
27   private
28   def comment_params
29     params.require(:comment).permit(:content, :user_id)
30   end
31 end

上記について、変更後に加えた2つのメソッドの説明は以下の通りです。

  1. createメソッド(5~25行目)
    入力テキストエリアで入力したコメント内容をデータベースの「Comment」モデルへ登録するためのメソッド。ajaxを用いてこのメソッドが呼び出される。
    また、ajaxメソッドが呼び出された場合、状況に合わせて、レスポンスとして以下の3種類の結果が返されるものとする。
    ・200(Success):問題なく登録できた場合
     ⇒17行目のresponse_success(:comment, :create)に対応
    ・400(Bad Request):登録するためのデータに不備があった場合
     ⇒10行目のresponse_bad_requestに対応
    ・500(Internal Server Error):登録失敗など何かが起きた場合
     ⇒22行目のresponse_internal_server_errorに対応

  2. comment_paramsメソッド(28~30行目)
    入力テキストボックスの入力コメントがJSONで送られた時のデータを分解・取得するためのメソッド。createメソッドの中で呼び出される。
    入力テキストボックスの入力コメントが格納されているJSONのデータは以下の形式で想定している。

{
  "comment": {
    "content": 1,
    "user_id": 1
  } 
}


application_controller.rb

chatコントローラー(chat_controller.rb)の親クラスであるapplicationコントローラー(application_controller.rb)にも、ajaxメソッドが呼び出された場合の状況に合わせたレスポンスを定義するための共通メソッドを定義して、chatコントローラーからそのメソッドを呼び出すことができるようにします。
※application_controller.rbは新しいRailsアプリケーションを作成する際に自動作成済です。

変更前

1  class ApplicationController < ActionController::Base
2    # Prevent CSRF attacks by raising an exception.
3    # For APIs, you may want to use :null_session instead.
4    protect_from_forgery with: :exception
5  end

変更後(8~21行目にresponse_success等、3つのメソッド追加)

1  class ApplicationController < ActionController::Base
2    # Prevent CSRF attacks by raising an exception.
3    # For APIs, you may want to use :null_session instead.
4    protect_from_forgery with: :exception
5  
6    protected
7    # 200 Success
8    def response_success(class_name, action_name)
9      render status: 200, json: { status: 200, message: "Success #{class_name.capitalize} #{action_name.capitalize}" }
10     # capitalizeメソッドは文字列の先頭を大文字に、残りを小文字に変換
11   end
12 
13   # 400 Bad Request
14   def response_bad_request
15     render status: 400, json: { status: 400, message: 'Bad Request' }
16   end
17 
18   # 500 Internal Server Error
19   def response_internal_server_error
20     render status: 500, json: { status: 500, message: 'Internal Server Error' }
21   end
22 end

上記について、変更後に加えた3つのメソッドの説明は以下の通りです。なお、これらのメソッドを定義する際、定義する行の前(今回の場合は6行目)にprotectedを付けることによって、子クラスのchatコントローラー(chat_controller.rb)からメソッドを呼び出せるようにします。

  1. response_successメソッド(8~11行目)
    リクエストに成功した場合のレスポンス(共通メソッド)
    例:入力コメントをデータベースへ登録成功した場合等

  2. response_bad_requestメソッド(13~16行目)
    リクエストに必要なバラメータに不備があった場合のレスポンス(共通メソッド)
    例:入力コメントが誰のものか不明(ユーザー名の情報がない)場合等

  3. response_internal_server_errorメソッド(19~20行目)
    何らかのエラーが起きた場合のレスポンス(共通メソッド)
    例:データベース登録失敗やネットワークに障害があった場合等

参考

【Ruby on Rails】API のレスポンスを生成するメソッドを紹介kyamanak83さん;『きゃまなかのブログ』)
⇒APIのレスポンス部分を参考にしました。

RailsにおけるAjaxの実装(JavaScriptとjQueryのコード比較)
@t-yama-3さん;『Qiita』)
⇒ajax通信におけるコントローラー部分を参考にしました。

おわりに

今日も説明は省エネ&開発は微々たる進捗ですが、積み重ねれば大きな山となることを信じて進んでいきます。

次回もよろしくお願いいたします。
ここまで読んでくださってありがとうございました。

この記事が気に入ったらサポートをしてみませんか?