Untitled
unknown
plain_text
2 years ago
14 kB
3
Indexable
using System; using System.Configuration; using System.Linq; using System.Net.Http; using System.Security.Claims; using System.Security.Cryptography; using System.Text; using System.Threading.Tasks; using System.Web; using System.Web.Helpers; using Abp.Extensions; using Abp.Owin; using Hangfire; using IdentityModel; using IdentityModel.Client; using Microsoft.AspNet.Identity; using Microsoft.IdentityModel.Protocols.OpenIdConnect; using Microsoft.Owin; using Microsoft.Owin.Security; using Microsoft.Owin.Security.Cookies; using Microsoft.Owin.Security.Facebook; using Microsoft.Owin.Security.Google; using Microsoft.Owin.Security.Notifications; using Microsoft.Owin.Security.OpenIdConnect; using Microsoft.Owin.Security.Twitter; using Nascence.BodynitsPortal.Web; using Nascence.BodynitsPortal.WebApi.Controllers; using NLog; using Owin; [assembly: OwinStartup(typeof(Startup))] namespace Nascence.BodynitsPortal.Web { public class Startup { private static Logger _logger = LogManager.GetCurrentClassLogger(); public void Configuration(IAppBuilder app) { app.UseAbp(); app.UseOAuthBearerAuthentication(AccountController.OAuthBearerOptions); app.UseKentorOwinCookieSaver(); app.UseCookieAuthentication(new CookieAuthenticationOptions { AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie, LoginPath = new PathString("/Account/Login") }); //app.UseExternalSignInCookie(DefaultAuthenticationTypes.ExternalCookie); //if (IsTrue("ExternalAuth.Facebook.IsEnabled")) //{ // app.UseFacebookAuthentication(CreateFacebookAuthOptions()); //} //if (IsTrue("ExternalAuth.Twitter.IsEnabled")) //{ // app.UseTwitterAuthentication(CreateTwitterAuthOptions()); //} //if (IsTrue("ExternalAuth.Google.IsEnabled")) //{ // app.UseGoogleAuthentication(CreateGoogleAuthOptions()); //} app.UseExternalSignInCookie(DefaultAuthenticationTypes.ExternalCookie); if (IsTrue("ExternalAuth.OpenId.IsEnabled")) { app.UseOpenIdConnectAuthentication(CreateOpenIdOptions()); } app.MapSignalR(); //Enable it to use HangFire dashboard (uncomment only if it's enabled in BodynitsPortalWebModule) //app.UseHangfireDashboard(); } private static OpenIdConnectAuthenticationOptions CreateOpenIdOptions() { AntiForgeryConfig.UniqueClaimTypeIdentifier = ClaimTypes.NameIdentifier; var options = new OpenIdConnectAuthenticationOptions { Authority = AppHelper.IdentityHelper.OpenIdAuthority, ClientId = AppHelper.IdentityHelper.OpenIdClientId, PostLogoutRedirectUri = AppHelper.IdentityHelper.OpenIdPostLogoutRedirectUri, RedirectUri = AppHelper.IdentityHelper.OpenIdRedirectUri, RequireHttpsMetadata = false, SignInAsAuthenticationType = DefaultAuthenticationTypes.ApplicationCookie, UseTokenLifetime = false, Notifications = new OpenIdConnectAuthenticationNotifications { RedirectToIdentityProvider = (n) => { // if signing out, add the id_token_hint if (n.ProtocolMessage.RequestType == OpenIdConnectRequestType.Logout) { var idTokenHint = n.OwinContext.Authentication.User.FindFirst("id_token"); if (idTokenHint != null) { n.ProtocolMessage.IdTokenHint = idTokenHint.Value; } } else if (n.ProtocolMessage.RequestType == OpenIdConnectRequestType.Authentication) { var tenancyName = "DEF"; if (tenancyName != null) { //n.ProtocolMessage.Parameters.Add("tenancy_name", tenancyName.Last()); n.ProtocolMessage.Parameters.Add("tenancy_name", tenancyName); HttpCookie tenancyNameCookie = new HttpCookie("tenancyNameCookie"); //tenancyNameCookie["tenancy_name"] = tenancyName.Last(); tenancyNameCookie["tenancy_name"] = tenancyName; var response = HttpContext.Current.Response; response.Cookies.Add(tenancyNameCookie); } // set PKCE parameters var codeVerifier = CryptoRandom.CreateUniqueId(32); string codeChallenge; using (var sha256 = SHA256.Create()) { var challengeBytes = sha256.ComputeHash(Encoding.UTF8.GetBytes(codeVerifier)); codeChallenge = Base64Url.Encode(challengeBytes); } n.ProtocolMessage.SetParameter("code_challenge", codeChallenge); n.ProtocolMessage.SetParameter("code_challenge_method", "S256"); // remember code_verifier (adapted from OWIN nonce cookie) RememberCodeVerifier(n, codeVerifier); } return Task.FromResult(0); }, AuthenticationFailed = (n) => { try { _logger.Info("Authentication Failed"); _logger.Info(n.Exception); _logger.Info(n.Response?.StatusCode); _logger.Info(n.Response?.ReasonPhrase); n.HandleResponse(); n.Response.Redirect("/Application/Index"); return Task.FromResult(0); } catch (Exception ex) { throw ex; }; }, AuthorizationCodeReceived = async n => { var client = new HttpClient(); // get code_verifier var codeVerifier = RetrieveCodeVerifier(n); // attach code_verifier n.TokenEndpointRequest.SetParameter("code_verifier", codeVerifier); var tokenResponse = await client.RequestAuthorizationCodeTokenAsync(new AuthorizationCodeTokenRequest() { Address = AppHelper.IdentityHelper.OpenIdTokenEndpoint, ClientId = AppHelper.IdentityHelper.OpenIdClientId, ClientSecret = AppHelper.IdentityHelper.OpenIdClientSecret, Code = n.Code, RedirectUri = n.RedirectUri, CodeVerifier = codeVerifier, }); if (tokenResponse.IsError) { throw new Exception(tokenResponse.Error); } var userInfoResponse = await client.GetUserInfoAsync(new UserInfoRequest() { Address = AppHelper.IdentityHelper.OpenIdUserInfoEndpoint, Token = tokenResponse.AccessToken, }); // create new identity var id = new ClaimsIdentity(n.AuthenticationTicket.Identity.AuthenticationType); id.AddClaims(userInfoResponse.Claims); id.AddClaim(new Claim("access_token", tokenResponse.AccessToken)); id.AddClaim(new Claim("expires_at", DateTime.Now.AddSeconds(tokenResponse.ExpiresIn).ToLocalTime().ToString())); id.AddClaim(new Claim("iss", n.AuthenticationTicket.Identity.FindFirst("iss").Value)); id.AddClaim(new Claim("id_token", n.ProtocolMessage.IdToken)); id.AddClaim(new Claim("sid", n.AuthenticationTicket.Identity.FindFirst("sid").Value)); id.AddClaim(new Claim(ClaimTypes.NameIdentifier, userInfoResponse.Claims.FirstOrDefault(x => x.Type == "preferred_username").Value)); n.AuthenticationTicket = new AuthenticationTicket( new ClaimsIdentity(id.Claims, n.AuthenticationTicket.Identity.AuthenticationType, ClaimTypes.NameIdentifier, "role"), n.AuthenticationTicket.Properties); } } }; var clientSecret = ConfigurationManager.AppSettings["ExternalAuth.OpenId.ClientSecret"]; if (!clientSecret.IsNullOrEmpty()) { options.ClientSecret = clientSecret; } return options; } private static void RememberCodeVerifier(RedirectToIdentityProviderNotification<OpenIdConnectMessage, OpenIdConnectAuthenticationOptions> n, string codeVerifier) { var properties = new AuthenticationProperties(); properties.Dictionary.Add("cv", codeVerifier); n.Options.CookieManager.AppendResponseCookie( n.OwinContext, GetCodeVerifierKey(n.ProtocolMessage.State), Convert.ToBase64String(Encoding.UTF8.GetBytes(n.Options.StateDataFormat.Protect(properties))), new CookieOptions { SameSite = SameSiteMode.None, HttpOnly = true, Secure = n.Request.IsSecure, Expires = DateTime.UtcNow + n.Options.ProtocolValidator.NonceLifetime }); } private static string RetrieveCodeVerifier(AuthorizationCodeReceivedNotification n) { string key = GetCodeVerifierKey(n.ProtocolMessage.State); string codeVerifierCookie = n.Options.CookieManager.GetRequestCookie(n.OwinContext, key); if (codeVerifierCookie != null) { var cookieOptions = new CookieOptions { SameSite = SameSiteMode.None, HttpOnly = true, Secure = n.Request.IsSecure }; n.Options.CookieManager.DeleteCookie(n.OwinContext, "cv", cookieOptions); } var cookieProperties = n.Options.StateDataFormat.Unprotect(Encoding.UTF8.GetString(Convert.FromBase64String(codeVerifierCookie))); cookieProperties.Dictionary.TryGetValue("cv", out var codeVerifier); return codeVerifier; } private static string GetCodeVerifierKey(string state) { using (var hash = SHA256.Create()) { return OpenIdConnectAuthenticationDefaults.CookiePrefix + "cv." + Convert.ToBase64String(hash.ComputeHash(Encoding.UTF8.GetBytes(state))); } } private static FacebookAuthenticationOptions CreateFacebookAuthOptions() { var options = new FacebookAuthenticationOptions { AppId = ConfigurationManager.AppSettings["ExternalAuth.Facebook.AppId"], AppSecret = ConfigurationManager.AppSettings["ExternalAuth.Facebook.AppSecret"] }; options.Scope.Add("email"); options.Scope.Add("public_profile"); return options; } private static TwitterAuthenticationOptions CreateTwitterAuthOptions() { return new TwitterAuthenticationOptions { ConsumerKey = ConfigurationManager.AppSettings["ExternalAuth.Twitter.ConsumerKey"], ConsumerSecret = ConfigurationManager.AppSettings["ExternalAuth.Twitter.ConsumerSecret"] }; } private static GoogleOAuth2AuthenticationOptions CreateGoogleAuthOptions() { return new GoogleOAuth2AuthenticationOptions { ClientId = ConfigurationManager.AppSettings["ExternalAuth.Google.ClientId"], ClientSecret = ConfigurationManager.AppSettings["ExternalAuth.Google.ClientSecret"] }; } private static bool IsTrue(string appSettingName) { return string.Equals( ConfigurationManager.AppSettings[appSettingName], "true", StringComparison.InvariantCultureIgnoreCase); } } }
Editor is loading...