You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

OData路由结合API版本控制时出现重复路由模板运行时异常

OData路由结合API版本控制时出现重复路由模板运行时异常

看起来你遇到的问题是因为控制器手动配置的路由和Asp.Versioning的OData路由组件配置重复叠加导致的,从异常信息里能看到v2的Get方法路由模板变成了odata/v{version:apiVersion}/Parts/odata/v{version:apiVersion}/Parts,明显是两次路由配置拼接的结果。下面是具体的解决步骤:

1. 移除控制器上的[Route]属性

你现在在v1和v2的PartsController上都加了[Route("odata/v{version:apiVersion}/[controller]")],但Asp.Versioning的OData集成会自动根据你配置的路由前缀生成对应路由,手动添加这个属性会和OData的路由配置冲突,导致重复拼接。

修改后的v1控制器示例:

namespace ...Api.Versions.v1.Controllers
{
    [ApiController]
    [ApiExplorerSettings(GroupName = "v1")]
    [ApiVersion("1")]
    // 移除手动的[Route]属性
    public class PartsController : ODataController
    {
        [Produces("application/json")]
        [EnableQuery]
        [HttpGet]
        public async Task<IQueryable<Part>> Get()
        {
            ...
        }
    }
}

v2的PartsController做同样的修改即可。

2. 调整API版本控制的OData配置

确保AddApiVersioning中的OData路由组件配置正确,同时避免和AddControllers中的OData配置重复冲突:

修改后的ConfigureServices示例:

public void ConfigureServices(IServiceCollection services)
{
   ...
    // 基础控制器配置,只保留OData的通用查询特性
    services.AddControllers()
        .AddOData(options =>
        {
            options.EnableQueryFeatures(maxTopValue: 8000);
            options.TimeZone = TimeZoneInfo.Utc;
        });

    services.AddApiVersioning(options =>
        {
            options.AssumeDefaultVersionWhenUnspecified = true;
            options.DefaultApiVersion = new ApiVersion(1);
            options.ReportApiVersions = true;
            options.ApiVersionReader = new UrlSegmentApiVersionReader();
        })
        .AddMvc()
        .AddOData(options =>
        {
            // 这里只配置OData路由组件前缀,由版本控制自动填充版本号
            options.AddRouteComponents("odata/v{version:apiVersion}");
        })
        .AddODataApiExplorer(options =>
        {
            options.GroupNameFormat = "'v'V";
            options.SubstituteApiVersionInUrl = true;
        });
    ...
}

3. 验证模型配置

你的PartModelConfiguration已经正确实现了IModelConfiguration接口,Asp.Versioning会自动发现并注册它,这部分不需要修改。后续如果v1和v2的模型有差异,直接在ConfigureV1和ConfigureV2方法中调整即可。

为什么这样能解决问题?

Asp.Versioning的OData集成会自动为每个版本的控制器生成匹配odata/v{version:apiVersion}/[controller]格式的路由,如果你手动在控制器上加[Route]属性,就会导致路由模板被重复拼接,最终触发“相同名称的路由必须有相同模板”的运行时异常。移除手动路由配置后,由版本控制组件统一管理路由生成,就能避免这个问题。

备注:内容来源于stack exchange,提问作者Jack Cotterill

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.14 10:17:59