Sky
Sky

Reputation: 65

ASP.NET Core OData v8.0 Routing Endpoint

Objective

To invoke OData Controllers with Endpoints defined differently to the controller name convention.

Reason

Worried about the brittleness of exposing internal controller names as paths...limiting the ability to rename controllers later.

Context

Using the latest OData libraries available currently (ASP.NET Core OData 8.0 RC)

Trying to make sense of a lot of documentation on MSDN that appears to be legacy/no longer applicable. Working with the what I think is the latest info available, here: https://devblogs.microsoft.com/odata/attribute-routing-in-asp-net-core-odata-8-0-rc/g

So, I'd like to use be able to query api/odata/anyotherroutename/get(1) rather than api/odata/someinternalnameforthecontroller/get(1)

[Route("AnyOtherRouteName")]
public class PresentationLayerExampleAEntityOData03Controller :
             ModuleQueryableODataControllerBase<ExampleAEntityDto>{
  ...
}

Registration

When building the edm model definition, the ControllerName used was developed from a helper method that rips off the Controller suffix from the controller class type name -- and if there is a RouteAttribute it reads its value (replacing [Controller] with the above value). In this case the controller is being registered under AnyOtherRouteName.

Results

Unfortunately... https://localhost:44406/$odata shows it -- but listing it under Non-OData Endpoint mappings rather than OData endpoints:

App.Modules.DevLearn.Presentation.Web.Api.OData.Controllers.Instances.Demo.PresentationLayerExampleAEntityOData03Controller.Get (App.Modules.DevLearn.Presentation.Web) GET AnyOtherRouteName
App.Modules.DevLearn.Presentation.Web.Api.OData.Controllers.Instances.Demo.PresentationLayerExampleAEntityOData03Controller.Get (App.Modules.DevLearn.Presentation.Web) GET AnyOtherRouteName/Get

rather than something more akin to:

App.Modules.DevLearn.Presentation.Web.Api.OData.Controllers.Instances.Demo.PresentationLayerExampleAEntityOData02Controller.Get (App.Modules.DevLearn.Presentation.Web) GET api/odata/v{version}/PresentationLayerExampleAEntityOData02 Yes
App.Modules.DevLearn.Presentation.Web.Api.OData.Controllers.Instances.Demo.PresentationLayerExampleAEntityOData02Controller.Get (App.Modules.DevLearn.Presentation.Web) GET api/odata/v{version}/PresentationLayerExampleAEntityOData02/$count  Yes

Other Outcomes

I tried several combinations in utter despair...and the results are not much better. I'm not getting any form of combination going on.

Where Prefix = "api/odata/v{version}/":

Route ("Things") + HttpVerb("") = FAIL to register as an odata route.
Route ("Things/") + HttpVerb("") = FAIL to register as an odata route.
Route ("Things") + HttpVerb("Things/") = FAIL to register as an odata route.
Route ("api/odata/v{version}/Things") + HttpVerb ("") = FAIL to register as an odata route.
Route ("api/odata/v{version}") + HttpVerb ("Things/") = FAIL to register as an odata route.

ERROR - Route ("") + HttpVerb ("api/odata/")

NO ROUTE + HttpVerb ("Things/") => comes out as "api/odata/v{version}/PresentationLayerExampleAEntityOData03/" (ie...ignoring Verb)
NO ROUTE + HttpVerb ("api/odata/Things/") => comes out as "api/odata/v{version}/PresentationLayerExampleAEntityOData03/" (ie...ignoring Verb)
NO ROUTE + HttpVerb ("api/odata/v{version}/Things/" => comes out as "api/odata/v{version}/PresentationLayerExampleAEntityOData03/" (ie...ignoring Verb)
NO ROUTE + HttpVerb ("api/odata/v{version}/Things/Get" => comes out as "api/odata/v{version}/PresentationLayerExampleAEntityOData03/" (ie...ignoring Verb)
NO ROUTE + HttpVerb ("api/odata/Bang/G") => comes out as "api/odata/v{version}/PresentationLayerExampleAEntityOData03/" (ie...ignoring Verb)
 
NO ROUTE + Route ("api/odata/v{version}/Things/" + HttpGet => comes out as "api/odata/v{version}/PresentationLayerExampleAEntityOData03/" (ie...ignoring Verb)

To my eyes, the above combined urls were all mostly valid OData urls: api/odata/v{version}/ + Things/ + optionalactionhttpverb and should have passed.

Other Inputs?

.UseEndpoints is by default true when configuring OData. And I set it anyway.

Questions

Thank you

Really (it's been driving me nuts for a while).

Upvotes: 3

Views: 1095

Answers (1)

Chen
Chen

Reputation: 5174

ODataRoutePrefixAttribute and ODataRouteAttribute are not specific to ASP.NET, it works in ASP.NET Core as well. They are still available in ASP.NET Core OData 8.0 Preview. But in ASP.NET Core OData 8.0 RC, these two attributes are gone.

For the use of ODataRoutePrefixAttribute and ODataRouteAttribute, you can refer to Routing in ASP.NET Core OData 8.0 Preview.

If these two properties don't work in your code, you can take a look at Sam Xu's explanation of this to see if your Url follows OData conventions.

For more examples and documentation, you can find at this GitHub link.

Upvotes: 2

Related Questions