44日目 入力コメントをajaxで送信①(コントローラーへのアクション追加)
おはようございます。今日も少しずつ開発を積み重ねていきます。
今までの進捗をまとめたものがこちらになります。
現在、以下のように、入力テキストボックスと縦線の区切りが表示されている見た目の画面のみ用意しています。
![](https://assets.st-note.com/img/1657652304318-MANQ0hBJ7I.png?width=1200)
今回は入力テキストボックスに何らかの文字列を入力して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つのメソッドの説明は以下の通りです。
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に対応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)からメソッドを呼び出せるようにします。
response_successメソッド(8~11行目)
リクエストに成功した場合のレスポンス(共通メソッド)
例:入力コメントをデータベースへ登録成功した場合等response_bad_requestメソッド(13~16行目)
リクエストに必要なバラメータに不備があった場合のレスポンス(共通メソッド)
例:入力コメントが誰のものか不明(ユーザー名の情報がない)場合等response_internal_server_errorメソッド(19~20行目)
何らかのエラーが起きた場合のレスポンス(共通メソッド)
例:データベース登録失敗やネットワークに障害があった場合等
参考
【Ruby on Rails】API のレスポンスを生成するメソッドを紹介(kyamanak83さん;『きゃまなかのブログ』)
⇒APIのレスポンス部分を参考にしました。
RailsにおけるAjaxの実装(JavaScriptとjQueryのコード比較)
(@t-yama-3さん;『Qiita』)
⇒ajax通信におけるコントローラー部分を参考にしました。
おわりに
今日も説明は省エネ&開発は微々たる進捗ですが、積み重ねれば大きな山となることを信じて進んでいきます。
次回もよろしくお願いいたします。
ここまで読んでくださってありがとうございました。