【问题标题】:How to add suffix on API Endpoints .NET Core如何在 API Endpoints .NET Core 上添加后缀
【发布时间】:2022-03-02 10:30:11
【问题描述】:

有没有办法在所有端点路由上自动添加后缀,例如 .json。

v1/users.json
v1/users/{id}.json

所以到目前为止我所尝试的是我创建了一个看起来像这样的 BaseController

[ApiController]
[Route("v1/[controller].json")]
public class BaseController : ControllerBase
{
}

但每次我将它用于我的控制器时,它看起来都是这样的

v1/users.json
v1/users.json/{id}

【问题讨论】:

  • 参数被传递给控制器​​动作。所以{id}.json 应该映射到控制器动作而不是控制器。
  • @Chetan 所以需要总是添加每个动作?是否有路由配置功能可以始终将其添加为后缀?
  • 您可以使用重写中间件在所有端点上接受.json,但在路由期间将其丢弃:docs.microsoft.com/en-us/aspnet/core/fundamentals/…
  • routes.MapRoute怎么样
  • 我先看看你们的建议。谢谢

标签: c# api rest asp.net-core


【解决方案1】:

您可以将额外的路由添加到实际的端点而不是控制器

[ApiController]
[Route("v1/[controller]")]
public class BaseController : ControllerBase
{
    [HttpGet(".json")]
    public IActionResult Get()
    {
    
    }
    
    // Without Route Parameters
    [HttpGet("{id}.json")]
    public IActionResult Get([FromRoute] int id)
    {
          ...
    }

    // With Route and Query Parameters
    [HttpGet("{id}.json/friend")]
    public IActionResult Get([FromRoute]int id,[FromQuery] string friendName)
    {
          ...
    }

    // With Route and Query Parameters and Body
    [HttpPost("{id}.json/friends")]
    public IActionResult Get([FromRoute]int id,[FromQuery] string message, [FromBody]IFilter filter)
    {
          ...
    }
}

【讨论】:

  • 我可以说这是一种方法。但是,如果您在获取端点上有查询参数怎么办?
  • @Carlo 然后你可能会得到类似/v1/base/123.json?abc=6
  • @CarloLuisito 我已经更新了答案,它展示了如何在一个请求中完成 QueryParams、Route Params 和 Body Params。
  • 我也认为问题是 .json 仍然需要添加到仅属于特定控制器的特定端点上?
【解决方案2】:

您可以使用 URL 重写中间件来接受带有 .json 的 URL,然后简单地将其删除。所以像:

/api/users/123/picture.json?query=123

会变成:

/api/users/123/picture?query=123

您可以通过将以下代码添加到 Startup 的 Configure 方法来做到这一点:

var rewriteOptions = new RewriteOptions()
    .AddRewrite(@"^(.*?)(?:\.json)(\?.*)?$", "$1$2");
app.UseRewriter(rewriteOptions);

请参阅docs 了解更多信息。

警告:如果您使用Url.Action(...) 等在代码中生成 URL,则它不会包含.json。重写只影响传入的请求。

【讨论】:

  • 有没有办法强制端点拥有 .json 并且如果没有则返回 not found?
  • @Carlo 您可以在^(?!.*?\.json) 上添加重写(这应该在我上面添加的.AddRewrite 之上)以重定向到不存在的端点,或者可能创建自定义IRule 实现在这种情况下返回 404 结果。
  • 我试过你上面的方法,但似乎没有用。 localhost:5001/v1/users - 工作 localhost:5001/v1/users.json - 不工作
  • @Carlo 将中间件应用于管道的顺序很重要。如果你把它放在app.UseRouting();下面,例如,它不会起作用,因为在它运行之前已经发生了路由。
  • 您还需要在 app.UseStaticFiles(); 之前使用它,这样静态文件中间件就不会尝试为请求提供服务。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-12-16
  • 2021-12-16
  • 1970-01-01
  • 1970-01-01
  • 2018-11-01
相关资源
最近更新 更多