如果我有这样的控制器:
[HttpPost] public JsonResult FindStuff(string query) { var results = _repo.GetStuff(query); var jsonResult = results.Select(x => new { id = x.Id, name = x.Foo, type = x.Bar }).ToList(); return Json(jsonResult); }
基本上,我从存储库中获取东西,然后将其投影到List<T>匿名类型中。
List<T>
如何进行单元测试?
System.Web.Mvc.JsonResult有一个名为的属性Data,但它的类型object与我们预期的一样。
System.Web.Mvc.JsonResult
Data
object
这是否意味着如果我想测试JSON对象是否具有我期望的属性(“ id”,“ name”,“ type”),我是否必须使用反射?
编辑:
这是我的测试:
// Arrange. const string autoCompleteQuery = "soho"; // Act. var actionResult = _controller.FindLocations(autoCompleteQuery); // Assert. Assert.IsNotNull(actionResult, "No ActionResult returned from action method."); dynamic jsonCollection = actionResult.Data; foreach (dynamic json in jsonCollection) { Assert.IsNotNull(json.id, "JSON record does not contain \"id\" required property."); Assert.IsNotNull(json.name, "JSON record does not contain \"name\" required property."); Assert.IsNotNull(json.type, "JSON record does not contain \"type\" required property."); }
但是我在循环中收到一个运行时错误,指出“对象不包含id的定义”。
当我将断点actionResult.Data定义为List<T>匿名类型时,因此我确定是否通过这些类型进行枚举,可以检查属性。在循环内部,该对象 确实 具有一个名为“ id”的属性-因此不确定是什么问题。
actionResult.Data
RPM,您看起来是正确的。我还有很多要学习的知识dynamic,我也无法获得Marc的工作方法。所以这是我以前的做法。您可能会发现它很有帮助。我只是写了一个简单的扩展方法:
dynamic
public static object GetReflectedProperty(this object obj, string propertyName) { obj.ThrowIfNull("obj"); propertyName.ThrowIfNull("propertyName"); PropertyInfo property = obj.GetType().GetProperty(propertyName); if (property == null) { return null; } return property.GetValue(obj, null); }
然后,我只是使用它对我的Json数据进行断言:
JsonResult result = controller.MyAction(...); ... Assert.That(result.Data, Is.Not.Null, "There should be some data for the JsonResult"); Assert.That(result.Data.GetReflectedProperty("page"), Is.EqualTo(page));