simplify configuration of external login providers

This commit is contained in:
sbwalker 2024-09-27 16:21:06 -04:00
parent b98535810b
commit be0754f568
4 changed files with 223 additions and 108 deletions

View File

@ -182,11 +182,29 @@ else
</div>
</Section>
<Section Name="ExternalLogin" Heading="External Login Settings" ResourceKey="ExternalLoginSettings">
<div class="row mb-1 align-items-center">
<Label Class="col-sm-3" For="provider" HelpText="Select the external login provider" ResourceKey="Provider">Provider:</Label>
<div class="col-sm-9">
<div class="input-group">
<select id="provider" class="form-select" value="@_provider" @onchange="(e => ProviderChanged(e))">
@foreach (var provider in Shared.ExternalLoginProviders.Providers)
{
<option value="@provider.Name">@Localizer[provider.Name]</option>
}
</select>
@if (!string.IsNullOrEmpty(_providerurl))
{
<a href="@_providerurl" class="btn btn-secondary" target="_new">@Localizer["Info"]</a>
}
</div>
</div>
</div>
<div class="row mb-1 align-items-center">
<Label Class="col-sm-3" For="providertype" HelpText="Select the external login provider type" ResourceKey="ProviderType">Provider Type:</Label>
<div class="col-sm-9">
<select id="providertype" class="form-select" value="@_providertype" @onchange="(e => ProviderTypeChanged(e))">
<option value="" selected>@Localizer["Not Specified"]</option>
<option value="" selected>&lt;@Localizer["Not Specified"]&gt;</option>
<option value="@AuthenticationProviderTypes.OpenIDConnect">@Localizer["OpenID Connect"]</option>
<option value="@AuthenticationProviderTypes.OAuth2">@Localizer["OAuth 2.0"]</option>
</select>
@ -452,6 +470,8 @@ else
private string _maximumfailures;
private string _lockoutduration;
private string _provider;
private string _providerurl;
private string _providertype;
private string _providername;
private string _authority;
@ -519,6 +539,20 @@ else
_maximumfailures = SettingService.GetSetting(settings, "IdentityOptions:Lockout:MaxFailedAccessAttempts", "5");
_lockoutduration = TimeSpan.Parse(SettingService.GetSetting(settings, "IdentityOptions:Lockout:DefaultLockoutTimeSpan", "00:05:00")).TotalMinutes.ToString();
LoadExternalLoginSettings(settings);
_secret = SettingService.GetSetting(settings, "JwtOptions:Secret", "");
_togglesecret = SharedLocalizer["ShowPassword"];
_issuer = SettingService.GetSetting(settings, "JwtOptions:Issuer", PageState.Uri.Scheme + "://" + PageState.Alias.Name);
_audience = SettingService.GetSetting(settings, "JwtOptions:Audience", "");
_lifetime = SettingService.GetSetting(settings, "JwtOptions:Lifetime", "20");
}
}
private void LoadExternalLoginSettings(Dictionary<string, string> settings)
{
_provider = SettingService.GetSetting(settings, "ExternalLogin:Provider", "Custom");
_providerurl = SettingService.GetSetting(settings, "ExternalLogin:ProviderUrl", "");
_providertype = SettingService.GetSetting(settings, "ExternalLogin:ProviderType", "");
_providername = SettingService.GetSetting(settings, "ExternalLogin:ProviderName", "");
_authority = SettingService.GetSetting(settings, "ExternalLogin:Authority", "");
@ -546,13 +580,6 @@ else
_domainfilter = SettingService.GetSetting(settings, "ExternalLogin:DomainFilter", "");
_createusers = SettingService.GetSetting(settings, "ExternalLogin:CreateUsers", "true");
_verifyusers = SettingService.GetSetting(settings, "ExternalLogin:VerifyUsers", "true");
_secret = SettingService.GetSetting(settings, "JwtOptions:Secret", "");
_togglesecret = SharedLocalizer["ShowPassword"];
_issuer = SettingService.GetSetting(settings, "JwtOptions:Issuer", PageState.Uri.Scheme + "://" + PageState.Alias.Name);
_audience = SettingService.GetSetting(settings, "JwtOptions:Audience", "");
_lifetime = SettingService.GetSetting(settings, "JwtOptions:Lifetime", "20");
}
}
private async Task LoadUsersAsync(bool load)
@ -617,6 +644,7 @@ else
settings = SettingService.SetSetting(settings, "IdentityOptions:Lockout:MaxFailedAccessAttempts", _maximumfailures, true);
settings = SettingService.SetSetting(settings, "IdentityOptions:Lockout:DefaultLockoutTimeSpan", TimeSpan.FromMinutes(Convert.ToInt64(_lockoutduration)).ToString(), true);
settings = SettingService.SetSetting(settings, "ExternalLogin:Provider", _provider, false);
settings = SettingService.SetSetting(settings, "ExternalLogin:ProviderType", _providertype, false);
settings = SettingService.SetSetting(settings, "ExternalLogin:ProviderName", _providername, false);
settings = SettingService.SetSetting(settings, "ExternalLogin:Authority", _authority, true);
@ -665,6 +693,17 @@ else
}
}
private void ProviderChanged(ChangeEventArgs e)
{
_provider = (string)e.Value;
var provider = Shared.ExternalLoginProviders.Providers.FirstOrDefault(item => item.Name == _provider);
if (provider != null)
{
LoadExternalLoginSettings(provider.Settings);
}
StateHasChanged();
}
private void ProviderTypeChanged(ChangeEventArgs e)
{
_providertype = (string)e.Value;

View File

@ -480,4 +480,13 @@
<data name="NameClaimType.Text" xml:space="preserve">
<value>Name Claim:</value>
</data>
<data name="Provider.HelpText" xml:space="preserve">
<value>Select the external login provider</value>
</data>
<data name="Provider.Text" xml:space="preserve">
<value>Provider:</value>
</data>
<data name="Info" xml:space="preserve">
<value>Info</value>
</data>
</root>

View File

@ -0,0 +1,11 @@
using System.Collections.Generic;
namespace Oqtane.Models
{
public class ExternalLoginProvider
{
public string Name { get; set; }
public Dictionary<string, string> Settings { get; set; }
}
}

View File

@ -0,0 +1,56 @@
using System.Collections.Generic;
using Oqtane.Models;
namespace Oqtane.Shared
{
public class ExternalLoginProviders
{
public static List<ExternalLoginProvider> Providers
{
get
{
var providers = new List<ExternalLoginProvider>
{
new ExternalLoginProvider
{
Name = "Custom",
Settings = new Dictionary<string, string>()
},
new ExternalLoginProvider
{
Name = "Microsoft Entra",
Settings = new Dictionary<string, string>()
{
{ "ExternalLogin:ProviderUrl", "https://entra.microsoft.com" },
{ "ExternalLogin:ProviderType", "oidc" },
{ "ExternalLogin:ProviderName", "Microsoft Entra" },
{ "ExternalLogin:Authority", "https://login.microsoftonline.com/YOUR_TENANT_ID/v2.0" },
{ "ExternalLogin:ClientId", "YOUR CLIENT ID" },
{ "ExternalLogin:ClientSecret", "YOUR CLIENT SECRET" }
}
},
new ExternalLoginProvider
{
Name = "GitHub",
Settings = new Dictionary<string, string>()
{
{ "ExternalLogin:ProviderUrl", "https://github.com/settings/developers#oauth-apps" },
{ "ExternalLogin:ProviderType", "oauth2" },
{ "ExternalLogin:ProviderName", "GitHub" },
{ "ExternalLogin:AuthorizationUrl", "https://github.com/login/oauth/authorize" },
{ "ExternalLogin:TokenUrl", "https://github.com/login/oauth/access_token" },
{ "ExternalLogin:UserInfoUrl", "https://api.github.com/user/emails" },
{ "ExternalLogin:ClientId", "YOUR CLIENT ID" },
{ "ExternalLogin:ClientSecret", "YOUR CLIENT SECRET" },
{ "ExternalLogin:Scopes", "user:email" },
{ "ExternalLogin:IdentifierClaimType", "email" },
{ "ExternalLogin:DomainFilter", "!users.noreply.github.com" }
}
}
};
return providers;
}
}
}
}