2011-03-28 47 views
2

私はMoqを使用してプロジェクトのユニットテストを作成していますが、DateTimeプロパティに値が割り当てられていることを確認しようとすると、ここに私が(失敗した)ことを確認します:It.IsAny <DateTime>()でMoqユニットテストが失敗する

 _mockTaskContext.Verify(context => context.TaskQueue.AddObject(It.Is<TaskQueueItem>(
      task_queue => task_queue.TaskCode == (int)TaskCode.MyTask 
        && task_queue.ClientID == ExpectedClientID 
        && task_queue.JobNumber == It.IsAny<int>() 
        && task_queue.Requester == String.Empty 
        && task_queue.JobStatus == (int)JobStatus.Submitted 
        && task_queue.TimeQueued == It.IsAny<DateTime>() 
        && task_queue.TimeStarted == new DateTime(1900, 1, 1) 
        && task_queue.TimeStopped == new DateTime(1900, 1, 1) 
        && task_queue.TaskParameters == expectedTaskParam 
      )), Times.Once()); 

私は私のテストに他の変更を加えることなく、task_queue.TimeQueuedは、テストが合格に期待をコメントアウトした場合。また、TimeStartedまたはTimeStoppedのいずれかの値をnew DateTime(1900, 1, 1)からIt.IsAny<DateTime>()に変更すると、テストは失敗します。私は、疑わしいリポジトリの代わりに実際の実装で単体テストの外でテスト対象のコードを実行しました。TimeQueuedにその値が正しく割り当てられています。 It.IsAnyDateTimeのプロパティで正しく動作しないと思っていますか、または私の期待を正しく設定していませんか?

更新:他のテストでIt.IsAny()を問題なく使用していますが、このテストはまだ失敗しています。私はそれがItの中にあるからかもしれないと思う。ラムダ式ですが、私はそれを回避する方法がわかりません。

答えて

7

It.IsAny<>()の構文をmockオブジェクトのスコープ内で使用する必要があります。この場合、Setupとモック引数を直接使用します。これは、モックオブジェクトが引数に渡す値をキャプチャする記録モードにあるためです。

mock.Setup(x => x.Foo(It.IsAny<Bar>())); 

は、セットアップ行の実行時に引数を処理するためです。

しかし、あなたの例では、代理人の中からIt.IsAny<>()を使用して、一致で渡された引数を検証しようとしています。これが起こると、モックは録音されていませんが、テスト中のオブジェクトの結果として使用されています(これはずっと後であります)。

したがってsomeValue == It.IsAny<DateTime>()は、IsAnyメソッドの返り値がtrueになるように一致する値を返さなければならないため、trueと評価することはできません。 It.IsAny<int>()も動作しないと思います。

私の提案は、あなたが正確な値のいずれかに一致するように持っているか、値を確認するため、あなたが持っているIsInRange単に別の方法は、2 minとmaxの範囲の間である場合、この場合には、日付

&& IsInRange(DateTime.MinValue, DateTime.MaxValue, task_queue.TimeQueued) 

の範囲と一致するということです。

+0

私はコードを誤読している可能性がありますが、私はコールバックを使用していないと思います。実際には、私はこれを投稿して以来、私は私のテストを再構築し、私は何かを返す必要がない限り、もはやセットアップを行います、今は厳密には、ベリファイ(...)を使用するので、私は質問を更新します。 It.IsAny ()は問題なく動作しますが、String.EmptyをIt.IsAny ()に置き換えると失敗します。 –

+0

'It.Is '内で使用されるデリゲートは、モックのセットアップが呼び出されたときではなく、テスト対象のコードが実行されるときに呼び出されます。私が言っていることは、 'It.IsAny <>'を使うことは、セットアップが呼び出されていて、後で実行されないときにのみ使用できるということです。私は少しテストを行い、 'It.IsAny ()'を使って失敗しました。この場合、おそらくint値は0です。 – aqwert

+0

あなたは正しいです! It.IsAny ()に対してチェックされたint値がデータベースに割り当てられているため、テストでは0になります。あなたがコールバックのあなたの言及は、正しいトラックに私を入れて、私は実際にここでおそらく2つの単体テスト、1つのチェックを追加し、SaveChanges()メソッド(動作検証)と別の単体テストを確認する値を確認する割り当てられるのは正しい(状態の確認)。正しい道を私に教えてくれてありがとう! –

関連する問題