ASP.NET Core中必需的查询字符串参数

mab*_*ead 8 c# asp.net-core-mvc .net-core asp.net-core

使用ASP.NET Core 1.1和VS2015(sdk 1.0.0-preview2-003131),我有以下控制器:

public class QueryParameters
{
    public int A { get; set; }
    public int B { get; set; }
}

[Route("api/[controller]")]
public class ValuesController : Controller
{
    // GET api/values
    [HttpGet]
    public IEnumerable<string> Get([FromQuery]QueryParameters parameters)
    {
        return new [] { parameters.A.ToString(), parameters.B.ToString() };
    }        
}
Run Code Online (Sandbox Code Playgroud)

如您所见,我有两个查询参数.我想要的是要求其中一个(例如:) A.也就是说,我想使用一个属性(如果可能)来说明这个属性是必需的.然后,我希望ASP.NET在调用我的控制器之前进行此验证.

我本来希望使用Newtonsoft RequiredAttribute来使用与我已经用于验证PUT/POST内容中所需属性相同的属性,但由于url不是JSON字符串,因此显然不使用它.

是否有任何建议让ASP.NET Core自动检查所需的查询参数?

请注意,我知道我可以使用可空的查询参数自行编码检查,但这样做的目的是让ASP.NET在调用我的控制器之前进行验证,从而保持控制器整洁.

Val*_*hel 43

在 ASP.NET Core 2.1 及更高版本中,您可以使用顶级参数验证。您可以将属性放在参数上

    [HttpGet]
    public IActionResult GetDices([Required, Range(1, 6)]int number)
    {
        if (ModelState.IsValid)
        {
            return Ok(_diceRepo.GetDices(number));
        }
        return BadRequest("Something went wrong");
    }
Run Code Online (Sandbox Code Playgroud)

更多关于这个 https://andrewlock.net/coming-in-asp-net-core-2-1-top-level-mvc-parameter-validation/

  • “using Microsoft.AspNetCore.Mvc.ModelBinding;”是我用来引用属性“BindRequired”的内容 (3认同)

Nko*_*osi 19

您可以考虑使用框架的模型绑定功能

根据此处的文档:使用属性自定义模型绑定行为

MVC包含几个可用于将其默认模型绑定行为指向不同源的属性.例如,您可以指定属性是否需要绑定,或者是否应该使用[BindRequired][BindNever] 属性进行绑定.

所以我建议你添加一个BindRequiredAttribute模型属性.

public class QueryParameters
{
    [BindRequired]
    public int A { get; set; }
    public int B { get; set; }
}
Run Code Online (Sandbox Code Playgroud)

从那里,框架应该能够处理绑定和更新模型状态,以便您可以检查操作中模型的状态

[Route("api/[controller]")]
public class ValuesController : Controller
{
    // GET api/values
    [HttpGet]
    public IActionResult Get([FromQuery]QueryParameters parameters)
    {    
        if (ModelState.IsValid)
        {
            return Ok(new [] { parameters.A.ToString(), parameters.B.ToString() });
        }
        return BadRequest();
    }        
}
Run Code Online (Sandbox Code Playgroud)

另一个选项是创建一个自定义模型绑定器,如果不存在所需的查询字符串,该绑定器将使操作出错.

参考:自定义模型绑定


小智 5

让框架为您完成工作。这是一个解决方案,因为在 ASP.NET Core 中似乎有多种方法可以完成相同的事情。但这对我有用并且非常简单。这似乎是一些已经给出的答案的组合。

public class QueryParameters
{
    [Required]
    public int A { get; set; }

    public int B { get; set; }
}

[Route("api/[controller]")]
public class ValuesController : Controller
{
    // GET api/values
    // [HttpGet] isn't needed as it is the default method, but ok to leave in
    // QueryParameters is injected here, the framework takes what is in your query string and does its best to match any parameters the action is looking for. In the case of QueryParameters, you have A and B properties, so those get matched up with the a and b query string parameters
    public IEnumerable<string> Get(QueryParameters parameters)
    {
        if (!ModelState.IsValid)
        {
            return BadRequest(); // or whatever you want to do
        }

        return new [] { parameters.a.ToString(), parameters.b.ToString() };
    }        
}
Run Code Online (Sandbox Code Playgroud)