Search code examples
c#asp.net-corepaginationodataasp.net-core-2.0

Pagination with AspNetCore.OData - missing @odata properties in response


I'm trying to implement pagination with asp.net core 2.2 and Microsoft.AspNetCore.OData 7.1.0 with following configuration:

public class Startup
{
    public void ConfigureServices(IServiceCollection services)
    {
        services.AddOData();
        services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_2);
    }

    public void Configure(IApplicationBuilder app, IHostingEnvironment env)
    {
        app.UseMvc(b =>
        {
            b.EnableDependencyInjection();
        });
    }
}

For this I have a testing controller:

[Route("api/[controller]")]
[ApiController]
public class ValuesController : ControllerBase
{
    [HttpGet]
    [EnableQuery(PageSize = 5)]
    public IQueryable<int> Get()
    {
        return new int[] { 1,2,3,4,5,6,7,8,9,10 }.AsQueryable();
    }
}

When invoking an endpoint, I would expect a response like:

{  
  "@odata.context":...,
  "value":[1,2,3,4,5],
  "@odata.nextLink":...  
}

but instead I get only:

[1,2,3,4,5]

So how do I get those extra @odata properties?


Solution

  • Finally I figured out how to do it.

    First it doesn't work with primitive types so I had to create strong one with Id property:

    public class Value
    {
        public Value(int id)
        {
            Id = id;
        }
    
        public int Id { get; set; }
    }
    

    Second I had to drop ApiController and Route attributes from controller .

    public class ValuesController : ControllerBase
    {
        [HttpGet]
        [EnableQuery(PageSize = 5)]
        public IQueryable<Value> Get()
        {
            return Enumerable.Range(1, 10).Select(i => new Value(i)).AsQueryable();
        }
    }
    

    And finally register odata endpoint:

    ODataModelBuilder builder = new ODataConventionModelBuilder();
    builder.EntitySet<Value>("Values");
    app.UseOData("odata", "api", builder.GetEdmModel());