用于 HttpClient 模拟的 SPN

问题描述

我正在使用 C# 调用 Web 服务,使用 HttpClient 模拟使用 spnego.sourceforge.net 对现有的 java WebLogic Web 服务进行调用。我们将 Windows 机器称为“machinename.forest.company.com”,并将 url 称为“https://weblogicnode.forest.company.com:7772/form/index.jsp”。 WebLogic 服务正在使用用户“serviceid@forest.company.com”的密钥表文件 krb5.keytab。

当 spengo 尝试解码 Kerberos 令牌时,我收到错误“在 GSS-API 级别未指定失败(机制级别:校验和失败)”。

我知道将 UseDefaultCredentials 与 HttpClient 结合使用会在幕后生成 Kerberos 令牌,但我不知道它使用的是什么 SPN。

我已经设置了 SPN:

setspn -S HTTP/machinename.forest.company.com FOREST\SERVICEID
setspn -S HTTPS/machinename.forest.company.com FOREST\SERVICEID

我应该使用不同的 SPN 吗? (“HOST”?端口号?)

客户端需要知道keytab文件吗?如果我使用 Kerberos.NET 和 keytab 文件生成令牌,我还能进行模拟吗?

客户端代码为:

var identity = (WindowsIdentity)System.Security.Principal.WindowsPrincipal.Current.Identity; //asp.net
//var identity = WindowsIdentity.GetCurrent(); //console
using (identity.Impersonate())
{
    using (System.Threading.ExecutionContext.SuppressFlow())
    {
        AppContext.SetSwitch("System.Net.Http.UseSocketsHttpHandler",false);
        HttpClientHandler httpClientHandler = new HttpClientHandler
        {
            UseDefaultCredentials = true,AllowAutoRedirect = true,};
        var cred = CredentialCache.DefaultCredentials.GetCredential(uri,"Negotiate");
        using (var client = new HttpClient(httpClientHandler))
        {
            ServicePointManager.SecurityProtocol = SecurityProtocolType.Ssl3 | SecurityProtocolType.Tls12;
            var message = new HttpRequestMessage(HttpMethod.Get,uri);
            foreach (var headerItem in headerItems)
            {
                message.Headers.Add(headerItem.Key,headerItem.Value);
            }
            var response = client.SendAsync(message).Result;

解决方法

我想通了。我需要在客户端上显式设置 SPN。

if (!System.Net.AuthenticationManager.CustomTargetNameDictionary.ContainsKey(uri.AbsoluteUri))
{
    System.Net.AuthenticationManager.CustomTargetNameDictionary.Add(uri.AbsoluteUri,"HTTPS/weblogicnode.forest.company.com");
}

这里我使用的是 WebLogic 节点而不是机器名称,因此我将其设置为:

setspn -S HTTP/weblogicnode.forest.company.com FOREST\SERVICEID

相关问答

依赖报错 idea导入项目后依赖报错,解决方案:https://blog....
错误1:代码生成器依赖和mybatis依赖冲突 启动项目时报错如下...
错误1:gradle项目控制台输出为乱码 # 解决方案:https://bl...
错误还原:在查询的过程中,传入的workType为0时,该条件不起...
报错如下,gcc版本太低 ^ server.c:5346:31: 错误:‘struct...