如何对剃刀视图进行单元测试

Posted

技术标签:

【中文标题】如何对剃刀视图进行单元测试【英文标题】:How to unit-test a razor-view 【发布时间】:2016-01-30 22:31:17 【问题描述】:

当 Scott Guthrie first blogged on Razor 时,他写道

新的视图引擎实现将支持对视图进行单元测试(无需控制器或 Web 服务器,并且可以托管在任何单元测试项目中 - 无需特殊的应用程序域)。

但是,我找不到其他关于剃须刀可测试性的声明(或示例)。 有一些使用 CodelanguageServie 或 RazorGenerator 或 some self-made renderer 的指针——我称之为“设计使然”。

目前是否可以以简单的方式对剃刀视图进行单元测试? (在 asp.net mvc-application 中,即 NancyFx 在它的 nancy.testing-package 中带来了可测试性。)

(目前我不在乎if views should be tested or not。)

我知道有loads of questions like this one,但是大部分都比较老了……

【问题讨论】:

【参考方案1】:

我认为您可以对任何 Razor 视图进行单元测试,如下所示:

ViewResult v = View("~/Views/Home/Index.cshtml");
            if (string.IsNullOrEmpty(v.ViewName))
                v.ViewName = RouteData.GetRequiredString("action");
            ViewEngineResult result = null;
            StringBuilder sb = new StringBuilder();
            StringWriter textwriter = new StringWriter(sb);
            HtmlTextWriter htmlwriter = new HtmlTextWriter(textwriter);
            if (v.View == null)
            
                result = new ViewEngineResult(new RazorView(ControllerContext,"~/Views/Home/Index.cshtml", null,false,null), new RazorViewEngine());
                v.View = result.View;
            
            ViewContext viewContext = new ViewContext(ControllerContext, v.View, ViewData, TempData, htmlwriter);
            v.View.Render(viewContext, htmlwriter);
            string html = sb.ToString();

在此之后,您可以解析html以检查内容是否符合规范。

【讨论】:

这个建议仍然需要一个控制器,包括控制器上下文和提供的各种属性。虽然它们可以在某种程度上被嘲笑,但这段代码 - 在使用有效 HttpContext.Current 运行的控制器之外 - 在System.Web.Compilation.BuildManager.GetCacheKeyFromVirtualPath(VirtualPath virtualPath, Boolean& keyFromVPP) 中运行到 NRE (NullReferenceException)。因此,寻找一种简单的方法来测试视图,例如继续执行RazorView.Render(string viewName, object model) 之类的内容。视图/部分似乎仍然不可测试。

以上是关于如何对剃刀视图进行单元测试的主要内容,如果未能解决你的问题,请参考以下文章

如何对在 Swift 中调用的私有方法进行单元测试

Django单元测试测试视图问题,怎么解决

如何在 django 中对文件上传进行单元测试

如何对使用 Axios(或其他异步更新)的 Vue 组件进行单元测试?

对指令进行单元测试 - 无法强制使用虚假数据

如何调整我的视图模型以实现依赖注入 swiftui(用于以后的单元测试)