【決断くん】確認画面とリザルト画面の実装
今回実装したいこと
1、Sqlを発行せずに、1つ前の選択肢入力画面で入力した情報を遷移先の画面で表示したい。
2、確認画面の抽選ボタンを押した時、2つの選択肢からランダムに1つを選びChoiceテーブルのresultカラムに代入する。
その後、お題、選択肢、リザルトをまとめてChoiceテーブルに登録する。
確認画面の実装
# choices_controller def new @choice = Choice.new end def confirm @choice = current_user.choices.build(choice_params) if @choice.invalid? render :new end end
単純だが、@choice = current_user.choices.build(choice_params)
で@choiceに前の画面で入力されたparamを渡すことで@choice.titleなどが機能するようにした。
# /choices/new .ui.form = form_with model: @choice, url: confirm_choices_path, local: true do |f| .field = f.label :お題 = f.text_field :title .field = f.label :1つ目の選択肢 = f.text_field :option_1 .field = f.label :2つ目の選択肢 = f.text_field :option_2 = f.submit '確認する', class: 'ui secondary button'
form_withで url: confirm_choices_pathで情報を渡す先を指定するのがポイント。
参考にしたURL
【Rails】インスタンスの状態を保ちながら入力 → 確認画面 → 保存 を実装する方法 - Qiita
リザルト画面の実装
# choice_controller内 def create @choice = current_user.choices.build(choice_params) # 空の文字列をoptionsとして定義 options = [] # 文字列optionsに、pushメソッドで受け取った選択肢を追加 options.push(@choice.option_1, @choice.option_2) # sampleメソッドによって文字列内からランダムに1つを取得し、resultカラムに格納。 @choice.result = options.sample if @choice.save redirect_to "/choices/result/#{@choice.id}" else render :new end end def result @choice = Choice.find(params[:id]) end
# routes.rb get '/choices/result/:id', to: 'choices#result'
結構簡単に実装できた。
最初はoptions << @choice.option_1
のように<<
を使っていたが、
これだと同時に2つの要素を登録できずスマートではなかったので、push
に変更。
ルーティングについては最初
# routes.rb resources :choices, only: %i[new create edit update] do collection do get :result end end
としていたのだが、これだとparams[:id]が取得できず、choiceテーブルからレコードを引っ張ってくるのが難しかったので変更し、慣れたやり方で実装することにした。
エラー
確認画面をリロードした際、リクエストがgetになってしまいno route matchエラーが出る
どうやらturbolinksのせいらしい。
Application.jsからrequire(“turbolinks”).start()
を削除したらpostリクエストが送られるようになった!
参考にしたURL
【Rails】POST後の画面をリロードしたのにURLをGETしてしまうときの対処法 - Qiita