勉強履歴(と雑記)

プログラミング初心者のメモ書きです

2カ月間の勉強でしでかしたミス その1

ブログの更新はこの2カ月全くやってなかった一方で、学習の方は進めていたので、

その中でやってしまったミスを思い出せる範囲で書き残して行きます。

 

1)@消し忘れ

スクールで作成中のアプリで、コメント編集・削除のajax 化を行った後、テストを行ったら下のエラーが出て、何時間も難儀してました。

 

1) コメント コメントのCRUD コメントの削除 コメントを削除できること
     Failure/Error:
       within("#comment-#{comment_by_me.id}") do
         page.accept_confirm { find('.js-delete-comment-button').click }
       end

     Capybara::ElementNotFound:
       Unable to find css "#comment-1"

     [Screenshot]: tmp/screenshots/failures_r_spec_example_groups_nested_3_crud_nested_3_コメントを削除できること_123.png

 

掲示板にコメントを投稿できるようになっているのですが、コメントを投稿した直後はidが残っている一方で、リロードや別のページに移動してから戻ると、idが消えてました。そのせいでコメントのidが見つからず、削除できなくなってました。

原因
<tr id="comment-<%= @comment.id %>" >

コメント全体を上のtrタグでidをつけているのですが、本来はcomment.idの前に@は入りません。これが原因でコメントのidがうまくいってなかったようです。

 

2)コピペする時は要注意

1)よりも時間が遡っていますが、掲示板にコメントを保存・投稿できるようにする機能を実装した時のミスです。コメントを投稿しても全く反応せず、binding.pryで検証した結果、下のメッセージが帰ってきました。

 

[2] pry(#<CommentsController>)> ↳ app/controllers/comments_controller.rb:20 User Load (0.4ms) SELECT "users".* FROM "users" WHERE "users"."id" = ? LIMIT ? [["id", 11], ["LIMIT", 1]] ↳ app/controllers/comments_controller.rb:20 (0.1ms) rollback transaction ↳ app/controllers/comments_controller.rb:20 Redirected to http://localhost:3000/comments/55 Completed 302 Found in 6395ms (ActiveRecord: 1.1ms)

ちゃんとコメントが入っていることはbinding.pryで確認していたので、ストロングパラメータやバリデーション辺りが怪しいです。

原因
comments_controller.rb
class CommentsController < ApplicationController
  before_action :require_login, only: %i[create index show]

  def show
    @board = Board.includes(:user).find(params[:id])
    @comments = @board.comments.includes(:user).all
    @comment = @board.comments.build(user_id: current_user.id) if current_user
  end

  def index
    @comments = Comment.all.includes(:user).order(created_at: :desc)
  end

  def create
    @board = Board.find(params[:board_id])
    @comments = @board.comments.includes(:board_id).all
    @comment = @board.comments.build(comment_params)
    @comment.user_id = current_user.id
    binding.pry
    if @comment.save
      flash[:success] = t('defaults.message.created', item: Comment.model_name.human)
      redirect_back(fallback_location: root_path)
    else
      flash.now[:danger] = t('defaults.message.not_created', item: Comment.model_name.human)
      redirect_back(fallback_location: root_path)
      @comment = @board.comments.build(comment_params)
    end
  end

  private

  def comment_params
      params.require(:comment).permit(:body, :user_id, :board_id)
  end
end

 

予測は当たっていて、ストロングパラメータでboard.idをmergeしていないのが原因でした。ただ、私はさらにどこからか引っ張ってきた下のコードを書き、更に無駄な時間を浪費します。

 

def comment_params
      params.require(:comment).permit(:body).merge(params.permit(:user_id,:board_id))
end

 

上のコードだと、コメントの保存はできても、コメント作成失敗時にロールバックが発生して、エラーメッセージが表示されませんでした。正しいコードは次のコードです。

 

def comment_params
      params.require(:comment).permit(:body).merge(board_id:params[:board_id])
end

 

ストロングパラメータのmergeを調べればすぐに出てくるようなコードです。逆に修正前のコードはどこからコピってきたのか今では思い出せません。誰かのコードをコピペする時はしっかりそのコードが合っているかどうか調べましょう。

3)コピペする時は要注意  その2

コメント編集のajax化を行っている時にやってしまったミスです。コメントの編集ボタンを押して非同期で編集フォームを表示させようとしてjsファイルを書いていたのですが、ボタンを押してもうまくイベントが発火しない状態に陥ってました。

色々と調べて、passive:falseだのstopPropagationだの試していましたがうまく行きませんでした。最終的にはイベントが発火するようになりましたが、うまく行かなかった理由は本当にしょうもないミスです。

この時も参考にしたコードをコピペしてjsファイルに貼っていたのですが、修正前はコメントが```~#コメント更新ボタン~```となっていました。しかし、jsファイルのコメントの書き方は```~//コメント更新ボタン~```または/*コメント更新ボタン*/です。

まあ、一応ProgateでJavaScript学んでいたのですが、期間空いてしまって忘れてたんですよ...

結論 コピペする時は本当にそのコードが正しいか見極めてから行う

当方、エンジニア目指してる途中の初心者なので、検索したら出てくるコードが正しいか判断できる知識がまだありませんが、怪しいところがあったらしっかりと調べてから使うようにします。

 

まだまだミスはありますが、今回はこの3つにしておきます。今まで学んできたこともまとめていければと思っていますし、その過程で自分のやったミスを思い出したり、学習を進めていく中でまたミスが発生することもあるので、それらについてまた記録しておきたいですね。正直、こんなミスするかと言われたら否定できませんが、もしかしたら自分と同じような初心者の方に役立つことがあるかもしれませんし。

 

とりあえず、ブログ更新という名のアウトプットを頑張って行きたいと思います。