locked
Web API 2 OData v4 Requesting a Derived Entity Collection keep response 404 RRS feed

Answers

  • User592395570 posted

    Hi Krunal,

    I think you are right. All Url path need to match with a routing config. (my concept was wrong, web api framework not "auto" do it for "cast" case)

    After i refer source code for the tutorial, i found below.

            // GET odata/People('key')/Trips(tripId)/PlanItems/Namespace.DerivedType
            [HttpGet]
            [EnableQuery(PageSize = Utility.DefaultPageSize)]
            [ODataRoute("People({key})/Trips({tripId})/PlanItems/ODataSamples.WebApiService.Models.Event")]
            [ODataRoute("People({key})/Trips({tripId})/PlanItems/ODataSamples.WebApiService.Models.Flight")]
            public IHttpActionResult GetPersonTripDerivedPlanItem([FromODataUri] string key, [FromODataUri] int tripId)
            {
                var person = TripPinSvcDataSource.Instance.People.SingleOrDefault(item => item.UserName == key);
                if (person == null)
                {
                    return NotFound();
                }
    
                var trip = person.Trips.SingleOrDefault(item => item.TripId == tripId);
                if (trip == null)
                {
                    return NotFound();
                }
    
                var derivedType = this.Url.Request.RequestUri.Segments.Last();
    
                return GetDerivedTypeItems(trip.PlanItems, derivedType);
            }

    thank lot for you ! 

    • Marked as answer by Anonymous Thursday, October 7, 2021 12:00 AM
    Tuesday, May 5, 2015 8:29 AM

All replies

  • User1644755831 posted

    Hello keatkeat,

    So i don understand what's the problem cause api/paymentAbles/EFDB.Order keep response 404 ?

    Have you defined a Odata Route that handles this route?

       ODataModelBuilder modelBuilder = new ODataConventionModelBuilder();
                // Create EDM (not shown).
    
                // Create the default collection of built-in conventions.
                var conventions = ODataRoutingConventions.CreateDefault();
                // Insert the custom convention at the start of the collection.
                conventions.Insert(0, new NavigationIndexRoutingConvention());
    
                config.Routes.MapODataRoute(routeName: "ODataRoute",
                    routePrefix: "odata",
                    model: modelBuilder.GetEdmModel(),
                    pathHandler: new DefaultODataPathHandler(),
                    routingConventions: conventions);
    
    

    Please see this for understanding the conventions for odata routing  . http://www.asp.net/web-api/overview/odata-support-in-aspnet-web-api/odata-routing-conventions

    Hope this helps.

    With Regards,

    Krunal Parekh

    Monday, May 4, 2015 11:09 PM
  • User592395570 posted

    hi Krunal,

    thank for your reply. But base on your refer : http://www.asp.net/web-api/overview/odata-support-in-aspnet-web-api/odata-routing-conventions.

    I think this not suit for me, because i am using OData v4 not v3, 

    my routing config setting is 

    config.MapODataServiceRoute("odata", "api", GetModel()); 

    and Attribute Routing http://www.asp.net/web-api/overview/releases/whats-new-in-aspnet-web-api-22#ARI

     

        [ODataRoutePrefix("paymentAbles")]
        public class PaymentAblesController : BaseController
        {
            [ODataRoute("")]
            [EnableQuery(AllowedQueryOptions = AllowedQueryOptions.All)]
            public IQueryable<PaymentAble> get()
            {
                return db.paymentAbles;
            }
          
            [EnableQuery]
            [ODataRoute("({id})")]
            public SingleResult<PaymentAble> getById(int id)
            {
                IQueryable<PaymentAble> result = db.paymentAbles.Where(p => p.id == id);
                return SingleResult.Create(result);
            }
    
            public async Task<IHttpActionResult> getTotal()  
            {
                return Ok(15);
            }
        }

    So any idea more ? 

    Tuesday, May 5, 2015 3:38 AM
  • User1644755831 posted

    Hello keatkeat,

    I am not that much familiar with odata but if you are using attribute routing where have you defined a route for this link api/paymentAbles/EFDB.Order ?

    keatkeat

    [ODataRoutePrefix("paymentAbles")]

    you have prefix so it will mapped to your controller. your default method is get and getbyid accepts {id} parameter which is int by the way so which method do you want api/paymentAbles/EFDB.Order  link to point to? can you explain?

    With Regards,

    Krunal Parekh

    Tuesday, May 5, 2015 3:55 AM
  • User1644755831 posted

    Hello keatkeat,

    Also here are Odata4 changes

    http://www.asp.net/web-api/overview/releases/whats-new-in-aspnet-web-api-22#OData

    Hope this helps.

    With Regards,

    Krunal Parekh

    Tuesday, May 5, 2015 4:03 AM
  • User592395570 posted

    Hi Krunal,

    I follow this tutorial http://www.odata.org/getting-started/advanced-tutorial/ (Requesting a Derived Entity Collection & Filter on Derived Type)

    The url for "/EFDB.Order" is something like a cast, so i think no need to setup a specific attribute routing for it, it should be done by web api framework (if i m wrong concept on it , let me know)

    In my case, the Filter on Derived Type is success. "~/api/paymentAbles?$filter=EFDB.Order/id eq 7" running well. (routing setup like above, web api "auto" help me to cast it)

    just the Requesting a Derived Entity Collection part fail. 

    any idea for me ? 

    Tuesday, May 5, 2015 7:15 AM
  • User592395570 posted

    Hi Krunal,

    I think you are right. All Url path need to match with a routing config. (my concept was wrong, web api framework not "auto" do it for "cast" case)

    After i refer source code for the tutorial, i found below.

            // GET odata/People('key')/Trips(tripId)/PlanItems/Namespace.DerivedType
            [HttpGet]
            [EnableQuery(PageSize = Utility.DefaultPageSize)]
            [ODataRoute("People({key})/Trips({tripId})/PlanItems/ODataSamples.WebApiService.Models.Event")]
            [ODataRoute("People({key})/Trips({tripId})/PlanItems/ODataSamples.WebApiService.Models.Flight")]
            public IHttpActionResult GetPersonTripDerivedPlanItem([FromODataUri] string key, [FromODataUri] int tripId)
            {
                var person = TripPinSvcDataSource.Instance.People.SingleOrDefault(item => item.UserName == key);
                if (person == null)
                {
                    return NotFound();
                }
    
                var trip = person.Trips.SingleOrDefault(item => item.TripId == tripId);
                if (trip == null)
                {
                    return NotFound();
                }
    
                var derivedType = this.Url.Request.RequestUri.Segments.Last();
    
                return GetDerivedTypeItems(trip.PlanItems, derivedType);
            }

    thank lot for you ! 

    • Marked as answer by Anonymous Thursday, October 7, 2021 12:00 AM
    Tuesday, May 5, 2015 8:29 AM