C# IHttpActionResult变量在测试方法中传递null

C# IHttpActionResult变量在测试方法中传递null,c#,unit-testing,moq,asp.net-web-api2,actionmethod,C#,Unit Testing,Moq,Asp.net Web Api2,Actionmethod,我正在为IHttpActionresult控制器编写一个测试方法。ActionResult不为NULL,并且包含必需的数据(Customer.ID=986574123)。但是,在第二行中,变量CreatedResult为null。我希望它将适当的数据返回到CreatedResult。我也在使用Moq框架。我不知道这是否重要。有什么想法吗?如果您需要ActionResult的更多数据,请在下面进行评论。Thx 试验方法代码: var CustomerRepository = new

我正在为IHttpActionresult控制器编写一个测试方法。ActionResult不为NULL,并且包含必需的数据(Customer.ID=986574123)。但是,在第二行中,变量CreatedResult为null。我希望它将适当的数据返回到CreatedResult。我也在使用Moq框架。我不知道这是否重要。有什么想法吗?如果您需要ActionResult的更多数据,请在下面进行评论。Thx

试验方法代码:

        var CustomerRepository = new Mock<ICustomerRepository>();

        CustomerRepository.Setup(x => x.Add()).Returns(new Customer { ID = 986574123, Date = DateTime.Now});      

        var Controller = new CustomerController(CustomerRepository.Object, new Mock<IProductRepository>().Object);
        var config = new HttpConfiguration();
        var request = new HttpRequestMessage(HttpMethod.Post, "http://localhost:38306/api/CreateCustomer");
        var route = config.Routes.MapHttpRoute("DefaultApi", "api/{controller}");
        var routeData = new HttpRouteData(route, new HttpRouteValueDictionary { { "controller", "Customers" } });
        Controller.ControllerContext = new HttpControllerContext(config, routeData, request);
        Controller.Request = request;
        Controller.Request.Properties[HttpPropertyKeys.HttpConfigurationKey] = config;

        IHttpActionResult ActionResult = Controller.CreateCustomer();
        // Null occurs here
        var CreatedResult = ActionResult as CreatedAtRouteNegotiatedContentResult<Customer>;
行动结果数据:

-       Location    {http://localhost:38306/api/createcustomer/986574123}   System.Uri
        AbsolutePath    "/api/createcustomer/986574123" string
        AbsoluteUri "http://localhost:38306/api/createcustomer/986574123"   string
        Authority   "localhost:38306"   string
        DnsSafeHost "localhost" string
        Fragment    ""  string
        Host    "localhost" string
        HostNameType    Dns System.UriHostNameType
        IsAbsoluteUri   true    bool
        IsDefaultPort   false   bool
        IsFile  false   bool
        IsLoopback  true    bool
        IsUnc   false   bool
        LocalPath   "/api/createCustomer/986574123" string
        OriginalString  "http://localhost:38306/api/createcustomer/986574123"   string
        PathAndQuery    "/api/createCustomer/986574123" string
        Port    38306   int
        Query   ""  string
        Scheme  "http"  string
+       Segments    {string[4]} string[]
        UserEscaped false   bool
        UserInfo    ""  string

要使您的测试通过,最简单的更改就是更改这一行

return Created(Request.RequestUri + "/" + NewCustomer.ID.ToString(), new { customerID = NewCustomer.ID });
以下

return Created(Request.RequestUri + "/" + NewCustomer.ID.ToString(), NewCustomer);
问题在于createDatRouteNegottatedContentResult的类型参数不是您所期望的。您尝试将
结果
强制转换为
CreatedAtRouteNegotiatedContentResult
,而其类型实际上是
CreatedAtRouteNegotiatedContentResult方法返回一个CreatedAtRouteNegotiatedContentResult,其类型参数
T
是您传入的
内容的类型,并且您正在传入一个


您希望使用匿名类型仅返回模型中的某些字段,但也希望在声明该类型的上下文之外引用该类型(即在单元测试中)。这是不可能的,参见上面关于匿名类型的链接(<代码>如果必须存储查询结果或将它们传递到方法边界之外,请考虑使用普通的命名结构或类而不是匿名类型。< /代码>)

因此,如果只想返回某些字段,则需要为此创建特定的视图模型

class CustomerDetails
{
     public int customerID { get; set; }
}
然后在你的行动方法中

return Created(Request.RequestUri + "/" + NewCustomer.ID.ToString(), new CustomerDetails { customerID = NewCustomer.ID });

好的,我补充了更多的信息。需要满足哪些条件?@user3754602我根据您提供的新信息更新了我的答案。谢谢。是否有任何方法可以返回类似“new{customerID=NewCustomer.ID}”这样的内容?我不想将所有客户数据发送回客户机,我想将JSON变量命名为customerIDIs有没有办法向客户强制转换匿名类型?然后通过CreateDatRouteneGottatedContentResult?@user3754602传递它,您不能将匿名类型强制转换为对象以外的任何对象(MSDN文档对此进行了说明)。请参阅我的答案以了解另一种可能的解决方案。因为我们知道
CreatedResult
的类型不是
createdRouteneGottatedContentResult
,它的类型是什么?类型是匿名的。那么,这就是问题所在。如何修复代码,同时确保返回的JSON与下面的{customerID=NewCustomer.ID}相同?
return Created(Request.RequestUri + "/" + NewCustomer.ID.ToString(), new CustomerDetails { customerID = NewCustomer.ID });