这是我的控制器的代码:
private readonly ILMS_Service lms_client;
private UrlHelper urlHelper;
public PackagesController(ILMS_Service client, UrlHelper _urlHelper)
{
lms_client = client;
urlHelper = _urlHelper;
}
public PackagesController()
{
lms_client = new LMS_ServiceClient();
urlHelper = new UrlHelper(Request.RequestContext);
}
[HttpPost]
public ActionResult EditPackageDetails(
int packageID,
string package_name,
int unit_type,
int product_id,
int unit_count,
string description
)
{
lms_client.EditPackageDetails(
packageID,
package_name,
unit_type,
product_id,
unit_count,
description);
var url = urlHelper.Action("PackagesList", "Packages");
return Json(new
{
statusCode = (int)HttpStatusCode.OK,
redirectURL = url
});
}
urlBuilder.Action("PackagesList", "Packages");
在测试运行期间返回null。我试图通过将UrlHelper
类分配给控制器来用假返回值来伪造它,但它似乎不起作用。以下是我的测试的当前实现:
private readonly PackagesController _controller_Packages;
private readonly ILMS_Service _lms_service;
private readonly HttpContextBase httpContext;
private readonly HttpResponseBase httpResponse;
private readonly HttpSessionStateBase httpSession;
private readonly UrlHelper urlBuilder;
public Packages_UnitTest()
{
// Mock WCF
_lms_service = A.Fake<ILMS_Service>();
// Fake session
httpContext = A.Fake<HttpContextBase>();
httpResponse = A.Fake<HttpResponseBase>();
httpSession = A.Fake<HttpSessionStateBase>();
urlBuilder = A.Fake<UrlHelper>();
//SUTs
_controller_Packages = new PackagesController(_lms_service, urlHelper);
A.CallTo(() => httpContext.Response).Returns(httpResponse);
A.CallTo(() => httpContext.Session).Returns(httpSession);
}
[TestMethod]
public void should_EditPackageDetails()
{
// Arrange
int packageID = 1;
string package_name = "Test package";
int unit_type = 1;
int product_id = 1;
int unit_count = 10;
string description = "Sample test description";
int expected_statusCode = (int)HttpStatusCode.OK;
string expected_page_destination = "/Packages/PackagesList";
var context = new ControllerContext(new RequestContext(httpContext, new RouteData()), _controller_Packages);
_controller_Packages.ControllerContext = context;
A.CallTo(() => urlBuilder.Action("PackagesList", "Packages"))
.Returns("/Packages/PackagesList");
// Act
_ = A.CallTo(() => _lms_service.EditPackageDetails(
A<int>.Ignored,
A<string>.Ignored,
A<int>.Ignored,
A<int>.Ignored,
A<int>.Ignored,
A<string>.Ignored
));
var _editPackage = _controller_Packages.EditPackageDetails(
packageID,
package_name,
unit_type,
product_id,
unit_count,
description
) as JsonResult;
dynamic result = _editPackage.Data;
// Assert
Assert.AreEqual(expected_statusCode, result.statusCode);
Assert.AreEqual(expected_page_destination, result.redirectURL);
}
使用此测试,它仍然返回null,而不是"/Packages/PackagesList"
。如何使用FakeitEasy将"/Packages/PackagesList"
返回为值来伪造UrlHelper
?如有任何帮助,我们将不胜感激。我有一个ASP。NET MVC 4、MSTest和FakeitEasy模拟框架。谢谢
伪UrlHelper
对我来说很好,但你没有在EditPackageDetails
中使用它。您使用的是您构建的新UrlHelper
:
var urlBuilder = new UrlHelper(Request.RequestContext);
请改用_controller_Packages.Url
。
还有一个对未来的提示:调试测试通常会很有帮助。检查你使用的那些你认为可能是假的价值观,看看它们是否真的是。
我最终将UrlHelper注入SUT的构造函数,并添加了一个if
语句来检查urlBuilder
是否已经实例化。一旦调用了.Action()
,它就会返回我定义的伪造路径,正如您在测试的A.CallTo()
部分中看到的那样。
请注意,下面的SUT和测试只是我的完整代码的摘录,以消除干扰。
SUT
private UrlHelper urlHelper;
public PackagesController(UrlHelper _urlHelper)
{
urlHelper = _urlHelper;
}
[HttpPost]
public ActionResult EditPackageDetails(
int packageID,
string package_name,
int unit_type,
int product_id,
int unit_count,
string description
)
{
lms_client.EditPackageDetails(
packageID,
package_name,
unit_type,
product_id,
unit_count,
description);
if(urlHelper == null)
urlHelper = new UrlHelper(Request.RequestContext);
var url = urlHelper.Action("PackagesList", "Packages");
return Json(new
{
statusCode = (int)HttpStatusCode.OK,
redirectURL = url
});
}
测试
private readonly PackagesController _controller_Packages;
private readonly ILMS_Service _lms_service;
private readonly UrlHelper urlHelper;
public Packages_UnitTest()
{
// Mock WCF
_lms_service = A.Fake<ILMS_Service>();
// Fakes
urlHelper = A.Fake<UrlHelper>();
// SUTs
_controller_Packages = new PackagesController(_lms_service, urlHelper);
}
[TestMethod]
public void should_EditPackageDetails()
{
// Arrange
int packageID = 1;
string package_name = "Test package";
int unit_type = 1;
int product_id = 1;
int unit_count = 10;
string description = "Sample test description";
int expected_statusCode = (int)HttpStatusCode.OK;
string expected_page_destination = "/Packages/PackagesList";
A.CallTo(() => urlHelper.Action("PackagesList", "Packages"))
.Returns("/Packages/PackagesList");
// Act
_ = A.CallTo(() => _lms_service.EditPackageDetails(
A<int>.Ignored,
A<string>.Ignored,
A<int>.Ignored,
A<int>.Ignored,
A<int>.Ignored,
A<string>.Ignored
));
var _editPackage = _controller_Packages.EditPackageDetails(
packageID,
package_name,
unit_type,
product_id,
unit_count,
description
) as JsonResult;
dynamic result = _editPackage.Data;
// Assert
Assert.AreEqual(expected_statusCode, result.statusCode);
Assert.AreEqual(expected_page_destination, result.redirectURL);
}
我的方法上的if
语句似乎是伪造UrlHelper的一种巧妙方法。不过,我无意在那里添加条件语句,所以这不是最优雅的方法。如果有更好的实现,请告诉我。任何附加信息都会有所帮助!