public async Task <ActionResult> OAuthAuthorizationCodeGrantClient(string code, string state) { try { OAuth2AndOIDCClient.HttpClient = new HttpClient(); string response = ""; if (state == this.State) // CSRF(XSRF)対策のstateの検証は重要 { response = await OAuth2AndOIDCClient.GetAccessTokenByCodeAsync( new Uri("http://localhost:63359/MultiPurposeAuthSite/OAuthBearerToken"), OAuth2AndOIDCParams.ClientID, OAuth2AndOIDCParams.ClientSecret, HttpUtility.HtmlEncode("http://localhost:63877/SPA_Sample/Home/OAuthAuthorizationCodeGrantClient"), code); // 汎用認証サイトはOIDCをサポートしたのでid_tokenを取得し、検証可能。 Base64UrlTextEncoder base64UrlEncoder = new Base64UrlTextEncoder(); Dictionary <string, string> dic = JsonConvert.DeserializeObject <Dictionary <string, string> >(response); // id_tokenの検証コード if (dic.ContainsKey("id_token")) { string id_token = dic["id_token"]; string sub = ""; List <string> roles = null; List <string> scopes = null; JObject jobj = null; if (JwtToken.Verify(id_token, out sub, out roles, out scopes, out jobj) && jobj["nonce"].ToString() == this.Nonce) { // ログインに成功 // /userinfoエンドポイントにアクセスする場合 response = await OAuth2AndOIDCClient.CallUserInfoEndpointAsync( new Uri("http://localhost:63359/MultiPurposeAuthSite/userinfo"), dic["access_token"]); FormsAuthentication.RedirectFromLoginPage(sub, false); MyUserInfo ui = new MyUserInfo(sub, Request.UserHostAddress); UserInfoHandle.SetUserInformation(ui); return(new EmptyResult()); } } else { } } else { } // ログインに失敗 return(RedirectToAction("Login")); } finally { this.ClearExLoginsParams(); } }
/// <summary>Page_Load</summary> /// <param name="sender">object</param> /// <param name="e">EventArgs</param> protected async void Page_Load(object sender, EventArgs e) { string code = Request.QueryString["code"]; string state = Request.QueryString["state"]; try { string response = ""; if (state == this.State) // CSRF(XSRF)対策のstateの検証は重要 { response = await OAuth2AndOIDCClient.GetAccessTokenByCodeAsync( new Uri("https://localhost:44300/MultiPurposeAuthSite/token"), OAuth2AndOIDCParams.ClientID, OAuth2AndOIDCParams.ClientSecret, HttpUtility.HtmlEncode("http://localhost:9999/WebForms_Sample/Aspx/Auth/OAuthAuthorizationCodeGrantClient.aspx"), code); // 汎用認証サイトはOIDCをサポートしたのでid_tokenを取得し、検証可能。 Base64UrlTextEncoder base64UrlEncoder = new Base64UrlTextEncoder(); Dictionary <string, string> dic = JsonConvert.DeserializeObject <Dictionary <string, string> >(response); string sub = ""; string nonce = ""; JObject jobj = null; // id_tokenの検証 if (IdToken.Verify(dic["id_token"], dic["access_token"], code, state, out sub, out nonce, out jobj) && nonce == this.Nonce) { // ログインに成功 // /userinfoエンドポイントにアクセスする場合 response = await OAuth2AndOIDCClient.GetUserInfoAsync( new Uri("https://localhost:44300/MultiPurposeAuthSite/userinfo"), dic["access_token"]); FormsAuthentication.RedirectFromLoginPage(sub, false); MyUserInfo ui = new MyUserInfo(sub, Request.UserHostAddress); UserInfoHandle.SetUserInformation(ui); return; } else { } } else { } // ResolveClientUrlがInvalidOperationExceptionを吐くので... //// ログインに失敗 //Response.Redirect("../Start/login.aspx"); } finally { this.ClearExLoginsParams(); } }
/// <summary>UserInfoエンドポイントで、認可ユーザのClaim情報を取得する。</summary> /// <param name="accessToken">accessToken</param> /// <returns>結果のJSON文字列(認可したユーザのClaim情報)</returns> public async Task <string> GetUserInfoAsync(string accessToken) { // 通信用の変数 // 認可したユーザのClaim情報を取得するWebAPI Uri userInfoUri = new Uri( ASPNETIdentityConfig.OAuth2ResourceServerEndpointsRootURI + ASPNETIdentityConfig.OAuth2GetUserClaimsWebAPI); return(await OAuth2AndOIDCClient.GetUserInfoAsync(userInfoUri, accessToken)); }
public ActionResult AuthorizationCode_PKCE_S256() { this.Init(); this.CodeVerifier = GetPassword.Base64UrlSecret(50); this.CodeChallenge = OAuth2AndOIDCClient.PKCE_S256_CodeChallengeMethod(this.CodeVerifier); this.Save(); // Authorization Code Flow (PKCE S256) return(Redirect(this.AssembleOAuth2Starter( OAuth2AndOIDCConst.AuthorizationCodeResponseType) + "&code_challenge=" + this.CodeChallenge + "&code_challenge_method=" + OAuth2AndOIDCConst.PKCE_S256)); }
/// <summary>外部ログイン</summary> /// <param name="userId">string</param> /// <param name="password">string</param> /// <returns>access_token</returns> private async Task <string> ExLogin(string userId, string password) { OAuth2AndOIDCClient.HttpClient = new HttpClient(); string response = await OAuth2AndOIDCClient.GetAccessTokenByROPAsync( new Uri("http://localhost:63359/MultiPurposeAuthSite/OAuthBearerToken"), OAuth2AndOIDCParams.ClientID, OAuth2AndOIDCParams.ClientSecret, userId, password, "profile email phone address roles").ConfigureAwait(false); // access_tokenを取得し、検証 Base64UrlTextEncoder base64UrlEncoder = new Base64UrlTextEncoder(); Dictionary <string, string> dic = JsonConvert.DeserializeObject <Dictionary <string, string> >(response); // access_tokenの検証コード if (dic.ContainsKey("access_token")) { string access_token = dic["access_token"]; string sub = ""; List <string> roles = null; List <string> scopes = null; JObject jobj = null; if (JwtToken.Verify(access_token, out sub, out roles, out scopes, out jobj)) { // ログインに成功 return(access_token); } else { // ログインに失敗 return(""); } } else { // ログインに失敗 return(""); } }
/// <summary>外部ログイン</summary> /// <param name="userId">string</param> /// <param name="password">string</param> /// <returns>access_token</returns> private async Task <string> ExLogin(string userId, string password) { OAuth2AndOIDCClient.HttpClient = new HttpClient(); string response = await OAuth2AndOIDCClient.ResourceOwnerPasswordCredentialsGrantAsync( new Uri("https://localhost:44300/MultiPurposeAuthSite/token"), OAuth2AndOIDCParams.ClientID, OAuth2AndOIDCParams.ClientSecret, userId, password, "profile email phone address roles").ConfigureAwait(false); // access_tokenを取得し、検証 Dictionary <string, string> dic = JsonConvert.DeserializeObject <Dictionary <string, string> >(response); // access_tokenの検証コード if (dic.ContainsKey("access_token")) { string access_token = dic["access_token"]; string sub = ""; List <string> roles = null; List <string> scopes = null; JObject jobj = null; if (AccessToken.Verify(access_token, out sub, out roles, out scopes, out jobj)) { // ログインに成功 return(access_token); } else { // ログインに失敗 return(""); } } else { // ログインに失敗 return(""); } }
/// <summary> /// Token2エンドポイントで、 /// JWT bearer token authorizationグラント種別の要求を行う。</summary> /// <param name="token2EndpointUri">Token2エンドポイントのUri</param> /// <param name="assertion">string</param> /// <returns>結果のJSON文字列</returns> public async Task <string> JwtBearerTokenFlowAsync(Uri token2EndpointUri, string assertion) { return(await OAuth2AndOIDCClient.JwtBearerTokenFlowAsync(token2EndpointUri, assertion)); }
/// <summary>Introspectエンドポイントで、Tokenを無効化する。</summary> /// <param name="introspectTokenEndpointUri">IntrospectエンドポイントのUri</param> /// <param name="client_id">client_id</param> /// <param name="client_secret">client_secret</param> /// <param name="token">token</param> /// <param name="token_type_hint">token_type_hint</param> /// <returns>結果のJSON文字列</returns> public async Task <string> IntrospectTokenAsync( Uri introspectTokenEndpointUri, string client_id, string client_secret, string token, string token_type_hint) { return(await OAuth2AndOIDCClient.IntrospectTokenAsync( introspectTokenEndpointUri, client_id, client_secret, token, token_type_hint)); }
/// <summary>Revokeエンドポイントで、Tokenを無効化する。</summary> /// <param name="revokeTokenEndpointUri">RevokeエンドポイントのUri</param> /// <param name="client_id">client_id</param> /// <param name="client_secret">client_secret</param> /// <param name="token">token</param> /// <param name="token_type_hint">token_type_hint</param> /// <returns>結果のJSON文字列</returns> public async Task <string> RevokeTokenAsync( Uri revokeTokenEndpointUri, string client_id, string client_secret, string token, string token_type_hint) { return(await OAuth2AndOIDCClient.RevokeTokenAsync( revokeTokenEndpointUri, client_id, client_secret, token, token_type_hint)); }
/// <summary>Refresh Tokenを使用してAccess Tokenを更新する。</summary> /// <param name="tokenEndpointUri">tokenEndpointUri</param> /// <param name="client_id">client_id</param> /// <param name="client_secret">client_secret</param> /// <param name="refreshToken">refreshToken</param> /// <returns>結果のJSON文字列</returns> public async Task <string> UpdateAccessTokenByRefreshTokenAsync( Uri tokenEndpointUri, string client_id, string client_secret, string refreshToken) { return(await OAuth2AndOIDCClient.UpdateAccessTokenByRefreshTokenAsync( tokenEndpointUri, client_id, client_secret, refreshToken)); }
/// <summary> /// Client Credentials Grant /// </summary> /// <param name="tokenEndpointUri">TokenエンドポイントのUri</param> /// <param name="client_id">string</param> /// <param name="client_secret">string</param> /// <param name="scopes">string</param> /// <returns>結果のJSON文字列</returns> public async Task <string> ClientCredentialsGrantAsync( Uri tokenEndpointUri, string client_id, string client_secret, string scopes) { return(await OAuth2AndOIDCClient.ClientCredentialsGrantAsync( tokenEndpointUri, client_id, client_secret, scopes)); }
/// <summary> /// FAPI1 : code, code_verifierからAccess Tokenを取得する。 /// </summary> /// <param name="tokenEndpointUri">TokenエンドポイントのUri</param> /// <param name="redirect_uri">redirect_uri</param> /// <param name="code">code</param> /// <param name="assertion">assertion</param> /// <returns>結果のJSON文字列</returns> public async Task <string> GetAccessTokenByCodeAsync( Uri tokenEndpointUri, string redirect_uri, string code, string assertion) { return(await OAuth2AndOIDCClient.GetAccessTokenByCodeAsync( tokenEndpointUri, redirect_uri, code, assertion)); }
/// <summary> /// PKCE : code, code_verifierからAccess Tokenを取得する。 /// </summary> /// <param name="tokenEndpointUri">TokenエンドポイントのUri</param> /// <param name="client_id">client_id</param> /// <param name="client_secret">client_secret</param> /// <param name="redirect_uri">redirect_uri</param> /// <param name="code">code</param> /// <param name="code_verifier">code_verifier</param> /// <returns>結果のJSON文字列</returns> public async Task <string> GetAccessTokenByCodeAsync( Uri tokenEndpointUri, string client_id, string client_secret, string redirect_uri, string code, string code_verifier) { return(await OAuth2AndOIDCClient.GetAccessTokenByCodeAsync( tokenEndpointUri, client_id, client_secret, redirect_uri, code, code_verifier)); }
public async Task <ActionResult> OAuth2AuthorizationCodeGrantClient(string code, string state) { try { string response = ""; if (state == this.State) // CSRF(XSRF)対策のstateの検証は重要 { response = await OAuth2AndOIDCClient.GetAccessTokenByCodeAsync( new Uri("https://localhost:44300/MultiPurposeAuthSite/token"), OAuth2AndOIDCParams.ClientID, OAuth2AndOIDCParams.ClientSecret, HttpUtility.HtmlEncode("http://localhost:58496/Home/OAuth2AuthorizationCodeGrantClient"), code); // 汎用認証サイトはOIDCをサポートしたのでid_tokenを取得し、検証可能。 //Base64UrlTextEncoder base64UrlEncoder = new Base64UrlTextEncoder(); Dictionary <string, string> dic = JsonConvert.DeserializeObject <Dictionary <string, string> >(response); // id_tokenの検証コード if (dic.ContainsKey("id_token")) { string sub = ""; string nonce = ""; JObject jobj = null; if (IdToken.Verify(dic["id_token"], dic["access_token"], code, state, out sub, out nonce, out jobj) && nonce == this.Nonce) { // ログインに成功 // /userinfoエンドポイントにアクセスする場合 response = await OAuth2AndOIDCClient.GetUserInfoAsync( new Uri("https://localhost:44300/MultiPurposeAuthSite/userinfo"), dic["access_token"]); // 認証情報を作成する。 List <Claim> claims = new List <Claim>(); claims.Add(new Claim(ClaimTypes.Name, sub)); // 認証情報を保存する。 ClaimsIdentity userIdentity = new ClaimsIdentity(claims, CookieAuthenticationDefaults.AuthenticationScheme); ClaimsPrincipal userPrincipal = new ClaimsPrincipal(userIdentity); // サイン アップする。 await AuthenticationHttpContextExtensions.SignInAsync( this.HttpContext, CookieAuthenticationDefaults.AuthenticationScheme, userPrincipal); // 認証情報を保存する。 MyUserInfo ui = new MyUserInfo(sub, (new GetClientIpAddress()).GetAddress()); UserInfoHandle.SetUserInformation(ui); return(this.Redirect(Url.Action("Index", "Home"))); } } else { } } else { } // ログインに失敗 return(RedirectToAction("Login")); } finally { this.ClearExLoginsParams(); } }
/// <summary>VerifyCodeVerifier</summary> /// <param name="value">string</param> /// <param name="code_verifier">string</param> /// <returns>ticket</returns> private string VerifyCodeVerifier(string value, string code_verifier) { // null チェック if (string.IsNullOrEmpty(value)) { return(""); } Dictionary <string, string> temp = JsonConvert.DeserializeObject <Dictionary <string, string> >(value); bool isPKCE = (code_verifier != null); if (!isPKCE) { // 通常のアクセストークン・リクエスト if (string.IsNullOrEmpty(temp[OAuth2AndOIDCConst.code_challenge])) { // Authorization Codeのcode return(temp["ticket"]); } else { // OAuth PKCEのcode(要 code_verifier) return(""); } } else { // OAuth PKCEのアクセストークン・リクエスト if (!string.IsNullOrEmpty(temp[OAuth2AndOIDCConst.code_challenge]) && !string.IsNullOrEmpty(code_verifier)) { if (temp[OAuth2AndOIDCConst.code_challenge_method].ToLower() == OAuth2AndOIDCConst.PKCE_plain) { // plain if (temp[OAuth2AndOIDCConst.code_challenge] == code_verifier) { // 検証成功 return(temp["ticket"]); } else { // 検証失敗 } } else if (temp[OAuth2AndOIDCConst.code_challenge_method].ToUpper() == OAuth2AndOIDCConst.PKCE_S256) { // S256 if (temp[OAuth2AndOIDCConst.code_challenge] == OAuth2AndOIDCClient.PKCE_S256_CodeChallengeMethod(code_verifier)) { // 検証成功 return(temp["ticket"]); } else { // 検証失敗 } } else { // パラメタ不正 } } else { // パラメタ不正 } return(null); } }