Testing is one of the most important areas of software development. Any other aspects you want to know about? Source code available at: github.com/JasperKent/WebApi-Integration-Testing Remember to subscribe at ruclips.net/channel/UCqWQzlUDdllnLmtgfSgYTCA And if you liked the video, click the 👍.
Hi Jesper thank you for your videos, they are really helpful! I have some suggestions for future videos: It would be nice to hear your perspectives on Design patterns and the architecture of applications. I love to hear perspectives from people with a lot of experience, because a new developer is bombarded with all these "SOLID" Principles and weird over-engineered architectures on the internet when in my opinion these things should just be "guidelines" that you probably should use, but only if your application has the need for them. Here is an example what the talking points in an "application architecture" video could be: - brief history of how architectures evolved over time - how to design a layer (e.g. Folderstructure) - why we use different layers - when should we add a new layer - differences and commonalities between different architectures (monolith, onion, hexagonal, microservices) - how to design a class - how to design a method (This is an important topic that is not talked enough about in my opinion) ... Examples of design patterns videos could be: - when and why exactly should we use them - different implementations of the pattern (more "complicated" implementation vs "simple" implementation and when to use which one) (I only ever see complicated implementation of patterns, which in my opinion could be written much simpler for a lot of applications) - related/similar patterns and their differences There is a lot to talk about but so little good information on the internet. These topics are probably really dry, but I hope you consider these topics for your new videos. Thanks!
Hi Jesper, thank you for your explanation. A few things are clear to me now, however considering that this is integration testing, I would like to hear your opinion on mocking in integration tests. As I understand it, mocking a repository in an integration test goes against the essence of an integration test that is meant to test the end-to-end flow. In your example, the scope of the test only covers an http call made to the controller. It does not cover the repository and the database.
There are three kinds of tests. Unit Tests test individual components. End-To-End tests test the entire application from UI to DB. Integration tests are somewhere in between, test how some - but not all - of the components interact. Here, we're testing how the controllers integrate with ASP.NET itself. If we also tested through to a real database, that would become E2E. We'd lose focus on what it is we're testing (the controller/ASP.NET interaction) and we'd have to do extra work to populate and clear some kind of test DB>
Thank you so much as a young developer. Your videos are giving me so much in depth knowledge. I will start a private project doing Intergration test for the current api I am developing.
Thanks for video. It's so curious. But I've a one concern about Mocking for integration tests. Integration tests are needed specifically to test a part and including the database. And using Mock is not correct in my opinion.
That's a matter of definition. Integration tests are there to test more than units (i.e. individual classes) but less than end-to-end tests (the entire application). Unfortunately, it's a vague term. An integration test can test the routing and not the DB (as this does) or the DB and not the routing.
hi Jesper, one question. If your API is configured with SnakeCase naming convention to translate the request payload to PascalCase request classes and response classes with PascalCase to snake_case to as the response. How to setup the BaseTest or the factory.CreateClient() to make the client requests made in the test fact are transform to snake case convetion? Let's say for example: var response = await _client.PostAsync("api/v1/auth/register", JsonContent.Create(new { FirstName = "john", LastName = "doe", // more attributes })); internally, what is required is that the request is transformed to { "first_name": "john", "last_name": "doe" }
hi, great video! if i understand correctly for the integration test, you're not actually accessing the db? would it be better to make an integration test with a db (managing test data so there's no conflict or using containers for db) in which case both the db and api calls would be tested together in the same test without needing fake data for testing the api? also, i'm trying to understand the difference, is "mockRepository" actually a stub since it's not the subject being tested? thank you
Integration test is quite a vague term. A Unit Test tests a single class or very tight group of classes. An End-to-End test test the entire application. An Integration test is somewhere in between. So an integration test could test a live DB as long as it didn't, say, test the GUI. Even so, you'd need fake data. You don't want to test against real data, because real data changes. The fake data would have to be added before the test and removed after it. Personally, I find the precise distinctions between fakes, dummies, mocks, spies etc. add no benefit to the process, so I don't bother with them. But if you want to be precise (and it's just a personal preference), then you are correct.
According to latest news many users of Moq have noticed that it is not safe. Because the Creator of the Moq has also created the Sponsor Link Nuget package and he add it to Moq. This maybe puts your data at risk and the best thing is to change it with NSubstitute Nuget. However, you can use a dummy database, a copy of your production database to do all tests. This as option sounds good, isn't it?
You could use a dummy database, but it would slow down the tests and be additional development work on the tests, when what you're trying to test is the API interaction, not the database interaction. An end-to-end test would use such a database.
Thanks but "_client = _factory.CreateClient()" is giving the error 'System.InvalidOperationException: 'The server has not been started or no web application was configured.' Might be my API?
Very odd. CreateClient() doesn't make any attempt to access the server - it's only when a request is sent. Are you sure that's where the exception is being raised?
You can add services.AddLogging(builder => builder.AddConsole().AddDebug()); to your builder.ConfigureTestServices() to see the output logs. In my case, I have Hangfire installed in my API and that was failing to build.
Testing is one of the most important areas of software development. Any other aspects you want to know about?
Source code available at: github.com/JasperKent/WebApi-Integration-Testing
Remember to subscribe at ruclips.net/channel/UCqWQzlUDdllnLmtgfSgYTCA
And if you liked the video, click the 👍.
Hi Jesper thank you for your videos, they are really helpful!
I have some suggestions for future videos: It would be nice to hear your perspectives on Design patterns and the architecture of applications. I love to hear perspectives from people with a lot of experience, because a new developer is bombarded with all these "SOLID" Principles and weird over-engineered architectures on the internet when in my opinion these things should just be "guidelines" that you probably should use, but only if your application has the need for them.
Here is an example what the talking points in an "application architecture" video could be:
- brief history of how architectures evolved over time
- how to design a layer (e.g. Folderstructure)
- why we use different layers
- when should we add a new layer
- differences and commonalities between different architectures (monolith, onion, hexagonal, microservices)
- how to design a class
- how to design a method (This is an important topic that is not talked enough about in my opinion)
...
Examples of design patterns videos could be:
- when and why exactly should we use them
- different implementations of the pattern (more "complicated" implementation vs "simple" implementation and when to use which one) (I only ever see complicated implementation of patterns, which in my opinion could be written much simpler for a lot of applications)
- related/similar patterns and their differences
There is a lot to talk about but so little good information on the internet.
These topics are probably really dry, but I hope you consider these topics for your new videos.
Thanks!
Thank you so much, sir. I have to do a presentation at my workplace and your video has gave me the key of integration tests in a breeze. I'm grateful.
Funny. Was just talking about this approach with a colleague 30 minuts ago and then you released a video about it. Thank you!
Hi Jesper, thank you for your explanation. A few things are clear to me now, however considering that this is integration testing, I would like to hear your opinion on mocking in integration tests. As I understand it, mocking a repository in an integration test goes against the essence of an integration test that is meant to test the end-to-end flow. In your example, the scope of the test only covers an http call made to the controller. It does not cover the repository and the database.
There are three kinds of tests. Unit Tests test individual components. End-To-End tests test the entire application from UI to DB. Integration tests are somewhere in between, test how some - but not all - of the components interact.
Here, we're testing how the controllers integrate with ASP.NET itself. If we also tested through to a real database, that would become E2E. We'd lose focus on what it is we're testing (the controller/ASP.NET interaction) and we'd have to do extra work to populate and clear some kind of test DB>
Thank you so much as a young developer. Your videos are giving me so much in depth knowledge. I will start a private project doing Intergration test for the current api I am developing.
Amazing!!! Another in time video I was looking for, thank you very much Jasper!!
Brilliant! Thanks for that valuable content.
Amazing video!! This channel needs to be seen more.
Amazing video!
Thank you so much for explaining it so well
Just in time. Thank you.
Amazing!! many thanks.. very helpful tutorial :) I wounder if (in Memory) testing data belongs to unit test or integration test?
It's always a point for debate. I'd say unit.
Thanks for video. It's so curious. But I've a one concern about Mocking for integration tests. Integration tests are needed specifically to test a part and including the database. And using Mock is not correct in my opinion.
That's a matter of definition. Integration tests are there to test more than units (i.e. individual classes) but less than end-to-end tests (the entire application). Unfortunately, it's a vague term. An integration test can test the routing and not the DB (as this does) or the DB and not the routing.
You saved my day witha small detail !!!! cheers
Which detail was that?
hi Jesper, one question.
If your API is configured with SnakeCase naming convention to translate the request payload to PascalCase request classes and response classes with PascalCase to snake_case to as the response.
How to setup the BaseTest or the factory.CreateClient() to make the client requests made in the test fact are transform to snake case convetion?
Let's say for example:
var response = await _client.PostAsync("api/v1/auth/register", JsonContent.Create(new
{
FirstName = "john",
LastName = "doe",
// more attributes
}));
internally, what is required is that the request is transformed to
{
"first_name": "john",
"last_name": "doe"
}
There's a new feature in .NET 8 to support this: learn.microsoft.com/en-gb/dotnet/core/whats-new/dotnet-8#naming-policies
@@CodingTutorialsAreGo thanks!
This means that for each test, the practice would be to serialize the object before sending it to the api, right?
Just pass the options object into the overload of JsonContent.Create.
@@CodingTutorialsAreGo Nice, thanks!
Such an amazing video! Thank you
Really awesome. Thank you👍👍👍
Hi Jasper. Thanks. I'd like to know how to create integration tests for gRPC service.
I'll put it on the list.
Loved it.
hi, great video!
if i understand correctly for the integration test, you're not actually accessing the db?
would it be better to make an integration test with a db (managing test data so there's no conflict or using containers for db) in which case both the db and api calls would be tested together in the same test without needing fake data for testing the api?
also, i'm trying to understand the difference, is "mockRepository" actually a stub since it's not the subject being tested?
thank you
Integration test is quite a vague term. A Unit Test tests a single class or very tight group of classes. An End-to-End test test the entire application. An Integration test is somewhere in between. So an integration test could test a live DB as long as it didn't, say, test the GUI. Even so, you'd need fake data. You don't want to test against real data, because real data changes. The fake data would have to be added before the test and removed after it.
Personally, I find the precise distinctions between fakes, dummies, mocks, spies etc. add no benefit to the process, so I don't bother with them. But if you want to be precise (and it's just a personal preference), then you are correct.
How can I further my knowledge on this topic. A book recommendation / documentation will be very welcome
This looks like a good resource: code-maze.com/aspnet-core-integration-testing/
Well it helped a lot. But I didn't understand why we want Moq?
Moq as opposed to writing our own mocks or as opposed to using a real database?
According to latest news many users of Moq have noticed that it is not safe. Because the Creator of the Moq has also created the Sponsor Link Nuget package and he add it to Moq. This maybe puts your data at risk and the best thing is to change it with NSubstitute Nuget.
However, you can use a dummy database, a copy of your production database to do all tests. This as option sounds good, isn't it?
You could use a dummy database, but it would slow down the tests and be additional development work on the tests, when what you're trying to test is the API interaction, not the database interaction. An end-to-end test would use such a database.
Thanks but
"_client = _factory.CreateClient()" is giving the error 'System.InvalidOperationException: 'The server has not been started or no web application was configured.'
Might be my API?
Very odd. CreateClient() doesn't make any attempt to access the server - it's only when a request is sent. Are you sure that's where the exception is being raised?
You can add
services.AddLogging(builder => builder.AddConsole().AddDebug());
to your builder.ConfigureTestServices() to see the output logs.
In my case, I have Hangfire installed in my API and that was failing to build.
What if the api we are testing need authentication?
That's the subject of some upcoming videos.
Great video