How do I add an IP address to a HttpRequestMessage?
I am writing unit tests for a Web.API application, I have an AuthorizeAttribute that checks the callers IP address -
        string[] AllowedIPs = new string[] { "127.0.0.1",  "::1" }
        string sourceIP = "";
        var contextBase = actionContext.Request.Properties["MS_HttpContext"] as System.Web.HttpContextBase;
        if (contextBase != null)
        {
            sourceIP = contextBase.Request.UserHostAddress;
        }
        if (!string.IsNullOrEmpty(sourceIP))
        {
            return AllowedIPs.Any(a => a == sourceIP);
        }
        return false;
I construct a test request as follows -
    var request = CreateRequest("http://myserver/api/CustomerController, "application/json", HttpMethod.Get);            
    HttpResponseMessage response = client.SendAsync(request).Result;
. .
    private HttpRequestMessage CreateRequest(string url, string mthv, HttpMethod method)
    {
        var request = new HttpRequestMessage();
        request.RequestUri = new Uri(url);
        request.Headers.Accept.Add(new MediaTypeWithQualityHeaderValue(mthv));
        request.Method = method;
        return request;
    } 
BUT actionContext.Request.Properties["MS_HttpContext"] is null and I cannot perform the test.
SOLUTION BELOW - see my own answer.
Thanks to Davin for his suggestion.
Here is the solution -
private HttpRequestMessage CreateRequest(string url, string mthv, HttpMethod method)
{
    var request = new HttpRequestMessage();
    var baseRequest = new Mock<HttpRequestBase>(MockBehavior.Strict);
    var baseContext = new Mock<HttpContextBase>(MockBehavior.Strict);
    baseRequest.Setup(br => br.UserHostAddress).Returns("127.0.0.1");
    baseContext.Setup(bc => bc.Request).Returns(baseRequest.Object);
    request.RequestUri = new Uri(url);
    request.Headers.Accept.Add(new MediaTypeWithQualityHeaderValue(mthv));
    request.Properties.Add("MS_HttpContext", baseContext.Object);
    request.Method = method;
    return request;
} 
Then use that method in the following way -
 var request = CreateRequest("http://myserver/api/CustomerController, "application/json", HttpMethod.Get);            
 HttpResponseMessage response = client.SendAsync(request).Result;
                        It seems you are attempting to get the IP address from the host myserver which in this case will not be resolved by anything.  This leaves the property MS_HttpContext null.
I would suggest a different approach.  First, mock System.Web.HttpContextBase and set up return values for Request.UserHostAddress, then, in your test setup, set the property directly:
private HttpRequestMessage CreateRequest(string url, string mthv, HttpMethod method)
    {
        var request = new HttpRequestMessage();
        request.RequestUri = new Uri(url);
        request.Headers.Accept.Add(new MediaTypeWithQualityHeaderValue(mthv));
        request.Method = method;
        request.Property["MS_HttpContext"] = mockedHttpContextBase //here
        return request;
    } 
                        If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With