NUnit Assert.ThrowsメソッドまたはExpectedException属性を使用しますか?


146

これらが例外をテストする2つの主な方法であると思われることを発見しました。

Assert.Throws<Exception>(()=>MethodThatThrows());

[ExpectedException(typeof(Exception))]

これらのうちどれが最良でしょうか?一方が他方よりも優れている点はありますか?それとも単に個人的な好みの問題ですか?


3
第三の選択肢は流暢なスタイルである:Assert.That(() => MethodThatThrows(), Throws.Exception)
ジャックUkleja

1
NUnitバージョン3以降はこのExpectedException属性をサポートしなくなったため、バージョン3以降ではAssert.Throwsバリアントのみが関連します。
joanlofe

なぜそうなのですか?そのNunit3はそのサポートをやめることに決めましたか?ぐるぐる回っていて、説明が見つからなかった... JUnitはまだこの方法をサポートしていますね。
ahaaman

回答:


92

最初の方法では、複数の呼び出しを使用して、複数の例外をテストできます。

Assert.Throws(()=>MethodThatThrows());
Assert.Throws(()=>Method2ThatThrows());

2つ目は、テスト関数ごとに1つの例外をテストすることのみを許可します。


25
テストでは1つの異なるロジックビットのみをテストする必要があるため、同じ単体テストで2つのエラーをテストすることは悪い習慣と見なされませんか?
SamuelDavis 2013

5
@SamuelDavis-一般に、同じテストで異なるケースをテストする必要はありません。ただし、複数ののユースケースがある場合がありますAssert.Throws
キューx 2013

3
いずれの場合も、ここでは例外をパラメーターとして取得します。これにより、例外の詳細をアサートできます。また、「予期された例外」を使用しても、同じ例外タイプが別のメソッド呼び出しでスローされても保護されません。ここでは、テスト全体ではなく、正確なメソッドをターゲットにします。テストで呼び出すコードはごくわずかですが、決して安全ではありません。特に、コードが複雑になったり、例外が一般的になりすぎたりした場合。「ArgumentNullExceptions」のようなものは大量にスローされる可能性があり、たとえばExpectedExceptionを使用すると簡単に見落とされます。Assert.Throwsはそれを見逃しません。
Gil Sand

254

主な違いは次のとおりです。

ExpectedException()属性は、テストメソッドのいずれかの場所で例外が発生した場合にテストに合格します。
の使用により、例外が予想されるコードの場所Assert.Throws()を指定できますexact

NUnit 3.0では、公式サポートがExpectedException完全に廃止されました。

したがって、私Assert.Throws()ExpectedException()属性よりもメソッドを使用することを確実に好みます。


7
これは断然正しい答えです。ちなみに、Assert.Throws()は例外も返すので、必要に応じて、例外のプロパティをさらに検査できます。
完璧主義者

1
私はバージョン3で...仕事にExpectedExceptionを得ることができない理由を最後に答える
JanT

2
リンクgithub.com/nunit/docs/wiki/Breaking-Changes-ExpectedExceptionAttributeはサポートされなくなりました。
アントンLyhin

これをNUnit 3.0で動作するように変更するには、次のように
Andrei Krasutski

38

例外がスローされた後、他の条件を検証およびアサートできるため、assert.throwsを好みます。

    [Test]
    [Category("Slow")]
    public void IsValidLogFileName_nullFileName_ThrowsExcpetion()
    {
        // the exception we expect thrown from the IsValidFileName method
        var ex = Assert.Throws<ArgumentNullException>(() => a.IsValidLogFileName(""));

        // now we can test the exception itself
        Assert.That(ex.Message == "Blah");

    }

これはより良い答えの1つです。例外がスローされた後に何かがエラー状態になったことを確認することはよくあることです。
Rhys Bevilaqua

11

また、予期しているエラーを強く入力することもできます(古いattribバージョンなど)。

Assert.Throws<System.InvalidOperationException>(() => breakingAction())

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