从Google OpenID迁移到新的OAuth 2

时间:2014-03-18 14:09:59

标签: c# oauth openid dotnetopenauth google-oauth

我看到有一些问题已经存在,但我找不到任何细节。

我之前使用过自己的DotNetOpenAuth代码,但现在我决定切换到Microsoft Wrapper for Authentication。无论如何,我发现这个非常好的OAuth客户端:

https://github.com/mj1856/DotNetOpenAuth.GoogleOAuth2

它似乎工作正常,但现在它来到迁移部分。在我当前的登录系统中,我保存了Google返回的完整OpenID网址,其格式为:

https://www.google.com/accounts/o8/id?id= ????????????????????????????????????

根据此处的文档https://developers.google.com/accounts/docs/OpenID,我应该可以通过新的OAuth系统以某种方式获得该值。

我在Auth请求中包含了“openid.realm”参数。

    return BuildUri(AuthorizationEndpoint, new NameValueCollection
        {
            { "response_type", "code" },
            { "client_id", _clientId },
            { "scope", string.Join(" ", scopes) },
            { "redirect_uri", returnUrl.GetLeftPart(UriPartial.Path) },
            { "state", state },
            { "openid.realm", "http://myoldopenidrealm" }
        });

据我了解文档应该是我需要做的全部。我确保我用于OpenID 2身份验证的Realm是相同的,它也与我的返回URL相同。

在我完成之后,我执行了令牌请求,据我所知,我应该看到一个“open_id”字段,但我无法理解如何获取它。

protected override string QueryAccessToken(Uri returnUrl, string authorizationCode) {
    var postData = HttpUtility.ParseQueryString(string.Empty);
    postData.Add(new NameValueCollection
        {
            { "grant_type", "authorization_code" },
            { "code", authorizationCode },
            { "client_id", _clientId },
            { "client_secret", _clientSecret },
            { "redirect_uri", returnUrl.GetLeftPart(UriPartial.Path) },
        });

    var webRequest = (HttpWebRequest)WebRequest.Create(TokenEndpoint);

    webRequest.Method = "POST";
    webRequest.ContentType = "application/x-www-form-urlencoded";

    using (var s = webRequest.GetRequestStream())
    using (var sw = new StreamWriter(s))
        sw.Write(postData.ToString());

    using (var webResponse = webRequest.GetResponse()) {
        var responseStream = webResponse.GetResponseStream();
        if (responseStream == null)
            return null;

        using (var reader = new StreamReader(responseStream)) {
            var response = reader.ReadToEnd();
            var json = JObject.Parse(response);
            var accessToken = json.Value<string>("access_token");
            return accessToken;
        }
    }
}

这是文档所说的,我看不到“sub”或“openid_id”字段。

*来自该令牌请求的响应包括常用字段(access_token等),以及openid_id字段和标准OpenID Connect子字段。在此上下文中您需要的字段是openid_id和sub:*

1 个答案:

答案 0 :(得分:2)

sub和openid_id字段包含在OpenID Connect ID token中,而不是访问令牌中。

您可以通过令牌端点(用于检索访问令牌的那个)获取ID令牌,或者您也可以直接从OpenID Connect身份验证请求中获取ID令牌(通过将id_token添加到response_type参数,可能会节省对令牌端点的后端调用。)

希望有所帮助!

-

如何获取ID令牌的示例

(使用oauthplayground生成的流程 - 强烈推荐的调试OAuth2 / OpenID Connect流程的工具)

  1. 转到https://developers.google.com/oauthplayground
  2. 选择(例如)Oauth2 API v2 userinfo.email范围
  3. 点击授权API
  4. 批准OAuth2请求
  5. 按下代币的#34; Exchange授权码&#34;按钮。
  6. 您可以查看所有http请求/响应。有趣的是,对Google代码API调用的响应包含

    {   &#34; access_token&#34;:&#34; ya29.XYZ&#34;,   &#34; token_type&#34;:&#34; Bearer&#34;,   &#34; expires_in&#34;:3600,   &#34; refresh_token&#34;:&#34; 1 / KgXYZ&#34;,   &#34; id_token&#34;:&#34; my.id.token&#34; }

    您可以对64获取的ID令牌的有效负载进行解码(在此示例中为&#34; id&#34;)并获取所有相关的用户信息。要手动执行base 64解码,您可以使用任何在线工具(例如,请参阅https://www.base64decode.org/)。