Railsでは、検証エラー以外に、.save()が失敗した原因をどのようにして見つけることができますか?


91

trueから戻っているvalid?(そして.errorsが空である)ActiveRecordモデルがありますが、falseから戻っていsave()ます。モデルインスタンスが有効な場合、保存が失敗する原因をどのようにして見つけることができますか?


7
私は数週間前にこの問題を抱えていました。一部のリファクタリングでは、before_save関数が常にfalseを返すため、保存が失敗していました。
Jeff Paquette、2011年

1
@Jeff-ありがとう、:before_saveメソッドがfalseを返すことが判明しました。あなたはどのようにして知りました?コードの検査だけでしたか?
kdt、2011年

コードインスペクションであり、バージョン管理との相違点を確認しました。
Jeff Paquette、2011年

回答:


48

すべてのコールバックを確認してください。

モデルに一連の変更を加えた後に失敗した「after_validate」メソッドと、このような問題がありました。モデルは有効でしたが、「after_validate」がfalseを返していたため、model.validするとtrueと表示されましたが、保存すると検証エラー(after_validateコールバックからパススルー)が発生しました。変だった。

アプリケーショントレースを見ると、どのコード行が例外を発生させているかを確認できるはずです。


2
ジェフのコメントによると、問題はfalseを返すbefore_saveコールバックであることが判明しました。
kdt、2011年

3
@kdt-それがまさに私の問題でした。before_saveは単にプロパティを設定することを意図していたので、私はそれについて考えていませんでしたが、それをfalse値に設定していたため、暗黙的に返され、保存がサイレントに失敗しました。明るい面では、行を追加してこのコードを修正するオプションがあります"Hey! That's MY fake leg!" # Believe it or not, this is important。そうするつもりはありません。;)
ネイサンロング

2
真の戻り値を保証する良い方法true.tap { do_something }
ネイサンロング

うわー、なんとあいまいな問題。falseを返すコールバックが保存を停止するだろうという推測は決してありません。誰かが私にこれに関するドキュメントを教えてもらえますか?これを指摘してくれてありがとう!
アンディ2013年


114

bangバージョンsave!(最後に感嘆符が付いています)を使用して、結果のエラーを確認してください。


4
保存する!RecordNotSavedをスローしているだけです(例外の.messageを出力すると、例外クラスの名前が表示されます)。詳細を探しているところはありますか?
kdt '17年

1
Rails開発モードの場合、エラーの完全な説明がスタックトレースとともに出力されます。手がかりを探したり、ここに投稿したりします。
アンディリンデマン

1
コンソールを使用してオブジェクトをロードし(例:o = Object.find #id)、次にo.saveを実行します!答えが言うように。保存されない理由を出力します。
2011年

1
ちなみに、呼び出しsave!ActiveRecord::RecordInvalid(検証を実行するActiveRecord::RecordNotSavedため)発生する可能性があり、それが救助したいものです。
デニス

2
+1は、.save検証が原因ではない障害を診断する方法に関する基本的な質問に対する最も満足のいく答えではないためです。「最も満足できない」資格とは、この答えではなく、Railsを指します。
チャックバット

108

@user.save(たとえば)が返された場合false、これを実行してすべてのエラーを取得します。

@user.errors.full_messages

12
質問で述べたように、.valid?真です-つまり、検証エラーはありません。.errorsも空のリストを返すことを確認しました(それを指摘するために質問を更新しました)
kdt

3

ええ、私はすべてのbefore_ *コールバックでtrueを返すようにしてこの問題を修正し、それが機能し始めました:)


-1

私が抱えていた問題は、モデルに検証を追加するのを忘れていたことでした。

class ContactGroup < ActiveRecord::Base
  validates_presence_of :name
end
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.