使用 MoQ 设置后台工作项
Setting up background work item using MoQ
我是单元测试的新手,我在单元测试后台工作人员方面遇到了一些困难。
正在测试方法
[HandleExceptions(LoggerName)]
public override IHttpActionResult ValidateToken(string auth_token)
{
var response = new HttpResponseMessage();
var userInfo = this._userInfoService.CreateUserInfoModel(auth_token);
response.StatusCode = HttpStatusCode.BadRequest;
if (userInfo.Status.IsSuccess)
{
//-- I want to test if the following worker is calling RunPlayerDetailsWorkflow method exactly once.
_taskScheduler.QueueBackgroundWorkItem(task =>
this._playerDetailsService.RunPlayerDetailsWorkflow(userInfo.UserID, userInfo.ServerID));
response.StatusCode = HttpStatusCode.OK;
}
response.Content = new StringContent(_userInfoService.ParseUserInfo(userInfo));
response.Content.Headers.ContentType = new System.Net.Http.Headers.MediaTypeHeaderValue("text/plain");
return this.ResponseMessage(response);
}
测试方法
[Test]
public void TestValidateToken_Should_Call_PlayerDetailsService_RunPlayerDetailsWorkflow_Exactly_Once()
{
// Arrange
var userInfoModel = AdminControllerHelpers.CreateUserInfoModel();
userInfoModel.Status = ETIStatus.CreateSuccess();
_mockUserInfoService
.Setup(m => m.CreateUserInfoModel(It.IsAny<string>()))
.Returns(userInfoModel);
_mockUserInfoService
.Setup(s => s.ParseUserInfo(userInfoModel))
.Returns(_randomString);
_mockPlayerService
.Setup(m => m.RunPlayerDetailsWorkflow(userInfoModel.UserID, userInfoModel.ServerID));
//-- this is where I got the error.
_mockTaskScheduler
.Setup(t => t.QueueBackgroundWorkItem(
obj => _mockPlayerService.Object.RunPlayerDetailsWorkflow(userInfoModel.UserID,
userInfoModel.ServerID)));
// Act
_controller.ValidateToken(It.IsAny<string>());
// Assert
_mockPlayerService
.Verify(m => m.RunPlayerDetailsWorkflow(userInfoModel.UserID, userInfoModel.ServerID), Times.Exactly(1));
}
即使我正确设置了所有内容(至少对我而言),我仍收到以下错误:
An exception of type 'System.ArgumentException' occurred in System.Core.dll but was not handled in user code. Additional information: Argument types do not match
我正在模拟的 Task Scheduler 界面
public interface ITaskScheduler
{
/// <summary>
/// Schedules a task which can run in the background, independent of any request.
/// </summary>
/// <param name="workItem"> A unit of execution.</param>
void QueueBackgroundWorkItem(Action<CancellationToken> workItem);
}
更改设置以期待一个动作,然后使用回调来执行模拟
_mockTaskScheduler
.Setup(_ => _.QueueBackgroundWorkItem(It.IsAny<Action<CanellationToken>>()))
.Callback((Action<CancellationToken> action) => action(CancellationToken.None));
同样在练习被测方法时,不需要使用It.IsAny<>()
。传个值就可以了。
// Act
_controller.ValidateToken(String.Empty);
// Assert
_mockPlayerService
.Verify(m => m.RunPlayerDetailsWorkflow(userInfoModel.UserID, userInfoModel.ServerID), Times.Exactly(1));
现在应该可以按照预期进行测试了
我是单元测试的新手,我在单元测试后台工作人员方面遇到了一些困难。
正在测试方法
[HandleExceptions(LoggerName)]
public override IHttpActionResult ValidateToken(string auth_token)
{
var response = new HttpResponseMessage();
var userInfo = this._userInfoService.CreateUserInfoModel(auth_token);
response.StatusCode = HttpStatusCode.BadRequest;
if (userInfo.Status.IsSuccess)
{
//-- I want to test if the following worker is calling RunPlayerDetailsWorkflow method exactly once.
_taskScheduler.QueueBackgroundWorkItem(task =>
this._playerDetailsService.RunPlayerDetailsWorkflow(userInfo.UserID, userInfo.ServerID));
response.StatusCode = HttpStatusCode.OK;
}
response.Content = new StringContent(_userInfoService.ParseUserInfo(userInfo));
response.Content.Headers.ContentType = new System.Net.Http.Headers.MediaTypeHeaderValue("text/plain");
return this.ResponseMessage(response);
}
测试方法
[Test]
public void TestValidateToken_Should_Call_PlayerDetailsService_RunPlayerDetailsWorkflow_Exactly_Once()
{
// Arrange
var userInfoModel = AdminControllerHelpers.CreateUserInfoModel();
userInfoModel.Status = ETIStatus.CreateSuccess();
_mockUserInfoService
.Setup(m => m.CreateUserInfoModel(It.IsAny<string>()))
.Returns(userInfoModel);
_mockUserInfoService
.Setup(s => s.ParseUserInfo(userInfoModel))
.Returns(_randomString);
_mockPlayerService
.Setup(m => m.RunPlayerDetailsWorkflow(userInfoModel.UserID, userInfoModel.ServerID));
//-- this is where I got the error.
_mockTaskScheduler
.Setup(t => t.QueueBackgroundWorkItem(
obj => _mockPlayerService.Object.RunPlayerDetailsWorkflow(userInfoModel.UserID,
userInfoModel.ServerID)));
// Act
_controller.ValidateToken(It.IsAny<string>());
// Assert
_mockPlayerService
.Verify(m => m.RunPlayerDetailsWorkflow(userInfoModel.UserID, userInfoModel.ServerID), Times.Exactly(1));
}
即使我正确设置了所有内容(至少对我而言),我仍收到以下错误:
An exception of type 'System.ArgumentException' occurred in System.Core.dll but was not handled in user code. Additional information: Argument types do not match
我正在模拟的 Task Scheduler 界面
public interface ITaskScheduler
{
/// <summary>
/// Schedules a task which can run in the background, independent of any request.
/// </summary>
/// <param name="workItem"> A unit of execution.</param>
void QueueBackgroundWorkItem(Action<CancellationToken> workItem);
}
更改设置以期待一个动作,然后使用回调来执行模拟
_mockTaskScheduler
.Setup(_ => _.QueueBackgroundWorkItem(It.IsAny<Action<CanellationToken>>()))
.Callback((Action<CancellationToken> action) => action(CancellationToken.None));
同样在练习被测方法时,不需要使用It.IsAny<>()
。传个值就可以了。
// Act
_controller.ValidateToken(String.Empty);
// Assert
_mockPlayerService
.Verify(m => m.RunPlayerDetailsWorkflow(userInfoModel.UserID, userInfoModel.ServerID), Times.Exactly(1));
现在应该可以按照预期进行测试了