【发布时间】:2021-08-18 00:34:30
【问题描述】:
我面临的问题是ocelot kubernetservicediscorverProvider似乎没有在kubernetes的命名空间上找到其他服务。我的目标是使用api网关调用同一命名空间中其他服务中的api。我目前收到 http 404 Not Found 错误。 api 网关 pod 记录以下内容:
Ocelot.Provider.Kubernetes.KubernetesServiceDiscoveryProvider[0] requestId: 0HM93C93DL2T0:00000003, previousRequestId: no previous request id, message: namespace:serviceservice:managementservice 无法使用,无效。地址必须仅包含主机,例如localhost 和 port 必须大于 0
警告:Ocelot.Responder.Middleware.ResponderMiddleware[0] requestId:0HM93C93DL2T0:00000003,previousRequestId:没有以前的请求 id,消息:错误代码:ServicesAreEmptyError 消息:在 ResponderMiddleware 中发现 NoLoadBalancer 错误中没有服务。请求路径设置错误响应:/api/management/User/3910,请求方法:GET
我怀疑我配置错误。我首先尝试使用有关 kubernetes 的 Ocelot 文档,但该文档已过时。 (一个例子是类型的 sugest 值不起作用更多信息去这个 github 问题Docs/Kubernetes provider are wrong)
然后我继续在线搜索 github 问题、堆栈溢出帖子甚至源代码。但我没有看到我的配置中缺少什么。
我目前使用 minikube 在本地运行 kubernetes。我在网上看到的唯一的事情是其他人错误配置了ocelot.json。但我没有看到我在配置中做错了什么。
(在 kubernetes 上尝试 ocelot 之前,我首先在本地主机上尝试它,以尝试它是否有效并看看它缺少什么。它显然缺乏可以控制具有不同角色的 jwt 的中间件,这些角色有权访问端点. 我现在已经自己编写了中间件,它适用于 ocelot 的本地主机配置)
对于 kubernetes,我的 ocelot.json 配置文件如下所示:
{
"Routes": [
{
"UpstreamPathTemplate": "/api/management/User/{everything}",
"UpstreamHttpMethod": [ "POST", "PUT", "GET" ],
"DownstreamPathTemplate": "/api/management/User/{everything}",
"DownstreamScheme": "http",
"ServiceName": "managementservice",
"AuthenticationOptions": {
"AuthenticationProviderKey": "Bearer",
"AllowedScopes": [ "CompanyId", "http://schemas.xmlsoap.org/ws/2005/05/identity/claims/nameidentifier" ]
},
"RouteClaimsRequirement": { "role": "1,2,3" },
"AddHeadersToRequest": {
"CompanyId": "Claims[CompanyId] > value",
"UserId": "Claims[http://schemas.xmlsoap.org/ws/2005/05/identity/claims/nameidentifier] > value"
}
}
],
"GlobalConfiguration": {
"ServiceDiscoveryProvider": {
"Host": "127.0.0.1",
"Port": 8083,
"Namespace": "service",
"Type": "KubernetesServiceDiscoveryProvider"
}
}
}
我的 startup.cs ConfigureServices 方法如下所示
public void ConfigureServices(IServiceCollection services)
{
services.AddCors(c =>
{
c.AddPolicy("AllowOrigin", options => options.WithOrigins(Configuration["Cors:AllowOrigins"])
.AllowAnyHeader()
.AllowAnyMethod().AllowCredentials());
});
#region Authication settings
TokenValidationParameters tokenValidationParameters = new TokenValidationParameters
{
ValidateIssuerSigningKey = true,
IssuerSigningKey = new SymmetricSecurityKey(Encoding.ASCII.GetBytes(Configuration["Jwt:Key"])),
ValidateIssuer = false,
ValidateAudience = false,
ValidateLifetime = true,
ClockSkew = TimeSpan.Zero
};
services.AddSingleton(tokenValidationParameters);
services.AddAuthentication(
x =>
{
x.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
x.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
}
)
.AddJwtBearer(JwtBearerDefaults.AuthenticationScheme, x =>
{
x.RequireHttpsMetadata = false;
x.SaveToken = true;
x.TokenValidationParameters = tokenValidationParameters;
});
#endregion
//Some more code
services.AddOcelot().AddKubernetes();
}
我的 startup.cs 配置方法如下所示
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
// some more code
app.UseOcelot(configuration);
}
我的 program.cs CreateHostBuilder 方法如下所示
public static IHostBuilder CreateHostBuilder(string[] args) =>
Host.CreateDefaultBuilder(args)
.ConfigureAppConfiguration((hostingContext, config) =>
{
config.AddJsonFile("secrets/appsettings.kubernetes.json", optional: true)
.AddJsonFile("ocelot.json");
})
.ConfigureWebHostDefaults(webBuilder =>
{
webBuilder.UseStartup<Startup>();
});
【问题讨论】:
标签: kubernetes .net-5 ocelot