Integration Testing: Am I Doing It Right?

Here is the integration test I wrote for a class that interacts with a database:

[Test] public void SaveUser() { // Arrange var user = new User(); // Set a bunch of properties of the above User object // Act var usersCountPreSave = repository.SearchSubscribersByUsername(user.Username).Count(); repository.Save(user); var usersCountPostSave = repository.SearchSubscribersByUsername(user.Username).Count(); // Assert Assert.AreEqual(userCountPreSave + 1, userCountPostSave); } 

It seems to me that I cannot check the Save function SearchSubscriberByUsername function to find out if the user has been successfully saved. I understand that integration tests are not intended for unit tests, which should test one unit of code at a time. But ideally, it would be nice if I could test one function in my repository class per test, but I don't know how to do it.

Is it good how I wrote the code so far or is there a better way?

+7
source share
4 answers

You have a problem with your test. When you verify that the data is stored in the database, you should verify that it is in the database, and not that the repository says that it is in the database.

If you are testing the functionality of a repository, you cannot test this functionality by asking if it is executed correctly. This is the equivalent of the word to someone. "Did you do it right?" They are going to say yes.

Imagine a repository never commits. Your test will pass fine, but the data will not be in the database.

So, I would do to open a connection (pure SQL) with the database and verify that the data was saved correctly. You only need to select the counter (*) before and after to make sure that the user has been saved. If you do this, you can also avoid using the name SearchSubscribersByU.

If you are testing the functionality of a repository, you cannot trust the repository by definition.

+8
source

In order for the unit test to be something like the Save function, you will definitely need a trustworthy channel to check the result of the operation. If you trust SearchSubscribersByUsername (because you have already done separate unit tests for this function yourself), you can use it here.

If you do not trust SearchSubscribersByUsername and think that your unit test may also break, because there is an error in this function (and not in Save ), you should think about another channel (perhaps you have the opportunity to bypass SQL access to your DB for checking the Save result, which can be simpler than the implementation of SearchSubscribersByUsername )? However, do not redefine SearchSubscribersByUsername again, it will be pointless. In any case, you will need at least some other function that you can trust.

+2
source

If the method you are testing returns the final information about what you did, I see no way to avoid calling other methods. I think you're right in assuming that integration testing requires a different way of thinking when testing modules.

I would still collect tests that focused on individual methods. Therefore, when testing Save (), I can very well use the capabilities of Search (), but I focus on the extreme cases of Save (). I am building tests that deal with duplicate inserts or invalid input. Then I will build a whole array of Search () tests that deal with edge cases of Search ().

Now, one of the possible ways of thinking is that "Save and Search" have some commonality, an error in the search may mask the error in the "Save". Imagine, for example, if you have a caching layer. Therefore, perhaps an alternative approach is to use some other verification mechanisms. For example, calling JDBC directly to a database, or changing the mockery you entered at some point in your infrastructure. When creating complex integrated systems, this back door verification can be significant.

+1
source

Personally, I have written countless tests very similar to this, and I think that is great. The alternative is to drown out the database so that search subscribers never do anything but a lot of work, because I would say that this is of little benefit.

0
source

All Articles