2

作为理解 OpenIDConnect 的练习,我正在尝试按照本指南在我的网络应用程序中使用 Google 进行身份验证

问题是我无法读取 Google 发送到我的应用程序的令牌>

var bytes = Convert.FromBase64String(codeEx.Id_token);
var token = Encoding.ASCII.GetString(bytes);

它在第一行失败说:“输入不是有效的 Base-64 字符串,因为它包含非 base 64 字符、两个以上的填充字符或填充字符中的非法字符。”

该文档指出:“ID 令牌是加密签名的 JSON 对象,以 base 64 编码。”

出于显而易见的原因,我不能将令牌放在这里。我努力了:

我得到代码交换响应,并使用 NewtonSoft.Json 库对其进行反序列化:

  var http = new HttpClient(handler);
  HttpResponseMessage result = await http.PostAsync("https://www.googleapis.com/oauth2/v3/token", postData);
  var json = JObject.Parse(await result.Content.ReadAsStringAsync());

  if (json.Property("error") != null)
      throw new Exception(json.Property("error").Value.ToString() + ":" + json.Property("error_description").Value.ToString());

  var codeEx = json.ToObject<CodeExchangeResponse>();

我不知道编码是否存在任何潜在问题。我可以在令牌中看到几个“-”和“_”。

关于如何读取令牌的任何想法?

4

2 回答 2

4

这篇文章

“id_token”以一种称为 JSON Web Token (JWT) 的格式编码。JWT 是“header”、“body”、“signature”由句点 (.) 串联而成。

因此,您只需要拆分id_token.解码第二段:

var http = new HttpClient(handler);
var result = await http.PostAsync("https://www.googleapis.com/oauth2/v3/token", postData);
var json = JObject.Parse(await result.Content.ReadAsStringAsync());
var token = Convert.FromBase64String(json.id_token.split('.')[1]);
于 2015-02-16T20:00:47.590 回答
3

在反序列化令牌的紧凑表示后使用base64url解码(而不是 plain ),如下所示:base64

var http = new HttpClient(handler);
var result = await http.PostAsync("https://www.googleapis.com/oauth2/v3/token", postData);
var json = JObject.Parse(await result.Content.ReadAsStringAsync());
var payload = json.id_token.split('.')[1];
payload = payload.Replace('-', '+').Replace('_', '/');
var base64 = payload.PadRight(payload.Length + (4 - payload.Length % 4) % 4, '=');
var token = Convert.FromBase64String(base64);
于 2015-02-17T13:23:02.127 回答