This is a migrated thread and some comments may be shown as answers.

Moking HttpWebRequest & HttpWebResponse

4 Answers 1712 Views
General Discussions
This is a migrated thread and some comments may be shown as answers.
Divya
Top achievements
Rank 1
Divya asked on 06 Aug 2013, 07:10 AM
Hi,

I am new to justmock and need help in mocking the below code.I have a WCF data service method which process the service URI and gives out a XML result. I am not sure on how to mock the HTTP  request and response, especially assigning content type etc.Can anybody help out with below.Thanks in advance.

// Obtain an HTTP web Request object for the desired URI
        var Request = WebRequest.Create(strUri) as HttpWebRequest;
        if (Request != null)
        {
            Request.KeepAlive = false;
            Request.Method = "GET";
            Request.ContentType = "application/ems-v3+xml";
 
            // Obtain the HTTP web response
            using (var Response = Request.GetResponse() as HttpWebResponse)
            {
                // Read the response text stream (the XML) into a local string
                if (Response != null)
                    using (var ResponseStreamReader =
                        new StreamReader(Response.GetResponseStream()))
                    {
                        //get XML Result
                        result = ResponseStreamReader.ReadToEnd();
                    }
 
            }
 
        }

Thanks,
Divya

4 Answers, 1 is accepted

Sort by
0
Accepted
Kaloyan
Telerik team
answered on 08 Aug 2013, 11:17 AM
Hi Divya,

Thank you for contacting our forums.

Let's assume we have similar system under test:
class SUT
{
    public string result;
 
    public void SomeMethod(string strUri)
    {
        // Obtain an HTTP web Request object for the desired URI
        var Request = WebRequest.Create(strUri) as HttpWebRequest;
        if (Request != null)
        {
            Request.KeepAlive = false;
            Request.Method = "GET";
            Request.ContentType = "application/ems-v3+xml";
 
            // Obtain the HTTP web response
            using (var Response = Request.GetResponse() as HttpWebResponse)
            {
                // Read the response text stream (the XML) into a local string
                if (Response != null)
                    using (var ResponseStreamReader =
                        new StreamReader(Response.GetResponseStream()))
                    {
                        //get XML Result
                        result = ResponseStreamReader.ReadToEnd();
                    }
            }
        }
    }
}
Now, to test the SomeMethod, we need to isolate the HttpRequest and HttpResponse dependencies.

With the commercial version of JustMock, you can directly do the following:
[TestMethod]
public void SomeMethod_OnExecute_ShouldUpdateResultProperty_JMComercial()
{
    // ARRANGE
    // Creating mock objects for HttpWebRequest and HttpWebResponse.
    var httpRequest = Mock.Create<HttpWebRequest>();
    var httpResponse = Mock.Create<HttpWebResponse>();
 
    // Arranging: When the static WebRequest.Create() method is called with any string argument,
    //             it should return the mocked httpRequest object.
    Mock.Arrange(() => WebRequest.Create(Arg.AnyString)).Returns(httpRequest);
    //            When the GetResponse() method is called from the httpRequest instance,
    //             it should return the mocked httpResponse object.
    Mock.Arrange(() => httpRequest.GetResponse()).Returns(httpResponse);
    //            When the GetResponseStream() method is called from the httpResponse instance,
    //             it should return new MemoryStream().
    Mock.Arrange(() => httpResponse.GetResponseStream()).Returns(new MemoryStream());
 
    // ACT
    var sutMock = new SUT();
    sutMock.SomeMethod("test");
 
    // ASSERT - We assert that the result property is not null at the end of the test.
    Assert.IsNotNull(sutMock.result);
}
I believe, this is simple enough :).

However, if you are using the free version of JustMock, you will need to follow a bit more complicated approach. I used this blog post for assistance and I managed to isolate your method from the HttpRequest and the HttpResponse dependencies:

First, I constructed the CustomWebRequestCreate class, note it should inherit the IWebRequestCreate interface:
public class CustomWebRequestCreate : IWebRequestCreate
{
    /// <summary>
    /// The web request.
    /// </summary>
    private static WebRequest nextRequest;
 
    /// <summary>
    /// Internally held lock object for multi-threading support.
    /// </summary>
    private static object lockObject = new object();
 
    /// <summary>
    /// Gets or sets the next request object.
    /// </summary>
    public static WebRequest NextRequest
    {
        get
        {
            return nextRequest;
        }
 
        set
        {
            lock (lockObject)
            {
                nextRequest = value;
            }
        }
    }
 
    /// <summary>
    /// Creates the new instance of the CustomWebRequest.
    /// </summary>
    /// <param name="uri">The given Uri</param>
    /// <returns>An instantiated web request object requesting from the given Uri.</returns>
    public WebRequest Create(Uri uri)
    {
        return nextRequest;
    }
 
    /// <summary>
    /// Creates a Mock Http Web request
    /// </summary>
    /// <returns>The mocked HttpRequest object</returns>
    public static HttpWebRequest CreateMockHttpWebRequestWithGivenResponseCode(HttpStatusCode httpStatusCode)
    {
        var response = Mock.Create<HttpWebResponse>();
        Mock.Arrange(() => response.StatusCode).Returns(httpStatusCode);
        Mock.Arrange(() => response.GetResponseStream()).Returns(new MemoryStream());
 
        var request = Mock.Create<HttpWebRequest>();
        Mock.Arrange(() => request.GetResponse()).Returns(response);
         
        NextRequest = request;
         
        return request;
    }
}
This is the same class as in the above blog post, but the Moq arrangements in the CreateMockHttpWebRequestWithGivenResponseCode method have been replaced with their JustMock equivalents.

Next, I was able to write the following test method:
[TestMethod]
public void SomeMethod_OnExecute_ShouldUpdateResultProperty_JMFree()
{
    // ACT
    // Registering the CustomWebRequestCreate class.
    WebRequest.RegisterPrefix("http://testService.mywebservice.com", new CustomWebRequestCreate());
     
    CustomWebRequestCreate.CreateMockHttpWebRequestWithGivenResponseCode(HttpStatusCode.Forbidden);
 
    var sutMock = new SUT();
    sutMock.SomeMethod("http://testService.mywebservice.com");
 
    // ASSERT - We assert that the result property is not null at the end of the test.
    Assert.IsNotNull(sutMock.result);
}
Here, the important part is that you need to register your custom class, in order to be used for the Urls in your web request calls.

I hope this helps. Please, let me know if I can be in further assistance.

Regards,
Kaloyan
Telerik
Share what you think about JustTrace & JustMock with us, so we can become even better! You can use the built-in feedback tool inside JustTrace, our forums, or our JustTrace or JustMock portals.
0
Divya
Top achievements
Rank 1
answered on 12 Aug 2013, 06:49 AM
Hi Kaloyan ,

Thank you so much for the detailed reply , I now understand and can implement the below in my project.

Regards,
Divya
0
Kaloyan
Telerik team
answered on 13 Aug 2013, 07:16 AM
Hi again Divya,

I am glad this helped you out.

Please, do not hesitate to contact us again if there is anything else we could assist you with.

Regards,
Kaloyan
Telerik
Share what you think about JustTrace & JustMock with us, so we can become even better! You can use the built-in feedback tool inside JustTrace, our forums, or our JustTrace or JustMock portals.
0
netcana
Top achievements
Rank 1
answered on 12 Oct 2016, 07:48 AM
thanks you for sharing such information with us nice thread
Tags
General Discussions
Asked by
Divya
Top achievements
Rank 1
Answers by
Kaloyan
Telerik team
Divya
Top achievements
Rank 1
netcana
Top achievements
Rank 1
Share this question
or