控制器OnActionExecuting事件中的单元测试逻辑

时间:2017-01-06 03:32:30

标签: asp.net-mvc unit-testing moq

有一个自定义逻辑可以在我的控制器的OnActionExecuting事件中设置页面标题,如果没有使用action方法的属性设置它,它会设置title的默认值:

[PageTitle("Overriden page title")]
public ActionResult About()
{
    return View();
}

public ActionResult Error()
{
    return View();
}

protected override void OnActionExecuting(ActionExecutingContext filterContext)
{
    //Page title
    var title = filterContext.ActionDescriptor.GetCustomAttributes(typeof(PageTitleAttribute), false);
    if (title.Length == 1)
        ViewBag.Title = ((PageTitleAttribute)(title[0])).Parameter;
    else
        ViewBag.Title = "Default Website Title";
}

我如何对此功能进行单元测试?

1 个答案:

答案 0 :(得分:1)

这就是我最终做的事情(可能对遇到类似问题的人有帮助)。

1)我将控制器中的代码拆分为:

public class BaseController : Controller
{
    protected override void OnActionExecuting(ActionExecutingContext filterContext)
    {
        SetupMetadata(filterContext);
        base.OnActionExecuting(filterContext);
    }

    public virtual void SetupMetadata(ActionExecutingContext filterContext)
    {
        //Page title
        var title = filterContext.ActionDescriptor.GetCustomAttributes(typeof(PageTitleAttribute), false);
        if (title.Length == 1)
            ViewBag.Title = ((PageTitleAttribute)(title[0])).Parameter;
        else
            ViewBag.Title = "Default Page Title";
    }
}

2)从basecontroller派生我的HomeController。

3)然后使用以下单元进行单元测试:

[TestClass]
public class BaseControllerTests
{
    [TestMethod]
    public void OnActionExecuting_should_return_attribute_value_when_set() 
    {
        var ctx = new Mock<ActionExecutingContext>();
        var controller = new HomeController();

        ctx.Setup(c => c.Controller).Returns(controller);
        ctx.Setup(c => c.ActionDescriptor.GetCustomAttributes(typeof(PageTitleAttribute), false)).Returns(new object[] { new PageTitleAttribute("Overriden Title") });

        controller.SetupMetadata(ctx.Object);

        Assert.AreEqual("Overriden Title", controller.ViewBag.Title);
    }

    [TestMethod]
    public void OnActionExecuting_should_return_default_attribute_values_if_attributes_are_missing()
    {
        var ctx = new Mock<ActionExecutingContext>();
        var controller = new HomeController();

        ctx.Setup(c => c.Controller).Returns(controller);
        ctx.Setup(c => c.ActionDescriptor.GetCustomAttributes(typeof(PageTitleAttribute), false)).Returns(new object[0]);

        controller.SetupMetadata(ctx.Object);

        Assert.AreEqual("Default Page Title", controller.ViewBag.Title);
    }
}