findとfind_by
findメソッド ・・・id
を元にデータベースから該当のデータをひとつ引っ張ってくる
find_byメソッド・・・id
以外の項目でもデータベースから該当のデータをひとつ引っ張ってくる
[1] pry(main)> User.find(1)
id:〜
name:〜
email:〜
〜
〜
[2] pry(main)> User.find_by(1)
id:〜
name:〜
email:〜
〜
〜
##検索結果が見つからなかった場合の返り値の違い
findメソッド ・・・エラーが返ってくる
find_byメソッド・・・nilが返ってくる
[3] pry(main)> User.find(3)
User Load (0.5ms) SELECT `users`.* FROM `users` WHERE `users`.`id` = 3 LIMIT 1
ActiveRecord::RecordNotFound: Couldn't find User with 'id'=3
from /Users/moritasatoshi/.rvm/gems/ruby-2.5.0/gems/activerecord-5.2.1/lib/active_record/core.rb:177:in `find'
[4] pry(main)> User.find_by_id(3)
User Load (0.3ms) SELECT `users`.* FROM `users` WHERE `users`.`id` = 3 LIMIT 1
=> nil
条件分岐処理時のnil
の扱われ方
Railsでは、nil
が返ってきた際の条件分岐の処理は必ずfalse
にて処理されます。
そのため、下記のような記述の際にエラーの見せ方が変わってきます。
@userをfindと、find_byメソッドで探してきて、見つかった場合と見つからなかった場合でエラーメッセージを返す条件分岐を記述しました。
def show
@user = User.find(params[:id])
if @user
else
render json: { error: 'Faild find user'}, status: 422
end
end
findメソッドの場合、@user = User.find(params[:id]
の返り値でエラーが吐かれてしまうため、
下に記述したelse
の内容が処理されず404エラーが返ってしまいます。
def show
@user = User.find_by(id: params[:id])
if @user
else
render json: { error: 'Faild find user'}, status: 422
end
end
処理としては似ている記述ですが、条件分岐のelse
の記述を活かすには、返り値がnil
となるfind_byメソッドを使用しましょう。
検証
ターミナル上で、存在しないidにて検索を試してみました。
$ curl http://localhost:3000/api/users/3
{"error":"Failed find user"}
else
に記述したエラーメッセージを確認できました。
今日はこのあたりで失礼します。
参考サイト
【Rails初心者必見!】ひたすら丁寧にデータ取得を説明(find, where)
https://qiita.com/mr-myself/items/cfb936dcf63d2c44d2f5