3

我正在编写一个小工具,以使用支持票信息与我们的支持客户打开 WebEx。当网站使用用户名/密码时,我可以让它工作,现在我们使用 SSO。WebEx 服务器已设置为接受 SSO(由我们的 IT 经理 - 而不是我)。

WebEx 参考(链接如下)没有详细说明,官方网站上的 WebEx 开发论坛是如此休眠,并且没有关于该主题的答案,所以我决定在这里试试运气。
在官方论坛上发布了同样的问题

任何人都知道如何使下面的代码真正起作用?标签中的内容并将代码中的以下行<samlResponse>替换为使其工作的内容:

    <samlResponse>samlResponse message will go here</samlResponse>

文档中的SAML 断言(见下文)是什么意思?

到目前为止我发现了什么

WebEx 的XML-API 文档(第 68 页)描述了以下内容:

3.1 认证用户

AuthenticateUser API 将接受 SAML 断言来代替用户密码。返回的内容可用于后续 XML API 请求,而不用于超级管理员中定义的会话持续时间。这可以代替当前对 a 和对身份验证的要求。...

以下架构图显示了 AuthenticateUser 请求消息的元素结构。

然后它提供了 XML 模式图和一个示例。

引用示例 .NET 代码(不使用 SAML)我想出了以下代码:

string strXMLServer = "https://varonis.webex.com/WBXService/XMLService";
WebRequest request = WebRequest.Create(strXMLServer);
// Set the Method property of the request to POST.
request.Method = "POST";
// Set the ContentType property of the WebRequest.
request.ContentType = "application/x-www-form-urlencoded";

// Create POST data and convert it to a byte array.
Func<StringBuilder, StringBuilder> webExXML =
    bodySB => new StringBuilder(1024) // Currently 294 bytes in length
        .AppendLine("<?xml version=\"1.0\" encoding=\"ISO-8859-1\"?>")
        .Append("<serv:message xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\"")
        .Append(" xmlns:serv=\"http://www.webex.com/schemas/2002/06/service\"")
        .Append(" xsi:schemaLocation=\"http://www.webex.com/schemas/2002/06/service")
        .Append(" http://www.webex.com/schemas/2002/06/service/service.xsd\">") 
        .AppendLine("<header>")
        .AppendLine("<securityContext>")
        .AppendLine("<siteName>siteName</siteName>")
        .AppendLine("<webExID>username</webExID>")
        .AppendLine("<password></password>")
        .AppendLine("<partnerID></partnerID>")
        .AppendLine("</securityContext>")
        .AppendLine("</header>")
        .AppendLine()
        .AppendLine("<body>")
        .Append(bodySB)
        .AppendLine()
        .AppendLine("</body>")
        .AppendLine("</serv:message>");

var xmlAuthBodyContent = new StringBuilder()
    .AppendLine("<bodyContent ")
    .AppendLine("xsi:type=\"java:com.webex.service.binding.user.AuthenticateUser\">")
    .AppendLine("<samlResponse>samlResponse message will go here</samlResponse>")
    .AppendLine("</bodyContent>");

byte[] byteArray = Encoding.UTF8.GetBytes(webExXML(xmlAuthBodyContent).ToString());

// Set the ContentLength property of the WebRequest.
request.ContentLength = byteArray.Length;

// Get the request stream.
Stream dataStream = request.GetRequestStream();
// Write the data to the request stream.
dataStream.Write(byteArray, 0, byteArray.Length);
// Close the Stream object.
dataStream.Close();
// Get the response.
WebResponse response = request.GetResponse();

DataSet DSResponse = new DataSet();
DSResponse.ReadXml(response.GetResponseStream());
DSResponse.GetXml().Dump();

我得到的结果是:

<serv:message xmlns:serv="http://www.webex.com/schemas/2002/06/service">
<serv:header>
    <serv:response>
    <serv:result>FAILURE</serv:result>
    <serv:reason>Authentication Server can't generate a valid session ticket</serv:reason>
    <serv:gsbStatus>PRIMARY</serv:gsbStatus>
    <serv:exceptionID>030048</serv:exceptionID>
    <serv:subErrors>
        <serv:subError>
        <serv:exceptionID>AS0062</serv:exceptionID>
        <serv:reason>Validate assertion failed</serv:reason>
        <serv:value />
        </serv:subError>
    </serv:subErrors>
    </serv:response>
</serv:header>
<serv:body>
    <serv:bodyContent />
</serv:body>
</serv:message>
4

2 回答 2

4

我终于在 WebEx 论坛上得到了一个 Nathan Morrow 的回复,我在征得他的许可的情况下复制了这里的内容,以防有人在这里发现这很有用。

答案:

SAML 断言是用于基于 SAML 的身份验证的 XML 样式文档。它包括身份验证所需的几个值和使用先前配置的信任证书的数字签名。您将需要与 IT 合作,以获得从正在使用的身份管理系统中检索 SAML 断言的访问权限。一旦您能够以 BASE64 格式检索 SAML 断言(在这种格式中它看起来不像 XML,只是一个字符块),然后您将把整个断言放入您的 authenticateUser 请求中的 samlResponse 元素中。

然后我询问了 WebEx One-Click 工具是如何做到的,他回答说:

WebEx 生产力工具使用自定义内部 API 和 Web 浏览器功能访问您的公司身份验证门户以确认身份验证。在幕后有一个 SAML 断言。一旦您能够为您的工具检索断言,它也会在幕后向最终用户显示。

于 2013-01-02T18:42:40.870 回答
1

为线程死灵道歉,但这里的答案并没有那么有帮助,我想我会在 C# 中包含一个完整的工作示例(针对 ADFS 3.0 服务器进行测试),从上面的代码和一些额外的项目中一起破解:

 var handler = new HttpClientHandler
        {
            UseDefaultCredentials = true,
            AllowAutoRedirect = true,
            CookieContainer = new System.Net.CookieContainer(),
            UseCookies = true
        };
        var client = new HttpClient(handler) {MaxResponseContentBufferSize = 256000};
        client.DefaultRequestHeaders.Add("User-Agent", "Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.2; WOW64; Trident/6.0)");
        client.DefaultRequestHeaders.Add("Connection", "Keep-Alive");
        client.DefaultRequestHeaders.ExpectContinue = false;


        var samlResponseString = client
            .GetStringAsync(
                new Uri("https://AdfsServer/adfs/ls/IdpInitiatedSignOn.aspx?logintoRP=RPIdentifier")).Result;


        var parsedSamlResponse = "";
        Regex reg = new Regex("SAMLResponse\\W+value\\=\\\"([^\\\"]+)\\\"");
        MatchCollection matches = reg.Matches(samlResponseString);
        foreach (Match m in matches)
        {
            parsedSamlResponse =  m.Groups[1].Value;
        }        

        string strXMLServer = "https://mysite.webex.com/WBXService/XMLService";
        WebRequest request = WebRequest.Create(strXMLServer);
// Set the Method property of the request to POST.
        request.Method = "POST";
// Set the ContentType property of the WebRequest.
        request.ContentType = "application/x-www-form-urlencoded";

// Create POST data and convert it to a byte array.
        Func<StringBuilder, StringBuilder> webExXML =
            bodySB => new StringBuilder(1024) // Currently 294 bytes in length
                .AppendLine("<?xml version=\"1.0\" encoding=\"ISO-8859-1\"?>")
                .Append("<serv:message xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\"")
                .Append(" xmlns:serv=\"http://www.webex.com/schemas/2002/06/service\"")
                .Append(" xsi:schemaLocation=\"http://www.webex.com/schemas/2002/06/service")
                .Append(" http://www.webex.com/schemas/2002/06/service/service.xsd\">")
                .AppendLine("<header>")
                .AppendLine("<securityContext>")
                .AppendLine("<siteName>siteName</siteName>")
                .AppendLine("<webExID>adminUsername</webExID>")                    
                .AppendLine("</securityContext>")
                .AppendLine("</header>")
                .AppendLine()
                .AppendLine("<body>")
                .Append(bodySB)
                .AppendLine()
                .AppendLine("</body>")
                .AppendLine("</serv:message>");

        var xmlAuthBodyContent = new StringBuilder()
            .AppendLine("<bodyContent ")
            .AppendLine("xsi:type=\"java:com.webex.service.binding.user.AuthenticateUser\">")
            .AppendLine($"<samlResponse>{parsedSamlResponse}</samlResponse>")
            .AppendLine("<protocol>SAML2.0</protocol>")
            .AppendLine("</bodyContent>");

        byte[] byteArray = Encoding.UTF8.GetBytes(webExXML(xmlAuthBodyContent).ToString());

// Set the ContentLength property of the WebRequest.
        request.ContentLength = byteArray.Length;

// Get the request stream.
        Stream dataStream = request.GetRequestStream();
// Write the data to the request stream.
        dataStream.Write(byteArray, 0, byteArray.Length);
// Close the Stream object.
        dataStream.Close();
// Get the response.
        WebResponse response = request.GetResponse();

        DataSet DSResponse = new DataSet();
        DSResponse.ReadXml(response.GetResponseStream());
        string xmlResponse = DSResponse.GetXml();

更改代码以反映您的 ADFS 服务器、RP 标识符、Webex 站点名称和管理员用户名。

缺少的重要部分:

  • 从 ADFS 获取 SAMLResponse 的代码
  • 块中的protocol标签bodyContent(设置为SAML2.0
于 2018-09-26T20:40:07.063 回答