【问题标题】:SharePoint 2010 Client Object Model - Kerberos/Claims AuthenticationSharePoint 2010 客户端对象模型 - Kerberos/声明身份验证
【发布时间】:2012-03-15 19:27:57
【问题描述】:

我正在尝试从远程 SharePoint 网站(不同的 SP Web 应用程序)中的列表中读取值。 Web 应用程序使用声明身份验证进行设置,客户端 Web 应用程序 SP 托管帐户配置有 SPN。我相信 Kerberos 和声明设置正确,但我无法访问远程服务器,并且请求导致异常:“远程服务器返回错误:(401)未授权。”

异常发生在 ctx.ExecuteQuery(); 行中,但它没有在 if (scope.HasException) 中捕获异常,而是由调用代码(在 using{} 块之外)捕获异常。

当我使用 Wireshark 查看远程服务器上的流量时,看起来请求甚至没有到达服务器;就好像 401 发生在 Kerberos 票证兑换为索赔之前。

这是我的代码:

using (ClientContext ctx = new ClientContext(contextUrl))
{

    CredentialCache cc = new CredentialCache();
    cc.Add(new Uri(contextUrl), "Kerberos", CredentialCache.DefaultNetworkCredentials);
    ctx.Credentials = cc;
    ctx.AuthenticationMode = ClientAuthenticationMode.Default; 

    ExceptionHandlingScope scope = new ExceptionHandlingScope(ctx);
    Web ctxWeb = ctx.Web;
    List ctxList;
    Microsoft.SharePoint.Client.ListItemCollection listItems;

    using (scope.StartScope())
    {
        using (scope.StartTry())
        {

            ctxList = ctxWeb.Lists.GetByTitle("Reusable Content");
            CamlQuery qry = new CamlQuery();
            qry.ViewXml = string.Format(ViewQueryByField, "Title", "Text", SharedContentTitle);
            listItems = ctxList.GetItems(qry);
            ctx.Load(listItems, items => items.Include(
                                item => item["Title"],
                                item => item["ReusableHtml"],
                                item => item["ReusableText"]));
        }
        using (scope.StartCatch()) { }
        using (scope.StartFinally()) { }
    }
    ctx.ExecuteQuery();

    if (scope.HasException)
    {
        result = string.Format("Error retrieving content<!-- Error Message: {0} | {1} -->", scope.ErrorMessage, contextUrl);
    }


    if (listItems.Count == 1)
    {
        Microsoft.SharePoint.Client.ListItem contentItem = listItems[0];

        if (SelectedType == SharedContentType.Html)
        {
            result = contentItem["ReusableHtml"].ToString();
        }
        else if (SelectedType == SharedContentType.Text)
        {
            result = contentItem["ReusableText"].ToString();
        }
    }


}

我意识到带有 CredentialCache 的部分在声明中不应该是必需的,但是我能找到的每个示例要么在控制台应用程序中运行,要么在某种客户端应用程序中运行;此代码在常规 ASP.NET UserControl 的代码隐藏中运行。

编辑:我应该提一下,当远程 URL 是与调用代码相同的 Web 应用程序上的根网站集(在网站集中)时,上面的代码甚至不起作用/sites/)--换句话说,即使主机名与调用代码相同。

非常感谢您对下一步尝试的任何建议!

迈克

【问题讨论】:

    标签: sharepoint sharepoint-2010 claims-based-identity sharepoint-clientobject


    【解决方案1】:

    您不使用标准 OM 是否有原因?

    您已经说过这是在 Web 部件中运行的,这意味着它在应用程序池帐户的上下文中。除非您通过切换用户来提升权限,否则它将无法正确进行身份验证。也许尝试一下。但是当您已经可以访问 API 时,我不会使用客户端 OM。

    【讨论】:

    • 我需要能够跨 Web 应用程序和场进行调用...我想我可以放弃跨场功能,但我更愿意保留它。它实际上正在运行在用户控件中,而不是 Web 部件中,但我想就它而言,这里几乎没有区别——它们都在 SPContext 中运行。我认为值得尝试跨网络应用程序调用的服务器端 api,因为我使用的是 kerberos。今天早上我会试一试。
    • 好吧,接下来,我无法在那个环境中使用客户端 OM 进行跨场调用。我仍然不确定这是环境问题还是我这样做的方式有什么隐晦的错误,所以在我自己从头开始建立一个单独的环境之前,我放弃了跨农场的东西,然后去了回到使用标准的服务器端 OM。
    猜你喜欢
    • 2013-03-22
    • 1970-01-01
    • 2016-04-18
    • 1970-01-01
    • 1970-01-01
    • 2012-12-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多