sync full source from private myoffice
This commit is contained in:
@@ -0,0 +1,130 @@
|
||||
namespace MyOffice.Web.Auth;
|
||||
|
||||
using DbContext;
|
||||
using Infrastructure;
|
||||
using Microsoft.Extensions.Options;
|
||||
using OpenIddict.Abstractions;
|
||||
using static OpenIddict.Abstractions.OpenIddictConstants;
|
||||
|
||||
public sealed class OpenIddictSeeder : IHostedService
|
||||
{
|
||||
private readonly IServiceProvider _serviceProvider;
|
||||
private readonly IConfiguration _configuration;
|
||||
private readonly ILogger<OpenIddictSeeder> _logger;
|
||||
|
||||
public OpenIddictSeeder(
|
||||
IServiceProvider serviceProvider,
|
||||
IConfiguration configuration,
|
||||
ILogger<OpenIddictSeeder> logger
|
||||
)
|
||||
{
|
||||
_serviceProvider = serviceProvider;
|
||||
_configuration = configuration;
|
||||
_logger = logger;
|
||||
}
|
||||
|
||||
public async Task StartAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
await using var scope = _serviceProvider.CreateAsyncScope();
|
||||
|
||||
await RegisterScopesAsync(scope.ServiceProvider, cancellationToken);
|
||||
await RegisterClientAsync(scope.ServiceProvider, cancellationToken);
|
||||
}
|
||||
|
||||
public Task StopAsync(CancellationToken cancellationToken) => Task.CompletedTask;
|
||||
|
||||
private async Task RegisterScopesAsync(IServiceProvider provider, CancellationToken cancellationToken)
|
||||
{
|
||||
var manager = provider.GetRequiredService<IOpenIddictScopeManager>();
|
||||
|
||||
if (await manager.FindByNameAsync(OpenIddictAuthConstants.ApiScope, cancellationToken) is null)
|
||||
{
|
||||
await manager.CreateAsync(new OpenIddictScopeDescriptor
|
||||
{
|
||||
Name = OpenIddictAuthConstants.ApiScope,
|
||||
DisplayName = OpenIddictAuthConstants.ApiFriendlyName,
|
||||
Resources = { OpenIddictAuthConstants.ApiScope }
|
||||
}, cancellationToken);
|
||||
|
||||
_logger.LogInformation("Created OpenIddict scope {Scope}.", OpenIddictAuthConstants.ApiScope);
|
||||
}
|
||||
|
||||
if (await manager.FindByNameAsync(OpenIddictAuthConstants.RolesScope, cancellationToken) is null)
|
||||
{
|
||||
await manager.CreateAsync(new OpenIddictScopeDescriptor
|
||||
{
|
||||
Name = OpenIddictAuthConstants.RolesScope,
|
||||
DisplayName = "User roles"
|
||||
}, cancellationToken);
|
||||
|
||||
_logger.LogInformation("Created OpenIddict scope {Scope}.", OpenIddictAuthConstants.RolesScope);
|
||||
}
|
||||
}
|
||||
|
||||
private async Task RegisterClientAsync(IServiceProvider provider, CancellationToken cancellationToken)
|
||||
{
|
||||
var manager = provider.GetRequiredService<IOpenIddictApplicationManager>();
|
||||
var globalSettings = provider.GetRequiredService<GlobalSettings>();
|
||||
|
||||
var redirectUri = BuildRedirectUri(globalSettings.Host);
|
||||
var existing = await manager.FindByClientIdAsync(OpenIddictAuthConstants.SpaClientId, cancellationToken);
|
||||
var descriptor = CreateSpaClientDescriptor(redirectUri);
|
||||
|
||||
if (existing is null)
|
||||
{
|
||||
await manager.CreateAsync(descriptor, cancellationToken);
|
||||
_logger.LogInformation("Created OpenIddict client {ClientId}.", OpenIddictAuthConstants.SpaClientId);
|
||||
return;
|
||||
}
|
||||
|
||||
var currentRedirectUris = await manager.GetRedirectUrisAsync(existing, cancellationToken);
|
||||
foreach (var uri in currentRedirectUris)
|
||||
{
|
||||
if (!string.Equals(uri, redirectUri.ToString(), StringComparison.Ordinal))
|
||||
descriptor.RedirectUris.Add(new Uri(uri, UriKind.Absolute));
|
||||
}
|
||||
|
||||
await manager.UpdateAsync(existing, descriptor, cancellationToken);
|
||||
_logger.LogInformation("Updated OpenIddict client {ClientId}.", OpenIddictAuthConstants.SpaClientId);
|
||||
}
|
||||
|
||||
internal static OpenIddictApplicationDescriptor CreateSpaClientDescriptor(Uri redirectUri)
|
||||
{
|
||||
var descriptor = new OpenIddictApplicationDescriptor
|
||||
{
|
||||
ClientId = OpenIddictAuthConstants.SpaClientId,
|
||||
DisplayName = "MyOffice SPA",
|
||||
ClientType = ClientTypes.Public,
|
||||
ConsentType = ConsentTypes.Implicit,
|
||||
Permissions =
|
||||
{
|
||||
Permissions.Endpoints.Authorization,
|
||||
Permissions.Endpoints.Token,
|
||||
Permissions.Endpoints.EndSession,
|
||||
Permissions.GrantTypes.AuthorizationCode,
|
||||
Permissions.GrantTypes.Password,
|
||||
Permissions.GrantTypes.RefreshToken,
|
||||
Permissions.Prefixes.GrantType + OpenIddictAuthConstants.ExternalGrantType,
|
||||
Permissions.ResponseTypes.Code,
|
||||
Permissions.Scopes.Email,
|
||||
Permissions.Scopes.Profile,
|
||||
Permissions.Scopes.Roles,
|
||||
Permissions.Prefixes.Scope + Scopes.OpenId,
|
||||
Permissions.Prefixes.Scope + Scopes.OfflineAccess,
|
||||
Permissions.Prefixes.Scope + OpenIddictAuthConstants.ApiScope,
|
||||
Permissions.Prefixes.Scope + OpenIddictAuthConstants.RolesScope
|
||||
}
|
||||
};
|
||||
|
||||
descriptor.RedirectUris.Add(redirectUri);
|
||||
return descriptor;
|
||||
}
|
||||
|
||||
internal static Uri BuildRedirectUri(string? host)
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(host))
|
||||
return new Uri("http://localhost:4300/silent-refresh.html");
|
||||
|
||||
return new Uri($"{host.TrimEnd('/')}/silent-refresh.html");
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user