inuinu blog(開発用)

BOT @wagagun の開発ノウハウや、IT向け?の雑記ブログです。

【Ruby on Rails7】Turboリンクの不具合修正

この記事では、Ruby on Rails7でよく発生する、scaffoldの一覧表示画面で、削除リンクが有効にならない問題の、解決方法を解説します。

問題点

Ruby on Rails7を導入し、scaffoldでモデル+コントローラー+ビューを作成した場合、一覧画面の削除リンクが有効にならないケースがあります。

また、コントローラーが古く、バリデーションエラーが表示されないと言う現象も生じるケースがあるようです。

以下に、その解決方法を書いていきます。

解決方法(削除リンクの有効化)

importmapをインストール(binに存在しない場合)

binディレクトリにimportmapが存在しない場合は、importmapをインストールしてください。

bundle exec rails importmap:install

これで、config/importmap.rbが作成されるはずです。

Turboをインストール

bin/rails turbo:install

で、Turboをインストールします。

config/importmap.rbに、

pin "@hotwired/turbo-rails", to: "turbo.min.js", preload: true

が無い場合は、追記してください。

さらに、app/javascript/application.js

import "@hotwired/turbo-rails"

がない場合は、追記してください。

ビューファイルの変更

app/views/users/index.html.hamlの削除リンクの行を差し替えます。

        %td= button_to 'Destroy', user, method: :delete, data: { turbo_confirm: 'Are you sure?' }

link_tobutton_toに変更されていることに注目してください。
これで有効になるはずです。

CSSの変更

button_toですと、htmlのタグ構造が変わってしまい、削除ボタンが改行してしまうようです。
app/assets/stylesheets/application.scss(SCSSを使用している場合)に、下記を追記します。

/* TD内の「削除」ボタンを改行させない(button_toだと勝手にformが挿入されるため) */
td form {display: inline}

解決方法(バリデーションエラーが表示されない)

コントローラーの差し替え

Rails7になり、バリデーションエラーが表示されない場合は、下記に差し替えてください。

●app/controllers/users_controller.rb

  def create
(中略)
   respond_to do |format|
      if @user.save
(中略)
      else
        format.html { render :new, status: :unprocessable_entity }
        format.json { render json: @user.errors, status: :unprocessable_entity }
      end
    end
  end
(中略)
  def update
(中略)
   respond_to do |format|
      if @user.update(user_params)
(中略)
      else
        format.html { render :edit, status: :unprocessable_entity }
        format.json { render json: @user.errors, status: :unprocessable_entity }
      end
    end
  end

こちらで、エラー表示は解決すると思いますが、Turboは、バリデーションエラー時に、Javascriptのユーザーロジックが発火しなくなる現象を抱えています

これを解決するには、下記を参照してください。

タイトルはcocoonとなっていますが、cocoon以外でも有効です。

inuinu-tech.hatenablog.jp

inuinu-tech.hatenablog.jp

簡易版でも解決できますが、根本的な解決は、Stimulusを参考にしてみてください。