【问题标题】:Mocking HTTP request in unit test在单元测试中模拟 HTTP 请求
【发布时间】:2013-10-24 16:14:37
【问题描述】:

我开始学习起订量,但我遇到了这个问题。我需要模拟类/接口来发出 HTTP GET 和 HTTP POST 请求并返回 HTML 字符串作为服务器响应。

我简化了我的代码。这里是:

public interface IHttpManager
{
    /// <summary>
    /// Make HTTP GET request on server and return HTML string
    /// </summary>
    string HttpGet(Uri url, CookieContainer cookies, HttpRequestSettings settings);

    /// <summary>
    /// Make HTTP POST request and return HTML string
    /// </summary>
    string HttpPost(Uri url, string postData, CookieContainer cookies, HttpRequestSettings settings);
}

我在ConnectionManager 类中使用IHttpManager 在服务器上进行登录或注销。

public interface IConectionManager
{
    /// <summary>
    /// Connect to server and parse HTML response
    /// </summary>
    Result<T> LogIn(string nick, string password);

    /// <summary>
    /// Log off and parse HTML response
    /// </summary>
    /// <param name="account"></param>
    void LogOff(Acccount account);
}

public class ConnectionManager : IConectionManager
{
    private IHttpManager _httpManager;
    private HttpRequestSettings _httpRequestSettings;

    public ConnectionManager(IHttpManager httpManager, HttpRequestSettings httpRequestSettings)
    {
        _httpManager = httpManager;
        _httpRequestSettings = httpRequestSettings;
    }

    public Result<Account> LogIn(string nick, string password)
    {
        // I simplified this method

        // How correct mock IHttpManager, because it must return HTML string
        // so in Moq in Setup return hard coded HTML string which represent server response ?
        string htmlStringResponse = _httpManager.HttpGet(ServerUrl.LogOn, new CookieContainer(), _httpRequestSettings);

        // parse HTML string and return result
    }

    // ...
}

我对方法LogIn 进行了单元测试。我想模拟IHttpManager。但我不知道如何以正确的方式去做。

我试试这个:

// Arrange
var mockHttpManager = new Mock<IHttpManager>();

mockHttpManager.Setup(x=>x.HttpGet()).Returns(()=>"HTML SERVER RESPONSE");

var sut = new ConnectionManager(mockHttpManager.Object, new HttpRequestSettings());

// act
sut.Login("nick", "123")

// Assert

【问题讨论】:

    标签: c# testing mocking moq xunit.net


    【解决方案1】:

    似乎您需要在模拟中设置参数期望:

    mockHttpManager
        .Setup(x => x.HttpGet(
            It.IsAny<Uri>(),
            It.IsAny<CookieContainer>(),
            It.IsAny<HttpRequestSettings>()))
        .Returns(() => "HTML SERVER RESPONSE");
    

    理想情况下,您应该使用It.Is&lt;T&gt;() 来匹配参数,以确保使用您期望的确切参数调用该方法。例如,您可能想测试您的Login 方法是否使用ServerUrl.LogOn 调用HttpGet:

    It.Is<Uri>(uri => uri == ServerUrl.LogOn),
    

    【讨论】:

    • 谢谢。但我真正的问题是不同的。我想知道返回 HARD CODED HTML STRING 是否是模拟 IHttpManager.Get 与 Moq 的正确方法。如果不是正确的方法是什么?我不确定返回硬编码字符串是否有礼貌。
    • 好的。那还不清楚。好吧,您需要返回可以被 LogIn 方法解析的 HTML 响应,然后断言返回的 Result&lt;Account&gt; 对象是您所期望的。您需要为不同的测试返回不同的字符串,例如登录成功、登录失败、服务器不可用等
    • 是的,你是对的。它存在如何模拟 IHttpManager 的不同方式?有更好的吗?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-08-28
    • 2012-07-09
    • 2015-08-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多