OData / AspNetCoreOData

ASP.NET Core OData: A server library built upon ODataLib and ASP.NET Core
Other
457 stars 158 forks source link

$metadata endpoint does not work when creating the host from a Console Application #1306

Open Molinware opened 2 months ago

Molinware commented 2 months ago

Assemblies affected ASP.NET Core OData 9.0.0

Describe the bug Creating a console application then adding a WebHost to it containing oData, makes the /$metadata endpoint to not be created, generating a 404 - NotFound.

Reproduce steps

- Configure Program.cs:

using System.Net; using Microsoft.AspNetCore.OData; using Microsoft.OData.Edm; using Microsoft.OData.ModelBuilder;

namespace TestePesquisaConsole;

internal class Program { static void Main(string[] args) { Host.CreateDefaultBuilder() .ConfigureWebHostDefaults( webHost => { webHost.UseStartup(); webHost.ConfigureKestrel(kestrel => { kestrel.Listen(IPAddress.Any, 5900); }); }) .Build() .Run(); }

private class Startup
{
    public void ConfigureServices(IServiceCollection services)
    {
        services
            .AddControllers()
            .AddOData(option =>
            {
                option.Select().Filter().OrderBy().Expand().Count().SetMaxTop(null).AddRouteComponents("Pesquisa", GetEdmModel());
                option.TimeZone = TimeZoneInfo.Utc;
            });

        static IEdmModel GetEdmModel()
        {
            ODataConventionModelBuilder builder = new ODataConventionModelBuilder();
            builder.EntitySet<ClientePsqDto>(nameof(ClientePsqBo)).EntityType.Page(null, null);
            return builder.GetEdmModel();
        }
    }

    public void Configure(IApplicationBuilder app)
    {
        app.UseRouting();

        app.UseEndpoints(
            routeBuilder =>
            {
                routeBuilder.MapControllers();
            });
    }
}

}

- Go to: http://localhost:5900/Pesquisa/$metadata and get's 404

**Data Model**

public class ClientePsqDto { [Key] public long Identificador { get; set; }

public string Nome { get; set; } = string.Empty;

}



**EDM (CSDL) Model**
404 - NotFound

**Request/Response**
http://localhost:5900/Pesquisa/$metadata
404 - NotFound

**Expected behavior**
Return the metadata

**Additional context**
In the project file if I change the Project Sdk it works:
Doesn't Work: 
`<Project Sdk="Microsoft.NET.Sdk"> `
Works: 
`<Project Sdk="Microsoft.NET.Sdk.Web"> `
julealgon commented 2 months ago

In the project file if I change the Project Sdk it works: Doesn't Work: <Project Sdk="Microsoft.NET.Sdk"> Works: <Project Sdk="Microsoft.NET.Sdk.Web">

This is very interesting.... I personally had no idea the SDK had that kind of influence in the application side.

Out of curiosity, does it work if you use the Worker SDK? Microsoft.NET.Sdk.Worker?

Molinware commented 2 months ago

In the project file if I change the Project Sdk it works: Doesn't Work: <Project Sdk="Microsoft.NET.Sdk"> Works: <Project Sdk="Microsoft.NET.Sdk.Web">

This is very interesting.... I personally had no idea the SDK had that kind of influence in the application side.

Out of curiosity, does it work if you use the Worker SDK? Microsoft.NET.Sdk.Worker?

Tested! Doesn't work too...

xuzhg commented 2 months ago

FYI: https://learn.microsoft.com/en-us/dotnet/core/project-sdk/overview

The difference between "Microsoft.NET.Sdk" and "Microsoft.NET.Sdk.Web":

image

corranrogue9 commented 2 months ago

Shouldn't the nuget package automatically update the project's SDK? Or if not, include a .props and .targets file in the package to import the SDK like here

julealgon commented 2 months ago

@corranrogue9

Shouldn't the nuget package automatically update the project's SDK?

I don't think that is a thing.

Or if not, include a .props and .targets file in the package to import the SDK like here

But the question is "what is missing exactly"? Why does the metadata controller only work on the Web SDK?

I would be careful with any attempted solution before we fully understand that bit.