C# .NET Core 3.1 API调用使用windows身份验证保护的.NET Framework WCF服务(AD组)
我试图从.NET Core 3.1 API调用.NET Framework WCF服务(该服务由使用AD组的Windows身份验证保护),但收到错误消息: System.ServiceModel.Security.MessageSecurityException:HTTP请求未经客户端身份验证方案“协商”授权。从服务器接收的身份验证标头为“协商,NTLM” .NET Core API托管在windows上的IIS中,其运行所在的应用程序池有一个域帐户,该帐户位于访问所需的AD组中。 我们目前有其他.NET Framework应用程序调用WCF服务,它们都可以工作,但是这是第一个调用WCF服务的.NET核心应用程序。C# .NET Core 3.1 API调用使用windows身份验证保护的.NET Framework WCF服务(AD组),c#,wcf,.net-core,C#,Wcf,.net Core,我试图从.NET Core 3.1 API调用.NET Framework WCF服务(该服务由使用AD组的Windows身份验证保护),但收到错误消息: System.ServiceModel.Security.MessageSecurityException:HTTP请求未经客户端身份验证方案“协商”授权。从服务器接收的身份验证标头为“协商,NTLM” .NET Core API托管在windows上的IIS中,其运行所在的应用程序池有一个域帐户,该帐户位于访问所需的AD组中。 我们目前有其
部署API的服务器和部署WCF服务的服务器都存在于支持Kerberos协议的同一域中 它在本地运行时工作成功,但部署到服务器上时会显示上述错误消息 出现以下错误消息的IIS日志: POST/Broadcast.svc-8081-172.27.19.200--4012.50
POST/Broadcast.svc-8081-172.27.19.200--401132121225581 0 这是API中的客户端代理创建代码:
public IWcfClient<IBroadcastService> CreateBroadcastService()
{
var binding = new BasicHttpsBinding(BasicHttpsSecurityMode.Transport);
binding.Security.Transport.ClientCredentialType = HttpClientCredentialType.Windows;
binding.Security.Transport.ProxyCredentialType = HttpProxyCredentialType.Windows;
var client = new WcfClient<IBroadcastService>(
binding,
new EndpointAddress($"{remoteUrl}/Broadcast.svc"));
//My expectation is that the below line would make the call send the AppPoolIdentity Credentials?
client.ClientCredentials.Windows.ClientCredential = CredentialCache.DefaultNetworkCredentials;
return client;
}
API的Program.cs:
public class Program
{
[UsedImplicitly]
public static void Main(string[] args)
{
var appConfig = new ConfigurationBuilder()
// ReSharper disable once StringLiteralTypo
.AddJsonFile("appsettings.json")
.Build();
Log.Logger = new LoggerConfiguration()
.ReadFrom.Configuration(appConfig)
.Enrich.FromLogContext()
.CreateLogger();
CreateHostBuilder(args).Build().Run();
}
[UsedImplicitly]
public static IHostBuilder CreateHostBuilder(string[] args) =>
Host.CreateDefaultBuilder(args)
.ConfigureWebHostDefaults(
webBuilder =>
{
webBuilder.UseStartup<Startup>();
webBuilder.UseIIS();
webBuilder.UseSerilog();
});
}
公共类程序
{
[正确使用]
公共静态void Main(字符串[]args)
{
var appConfig=new ConfigurationBuilder()
//ReSharper禁用一次StringLiteralTypo
.AddJsonFile(“appsettings.json”)
.Build();
Logger.Logger=新的LoggerConfiguration()
.ReadFrom.Configuration(appConfig)
.Enrich.FromLogContext()的
.CreateLogger();
CreateHostBuilder(args.Build().Run();
}
[正确使用]
公共静态IHostBuilder CreateHostBuilder(字符串[]args)=>
Host.CreateDefaultBuilder(args)
.ConfigureWebHostDefaults(
webBuilder=>
{
webBuilder.UseStartup();
webBuilder.UseIIS();
webBuilder.useserlog();
});
}
.NET Framework WCF服务web.config的web.config在like so中具有指定的角色(我已删除实际名称)
有谁能告诉我,我是否遗漏了什么,或者提供了如何缩小问题范围的想法?
如果您需要查看代码的任何其他区域,也请发表意见,我们很乐意提供这些区域。我知道您使用windows身份验证。使用windows身份验证时,服务器还应存在于使用Kerberos协议作为其域控制器的windows域中。 如果服务器不在Kerberos支持的域上,或者Kerberos系统出现故障,则可以使用NT LAN Manager
<bindings>
<basicHttpBinding>
<binding name="SecurityByTransport">
<security mode="Transport">
<transport clientCredentialType="Ntlm"/>
</security>
</binding>
</basicHttpBinding>
</bindings>
有关运输安全的更多信息,请参阅以下链接:
由于它们都托管在同一台计算机上,您可能需要填充BackConnectionHostNames注册表项以禁用环回安全功能 步骤如下:
部署API的服务器和部署WCF服务的服务器都存在于支持Kerberos协议的同一个域上。如果将其更改为NTLM,则会出现以下错误:“HTTP请求未经客户端身份验证方案“NTLM”授权。从服务器收到的身份验证标头为“协商,NTLM”。”我可能要离开这里了……但是……您可能想回顾一下这篇关于一个dotnet核心应用程序使用kerberos(链接到AD)与sql server对话的文章。您应该提到您是在windows或linux上运行dotnet CORE应用程序。但这至少暗示了与dotnetcore的一些差异。谢谢,我更新了我的问题,我发现答案是禁用回环安全检查@granadacodeer您是否将dotnetCore代码部署到IIS?然后,是的,然后你回到更多的网络安全思考。
public class Program
{
[UsedImplicitly]
public static void Main(string[] args)
{
var appConfig = new ConfigurationBuilder()
// ReSharper disable once StringLiteralTypo
.AddJsonFile("appsettings.json")
.Build();
Log.Logger = new LoggerConfiguration()
.ReadFrom.Configuration(appConfig)
.Enrich.FromLogContext()
.CreateLogger();
CreateHostBuilder(args).Build().Run();
}
[UsedImplicitly]
public static IHostBuilder CreateHostBuilder(string[] args) =>
Host.CreateDefaultBuilder(args)
.ConfigureWebHostDefaults(
webBuilder =>
{
webBuilder.UseStartup<Startup>();
webBuilder.UseIIS();
webBuilder.UseSerilog();
});
}
<system.web>
<authentication mode="Windows"/>
<authorization>
<allow roles="DOMAIN\GROUPNAME"/>
<deny users="*"/>
</authorization>
</system.web>
<bindings>
<basicHttpBinding>
<binding name="SecurityByTransport">
<security mode="Transport">
<transport clientCredentialType="Ntlm"/>
</security>
</binding>
</basicHttpBinding>
</bindings>