web-dev-qa-db-ja.com

.Net CoreのODataが$ selectで正しい結果を返さない

ODataをWebAPIプロジェクトに追加しました。

バージョン:

  1. コア3.1
  2. OData 7.3.0(Core 3.xと連携するためのベータ版)
  3. EF Core 3.1.0

これが私のstartup.csです

public class Startup
{
    public Startup(IConfiguration configuration)
    {
        Configuration = configuration;
    }

    public IConfiguration Configuration { get; }

    public void ConfigureServices(IServiceCollection services)
    {
        services.AddDbContext<Models.Contexts.EntityContext>(opts => opts.UseSqlServer(Configuration["ConnectionString:MailBackup"]));
        services.AddControllers();
        services.AddMvc(options =>
        {
            options.EnableEndpointRouting = false;
        }).SetCompatibilityVersion(Microsoft.AspNetCore.Mvc.CompatibilityVersion.Version_3_0);

        services.AddOData();
    }

    public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
    {
        if (env.IsDevelopment())
        {
            app.UseDeveloperExceptionPage();
        }

        app.UseMvc(routeBuilder =>
        {
            routeBuilder.EnableDependencyInjection();
            routeBuilder.Expand().Select().OrderBy().Filter();
        });

        app.UseHttpsRedirection();
        app.UseAuthorization();

    }
}

そしてコントローラーは:

[EnableQuery()]
[HttpGet]
[Route("GetAll")]
public IQueryable<Models.EmailMessage> GetAll()
{    
    return this._context.EmailMessages;
}

APIは正常に動作していますが、$ selectのようなODataアクションを追加しようとすると、予期した結果ではなく次の結果が得られます。

{
    "instance": null,
    "container": {},
    "modelID": "529e8054-04c4-4729-aa91-d7eaf67a55d0",
    "untypedInstance": null,
    "instanceType": null,
    "useInstanceForProperties": false
},
{
    "instance": null,
    "container": {},
    "modelID": "529e8054-04c4-4729-aa91-d7eaf67a55d0",
    "untypedInstance": null,
    "instanceType": null,
    "useInstanceForProperties": false
},
6
Giox

APIは正常に動作していますが、$ selectのようなODataアクションを追加しようとすると、予期した結果ではなく次の結果が得られます

同じ問題を.NET Core 3.xアプリケーションで再現できますが、共有したのと同様のコードを使用します。現在、次のコードスニペットで既存のAPIコントローラーにODataサービスを挿入すると、.NET Core 3.xがうまくサポートされないようです。

routeBuilder.EnableDependencyInjection();

そして私のテストに基づいて、それは.NET Core 2.xでうまく機能することができます。作る $select機能は.NET Core 3.xで正常に動作します。現在、この回避策を試すことができます。

Startup.cs

var builder = new ODataConventionModelBuilder(app.ApplicationServices);

builder.EntitySet<Product>("Products");


app.UseMvc(routeBuilder =>
{
    // and this line to enable OData query option, for example $filter

    routeBuilder.Expand().Select().OrderBy().Filter();

    routeBuilder.MapODataServiceRoute("ODataRoute", "api", builder.GetEdmModel());

});

In ODataController

public class ProductsController : ODataController
{
    // ...
    //code logic here
    // ...

    [HttpGet]
    [EnableQuery]
    public IQueryable<Product> Get()
    {
        var products = _context.Products;

        return products;
    }

    // ...

}

テスト結果

enter image description here

詳細については、次を確認してください: https://docs.Microsoft.com/en-us/odata/webapi/netcore#e-configure-the-odata-endpoint

1
Fei Han