Today, when developing an ASP. NET Web API project to write unit tests, I really can't stand the stupid method and decide to make amends.
The previous unit tests for the Web API require the following actions:
Initial configuration:
1) Create a site in IIS to specify a Web API project
2) in hosts plus IP address resolution for the site
Each time you modify the code:
3) After modifying the code, press F6 to compile
4) Run unit test with TestDriven.NET
A look will know this method good soil, good stupid, good suffer. The ideal way should be: No initial configuration, no need to press F6 to compile after the code, run unit test directly, one step to complete the operation.
Today, in the case of the old way of torture, not withstand the temptation of the ideal way, determined to solve the problem, finally through the Owin host, through this blog post to share.
The idea of using Owin host is simply to run the ASP. Owin Host in the unit test, and the unit test code directly requests the Owin host site for testing.
Our web API project was developed based on the ASP. 4.5 + ASP. 5.2.3, there is no Owin related code, so add some code to the Web API project so that Owin host can load it.
First NuGet installs the Owin package (Iappbuilder in this package):
Pm> Install-package Owin
Then add Startup.cs:
Public class startup{ publicvoid configuartion (Iappbuilder app) { }}
Then NuGet installs the Microsoft.AspNet.WebApi.Owin package (App.usewebapi extension method in this package)
Pm> Install-package Microsoft.AspNet.WebApi.Owin
Add code to the Startup.configuratrion method, call the Webapiconfig.register method (this is where the routing configuration is already implemented), configure the httpconfiguration, and then register it in the Owin pipeline.
Public class startup{ publicvoid Configuration (Iappbuilder app) { var New httpconfiguration (); Webapiconfig.register (Configuraton); App. Usewebapi (Configuraton); }}
The Web API project simply needs to be transformed to support Owin Host without any side effects and without affecting the deployment of the site with IIS.
The transformation of unit test code is also simple, simply load the Web API site with the Webapp.start () method in Microsoft.Owin.Hosting before running the test.
First NuGet installs the Owin host package:
pm> install-package microsoft.owin.hostingpm> install-package Microsoft.Owin.Host.HttpListener
Next, start the Web API site with Webapp.start () in the constructor of the test class:
Public classcommentswebapitest:idisposable{Private Const stringHost_address ="http://localhost:8001"; PrivateIDisposable _webapp; Publiccommentswebapitest () {_webapp= webapp.start<startup>(host_address); Console.WriteLine ("Web API started!"); } Public voidDispose () {_webapp.dispose (); }}
You can then make it easy to do unit testing of Web APIs out of IIS.
Here's an actual experience:
1) Implement a Apicontroller in the Web API project
Public classcommentscontroller:apicontroller{[Route ("blogposts/{postid}/comments")] Public AsyncTask<ihttpactionresult> Get (intPostID) { varComments =NewComment[] {NewComment {PostID=PostID, Body="Coding changes the World1" } }; returnOk<comment[]>(comments); }}
2) write unit test code based on Owin host Web API site
Public classcommentswebapitest:idisposable{Private Const stringHost_address ="http://localhost:8001"; PrivateIDisposable _webapp; PrivateHttpClient _httclient; Publiccommentswebapitest () {_webapp= webapp.start<startup>(host_address); Console.WriteLine ("Web API started!"); _httclient=NewHttpClient (); _httclient.baseaddress=NewUri (host_address); Console.WriteLine ("HttpClient started!"); } Public voidDispose () {_httclient.dispose (); _webapp.dispose (); } [Fact] Public AsyncTask getcomments () {varPostID =1; varResponse =await_httclient.getasync ($"/blogposts/{postid}/comments"); if(Response. StatusCode! =Httpstatuscode.ok) {Console.WriteLine (awaitResponse. Content.readasstringasync ()); } assert.equal (Httpstatuscode.ok, Response. StatusCode); varComments =awaitResponse. Content.readasasync<comment[]>(); Assert.notempty (comments); Assert.equal (PostID, comments[0]. PostID); Assert.equal ("Coding changes the world", comments[0]. Body); }}
Note: In addition to the NuGet installation Microsoft.Owin.Hosting and Microsoft.Owin.Host.HttpListener packages, also install the Microsoft.AspNet.WebApi.Client package (Readasasync <Comment[]> in this package).
3) Run unit test: Right-click in the unit test method and hit run test (s) (TestDriven.NET, which compiles automatically before unit test)
4) Review the unit test results to verify that the best way to test the Web API is implemented:
Output from WebApiTests.CommentsWebApiTest.GetComments: Web API started! HttpClient Started!1 passed, 0 failed, 0 skipped, took 4.91 seconds (xunit.net 1.9.2 build 1705).
Test pass! The ideal way to achieve!
This experience proves once again that when there is a problem that affects the pleasure of writing your code, be sure to resolve it as soon as possible, otherwise it may be a waste of more than n times the time it takes to solve the problem, and many times the difficulty of solving a problem depends on how big your determination is.
Resources
ASP. NET Web API integration testing with one line of Code
Development Note: Use Owin host to implement the Web API unit test from IIS Run