質問

私の仕事の場所で「建築家」から伝えられた悪い練習に続いて数年後に続いて、より良い方法があるに違いないと考えて、私は最近TDDとDDDを読んでいて、原則と実践は私たちが書くソフトウェアの複雑さに最適です。

ただし、私が見たTDDサンプルの多くは、ドメインオブジェクトのメソッドを呼び出し、オブジェクトのプロパティをテストして、動作が正しく実行されるようにします。

一方、業界の尊敬される人々(グレッグ・ヤングは最も顕著なので、CQRに関する彼の講演で)は、すべての「ゲッター」を削除することにより、各ドメインオブジェクトを完全にカプセル化することを提唱しています。

したがって、私の質問は次のとおりです。ドメインオブジェクトの機能をどのようにテストしても、その状態を取得することが禁止されている場合はどうすればよいですか?

私は基本的な何かが欠けていると信じているので、私を馬鹿と呼んで、私を啓発してください - どんなガイダンスも大歓迎です。

役に立ちましたか?

解決

あなたが説明しているのはです 状態検証 ドメインオブジェクトの状態について主張します。呼び出されるTDDのブランチがあります 行動検証 モックオブジェクトを利用します。

動作の検証により、どのメソッドを呼び出すべきか、必要に応じてどの方法が呼び出されないかを指定できます。

詳細については、Martin Fowlerのこの記事をご覧ください。 モックはスタブではありません.

他のヒント

わかりました、この答えは1年遅れです;-)

ただし、CQRSモデルをテストする場合は、エンティティステートに関するアサーションではなく、燃えたドメインイベントでアサーションを作成できます。

たとえば、呼び出しをテストする場合:customer.rename( "foo")は正しい動作をもたらします。

customer.nameが「foo」に等しいかどうかをテストする代わりに、保留中のイベントストアに値「foo」を含む保留中のCustomErrenameイベントがあるかどうかをテストします。 (実装に応じてUOWまたはエンティティイベントリストで)

If you're really going to go as far as to forbid retrieval of state, then you will be limited to behavioural testing, probably through a mocking framework such as TypeMock, which has the power to track the behaviour of your object. If you are able to do pure BDD, then theoretically you can assert the correctness of your entire system just by the way it's behaving.

In practice, I've found BDD to be more brittle in a lot of cases than just stateful testing. While some people might call for a certain theory, it only works if it works for you. State-based testing still makes up 90% of all the unit tests we write, and we're well aware of BDD on our team.

Do what works best for you.

A couple things.

First, when you do things like TDD to make your code testable you end up with smaller class. If you have a class with lots of private properties you can't inspect, theres a good chance it could be broken into multiple classes and made more testable.

Second, oldschool OO architecture tries to make software safe by using language safeguards to prevent things from being accessible. A TDD architecture makes software more robust by writing tests that verify what the code actually does, putting less emphasis on using language constructs to ensure what the program doesn't do.

Last, checking a property is not the only way to validate code did what it was supposed to do. The book xUnit Design Patterns documents other approaches here: http://xunitpatterns.com/Result%20Verification%20Patterns.html

I call a system's public input methods (i.e. I push input data into the system), and then I get (and assert) the system's output. I'm not testing the system's internal state, but rather its public/visible behaviour: Should one test internal implementation, or only test public behaviour?

What you mention is called state testing. There's also behavior testing. The techniques used for that are Dependency Injection, Inversion Of Control, and Mocking:

All side effects of your class are implemented as method invocations on its "dependencies" -- i.e. objects supplied from the outside, usually in constructor. Then, in your unit-test, you supply a fake object instead of a real one. The fake object can remember if its' certain method was called, and that's what you assert in your test.

There exist number of Mocking Frameworks that automate mock object creation by dynamically generating classes that implement a given interface. Most popular are Rhino.Mocks and Moq.

Hey Justin, like you, I was recently thinking about adding getters to my write-only domain object for the sake of unit testing, but now I am convinced I was wrong. Assuming you've bought into the idea of a write-only domain in the first place, then if you have getters at all, you're asking for trouble. The write-only domain principle would want you to fire an event from your domain object, or read from a projection that your domain object wrote, or something like that. Once you expose getters you're starting to expose the object's "shape", and as Greg Young says, "Domain objects have Behavior, not Shape".

That being said, I am struggling with your same question ... how do you unit test a write-only domain object? Here's my current plan: I am thinking of making my Domain Object fire a Domain Event saying "These properties changed", and in my unit test, I'll register for it before I send the "EditCommand". Check out Udi Dahan's post on Domain Events here, and also see what Eric Evans says about Domain Events.

I was wondering the same thing until I finally stumbled upon the following papers. I found them to be great primers on performing behavior verification, especially the first one providing me several "aha moments":

  1. Using Mocks and Tests to Design Role-Based Objects
  2. Mock Roles, Not Objects
ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top