0
0

DM(チャット)機能非同期化の失敗

Last updated at Posted at 2024-06-19

はじめに

ポートフォリオ制作中です
今まで、いいねやコメント、フォローと非同期化してきましたが、
今回は大きく躓いてしまったのでアウトプットします

⚠️こちらは失敗のアウトプットです
非同期化の全体の流れは以下の記事にまとめてます🌱

一つ目のエラー

ActionController::UnknownFormat in Public::ChatsController#create
Public::ChatsController#create is missing a template for this request format and variant.
request.formats: ["text/html"]
request.variant: []
 raise ActionController::UnknownFormat, message

テンプレートフォーマットがないよと言われています
これはシンプルにlocal: truelocal: falseに変え忘れです
ここは簡単なエラーなのでさらっといきます

二つ目のエラー

これが問題のエラーです!

ActionView::Template::Error (undefined method `each' for nil:NilClass):
    1: <div class="row justify-content-center">
    2:   <% chats.each do |chat| %>
    3:     <% if chat.user == current_user %>
    4:       <div class="col-10 text-right mb-3">
    5:         <div class="says px-3">
  
app/views/public/chats/_chats.html.erb:2
app/views/public/chats/create.js.erb:1

チャット一覧のeach(chats)がnilだと言われています
非同期でない時はテンプレートとして使えているのにどうして?
となったのですが、そもそも非同期化していると順序が違うのでエラーになってしまうのでした!

非同期化時の流れ

①フォームを送信してcreateする

chats_controller.rb
class Public::ChatsController < ApplicationController
  def show
:
    @chats = @room.chats
    @chat = Chat.new(room_id: @room.id)
  end

  def create
    @chat = current_user.chats.new(chat_params)
    @chat.save
      # redirect_to request.referer
  end
end

・show画面でフォームから送信されたデータはcreateにいく
・createでは通常時redirect_to request.refererを使用するが、今回は非同期化のためcreate.js.erbにいく

create.js.erb
$('.chat-index').html("<%= j(render "public/chats/chats", chats: @chats) %>");
$('.chat_textfield').val("");

create.js.erbでrenderするため、@chatsはcreateアクションで定義しないと使用することができない
ではもう一度コントローラーを見てみましょう

chats_controller.rb
class Public::ChatsController < ApplicationController
  def show
:
    @chats = @room.chats
    @chat = Chat.new(room_id: @room.id)
  end

  def create
    @chat = current_user.chats.new(chat_params)
    @chat.save
      # redirect_to request.referer
  end
end

createに定義されていないですね!!!
非同期化でない場合は必要ないので盲点でした😭

chats_controller.rb
class Public::ChatsController < ApplicationController
  def create
    room = Room.find(params[:chat][:room_id])
    @chats = room.chats
    @chat = current_user.chats.new(chat_params)
    @chat.save
  end
end

さいごに

これで無事非同期化できました!
今回は失敗のアウトプットです!

0
0
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
0
0