如何在 C# 中为 Google AutoML 获取 OAuth 2.0 身份验证承载令牌?
How to get an OAuth 2.0 authentication bearer token in C# for Google AutoML?
以下代码从 google 抛出返回响应,缺少必需的参数:response_type。该错误可能会误导其他内容,或者该值可能是错误的。这是文档:https://cloud.google.com/docs/authentication/#oauth-2.0-clients
var client = new RestClient("https://accounts.google.com/o/oauth2/auth");
var request = new RestRequest(Method.POST);
request.AddHeader("cache-control", "no-cache");
request.AddHeader("content-type", "application/x-www-form-urlencoded");
request.AddParameter("application/x-www-form-urlencoded", "grant_type=client_credentials&client_id=501819637859-6ng1c949htt0admmpa19vm6tfle04jdc.apps.googleusercontent.com&client_secret=nrrIjxFqugLKd24E8xVesA6f", ParameterType.RequestBody);
IRestResponse response = client.Execute(request);
是的,可以编写您自己版本的 Google Oauth2 流程。
第一次通话
第一个调用是 HTTP GET,是 link 显示给用户的同意屏幕。
如果这是已安装的应用程序,例如桌面应用程序或控制台应用程序。那么重定向 uri 应该是 urn:ietf:wg:oauth:2.0:oob.
范围应该用space分开,如果你想要一个以上,如果你想取回刷新令牌,请添加离线。
GET https://accounts.google.com/o/oauth2/v2/auth?client_id={clientid}&redirect_uri={RedirectURI}&scope={scopes}&response_type=code
第二次通话
第一次调用的响应是验证码,此代码需要与 google 交换。这是一个 HTTP POST
POST https://oauth2.googleapis.com/token
code=4/X9lG6uWd8-MMJPElWggHZRzyFKtp.QubAT_P-GEwePvB8fYmgkJzntDnaiAI&client_id=
{ClientId}&client_secret={ClientSecret}&redirect_uri={RedirectURI}&grant_type=authorization_code
此调用的 post 数据是一个长字符串,请勿尝试解析它。只需 post 它在您的通话正文中。您是正确的,内容类型是“application/x-www-form-urlencoded”;
对此调用的响应将包含一个访问令牌和一个刷新令牌
{
"access_token" : "ya29.1.AADtN_VSBMC2Ga2lhxsTKjVQ_ROco8VbD6h01aj4PcKHLm6qvHbNtn-_BIzXMw",
"token_type" : "Bearer",
"expires_in" : 3600,
"refresh_token" : "1/J-3zPA8XR1o_cXebV9sDKn_f5MTqaFhKFxH-3PUPiJ4"
}
访问令牌将在一小时后过期,因此您需要刷新它,这就是刷新令牌的用途。
刷新访问令牌
下面的调用也是HTTP POST
https://oauth2.googleapis.com/token
client_id={ClientId}&client_secret={ClientSecret}&refresh_token={Refresh token from previous call}&grant_type=refresh_token
工作示例
class Program
{
private const string Clientid = "Add yours";
private const string Secret = "Add yours.";
static async Task Main(string[] args)
{
Console.WriteLine("Hello World!");
Console.WriteLine($"open the following link in your browser window: {Helper.BuildConsentURL(Clientid, new []{ "profile" })}");
Console.WriteLine("Please paste the Authorization code here:");
var authorizationCode = Console.ReadLine();
var tokenResponse = await Helper.ExchangeAuthorizationCode(authorizationCode, Clientid, Secret);
var refreshTokenResponse = await Helper.ExchangeRefreshToken(tokenResponse.refresh_token, Clientid, Secret);
}
}
Helper.cs
public class Helper
{
/// <summary>
///
/// </summary>
/// <param name="clientId"></param>
/// <param name="scope">string array of scopes</param>
/// <param name="redirectUri">leave empty for installed application</param>
/// <returns></returns>
public static string BuildConsentURL(string clientId, string[] scope, string redirectUri = null)
{
if (string.IsNullOrEmpty(redirectUri))
{
redirectUri = "urn:ietf:wg:oauth:2.0:oob"; // for installed application
}
return
$"https://accounts.google.com/o/oauth2/auth?client_id={clientId}&redirect_uri={redirectUri}&scope={string.Join(" ", scope)}&response_type=code";
}
private static string BuildAuthorizationCodeRequest(string code, string clientId, string secret,
string redirectUri)
{
return
$"code={code}&client_id={clientId}&client_secret={secret}&redirect_uri={redirectUri}&grant_type=authorization_code";
}
private static string BuildRefreshAccessTokenRequest(string refreshToken, string clientId, string secret)
{
return
$"client_id={clientId}&client_secret={secret}&refresh_token={refreshToken}&grant_type=refresh_token";
}
private static async Task<AuthResponse> PostMessage(string postData)
{
AuthResponse result;
var client = new HttpClient();
client.BaseAddress = new Uri("https://accounts.google.com/");
var request = new HttpRequestMessage(HttpMethod.Post, "o/oauth2/token");
request.Content = new StringContent(postData, Encoding.UTF8, "application/x-www-form-urlencoded");
var response = await client.SendAsync(request);
using (var content = response.Content)
{
var json = content.ReadAsStringAsync().Result;
result = JsonSerializer.Deserialize<AuthResponse>(json);
}
return result;
}
public static async Task<AuthResponse> ExchangeAuthorizationCode(string code, string clientId, string secret,
string redirectUri = null)
{
var result = new AuthResponse();
if (string.IsNullOrEmpty(redirectUri))
{
redirectUri = "urn:ietf:wg:oauth:2.0:oob"; // for installed application
}
var postData = BuildAuthorizationCodeRequest(code, clientId, secret, redirectUri);
return await PostMessage(postData);
}
public static async Task<AuthResponse> ExchangeRefreshToken(string refreshToken, string clientId, string secret)
{
var postData = BuildRefreshAccessTokenRequest(refreshToken, clientId, secret);
return await PostMessage(postData);
}
}
authresonse.cs
public class AuthResponse
{
public string access_token { get; set; }
public string token_type { get; set; }
public int expires_in { get; set; }
public string refresh_token { get; set; }
}
试试这个。
String client_id = "<OAUTH_client_id >";
String client_secret = "<OAUTH_client_secret>";
var BaseAddress = "https://gateway-stage-core.optum.com";
var httpClient = new HttpClient() { BaseAddress = new Uri(BaseAddress) };
var creds = $"client_id={client_id}&client_secret={client_secret}&grant_type=client_credentials";
httpClient.DefaultRequestHeaders.Accept.Clear();
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/x-www-form-urlencoded"));
var content = new StringContent(creds, Encoding.UTF8, "application/x-www-form-urlencoded");
var response = httpClient.PostAsync("/auth/oauth2/cached/token", content).Result;
var jsonContent = response.Content.ReadAsStringAsync().Result;
var tokenObj = JsonConvert.DeserializeObject<BearerViewModel>(jsonContent);
var token = tokenObj.access_token;
以下代码从 google 抛出返回响应,缺少必需的参数:response_type。该错误可能会误导其他内容,或者该值可能是错误的。这是文档:https://cloud.google.com/docs/authentication/#oauth-2.0-clients
var client = new RestClient("https://accounts.google.com/o/oauth2/auth");
var request = new RestRequest(Method.POST);
request.AddHeader("cache-control", "no-cache");
request.AddHeader("content-type", "application/x-www-form-urlencoded");
request.AddParameter("application/x-www-form-urlencoded", "grant_type=client_credentials&client_id=501819637859-6ng1c949htt0admmpa19vm6tfle04jdc.apps.googleusercontent.com&client_secret=nrrIjxFqugLKd24E8xVesA6f", ParameterType.RequestBody);
IRestResponse response = client.Execute(request);
是的,可以编写您自己版本的 Google Oauth2 流程。
第一次通话
第一个调用是 HTTP GET,是 link 显示给用户的同意屏幕。
如果这是已安装的应用程序,例如桌面应用程序或控制台应用程序。那么重定向 uri 应该是 urn:ietf:wg:oauth:2.0:oob.
范围应该用space分开,如果你想要一个以上,如果你想取回刷新令牌,请添加离线。
GET https://accounts.google.com/o/oauth2/v2/auth?client_id={clientid}&redirect_uri={RedirectURI}&scope={scopes}&response_type=code
第二次通话
第一次调用的响应是验证码,此代码需要与 google 交换。这是一个 HTTP POST
POST https://oauth2.googleapis.com/token
code=4/X9lG6uWd8-MMJPElWggHZRzyFKtp.QubAT_P-GEwePvB8fYmgkJzntDnaiAI&client_id=
{ClientId}&client_secret={ClientSecret}&redirect_uri={RedirectURI}&grant_type=authorization_code
此调用的 post 数据是一个长字符串,请勿尝试解析它。只需 post 它在您的通话正文中。您是正确的,内容类型是“application/x-www-form-urlencoded”;
对此调用的响应将包含一个访问令牌和一个刷新令牌
{
"access_token" : "ya29.1.AADtN_VSBMC2Ga2lhxsTKjVQ_ROco8VbD6h01aj4PcKHLm6qvHbNtn-_BIzXMw",
"token_type" : "Bearer",
"expires_in" : 3600,
"refresh_token" : "1/J-3zPA8XR1o_cXebV9sDKn_f5MTqaFhKFxH-3PUPiJ4"
}
访问令牌将在一小时后过期,因此您需要刷新它,这就是刷新令牌的用途。
刷新访问令牌
下面的调用也是HTTP POST
https://oauth2.googleapis.com/token
client_id={ClientId}&client_secret={ClientSecret}&refresh_token={Refresh token from previous call}&grant_type=refresh_token
工作示例
class Program
{
private const string Clientid = "Add yours";
private const string Secret = "Add yours.";
static async Task Main(string[] args)
{
Console.WriteLine("Hello World!");
Console.WriteLine($"open the following link in your browser window: {Helper.BuildConsentURL(Clientid, new []{ "profile" })}");
Console.WriteLine("Please paste the Authorization code here:");
var authorizationCode = Console.ReadLine();
var tokenResponse = await Helper.ExchangeAuthorizationCode(authorizationCode, Clientid, Secret);
var refreshTokenResponse = await Helper.ExchangeRefreshToken(tokenResponse.refresh_token, Clientid, Secret);
}
}
Helper.cs
public class Helper
{
/// <summary>
///
/// </summary>
/// <param name="clientId"></param>
/// <param name="scope">string array of scopes</param>
/// <param name="redirectUri">leave empty for installed application</param>
/// <returns></returns>
public static string BuildConsentURL(string clientId, string[] scope, string redirectUri = null)
{
if (string.IsNullOrEmpty(redirectUri))
{
redirectUri = "urn:ietf:wg:oauth:2.0:oob"; // for installed application
}
return
$"https://accounts.google.com/o/oauth2/auth?client_id={clientId}&redirect_uri={redirectUri}&scope={string.Join(" ", scope)}&response_type=code";
}
private static string BuildAuthorizationCodeRequest(string code, string clientId, string secret,
string redirectUri)
{
return
$"code={code}&client_id={clientId}&client_secret={secret}&redirect_uri={redirectUri}&grant_type=authorization_code";
}
private static string BuildRefreshAccessTokenRequest(string refreshToken, string clientId, string secret)
{
return
$"client_id={clientId}&client_secret={secret}&refresh_token={refreshToken}&grant_type=refresh_token";
}
private static async Task<AuthResponse> PostMessage(string postData)
{
AuthResponse result;
var client = new HttpClient();
client.BaseAddress = new Uri("https://accounts.google.com/");
var request = new HttpRequestMessage(HttpMethod.Post, "o/oauth2/token");
request.Content = new StringContent(postData, Encoding.UTF8, "application/x-www-form-urlencoded");
var response = await client.SendAsync(request);
using (var content = response.Content)
{
var json = content.ReadAsStringAsync().Result;
result = JsonSerializer.Deserialize<AuthResponse>(json);
}
return result;
}
public static async Task<AuthResponse> ExchangeAuthorizationCode(string code, string clientId, string secret,
string redirectUri = null)
{
var result = new AuthResponse();
if (string.IsNullOrEmpty(redirectUri))
{
redirectUri = "urn:ietf:wg:oauth:2.0:oob"; // for installed application
}
var postData = BuildAuthorizationCodeRequest(code, clientId, secret, redirectUri);
return await PostMessage(postData);
}
public static async Task<AuthResponse> ExchangeRefreshToken(string refreshToken, string clientId, string secret)
{
var postData = BuildRefreshAccessTokenRequest(refreshToken, clientId, secret);
return await PostMessage(postData);
}
}
authresonse.cs
public class AuthResponse
{
public string access_token { get; set; }
public string token_type { get; set; }
public int expires_in { get; set; }
public string refresh_token { get; set; }
}
试试这个。
String client_id = "<OAUTH_client_id >";
String client_secret = "<OAUTH_client_secret>";
var BaseAddress = "https://gateway-stage-core.optum.com";
var httpClient = new HttpClient() { BaseAddress = new Uri(BaseAddress) };
var creds = $"client_id={client_id}&client_secret={client_secret}&grant_type=client_credentials";
httpClient.DefaultRequestHeaders.Accept.Clear();
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/x-www-form-urlencoded"));
var content = new StringContent(creds, Encoding.UTF8, "application/x-www-form-urlencoded");
var response = httpClient.PostAsync("/auth/oauth2/cached/token", content).Result;
var jsonContent = response.Content.ReadAsStringAsync().Result;
var tokenObj = JsonConvert.DeserializeObject<BearerViewModel>(jsonContent);
var token = tokenObj.access_token;