-
Notifications
You must be signed in to change notification settings - Fork 426
/
AuthenticationExtensions.cs
108 lines (90 loc) · 4.63 KB
/
AuthenticationExtensions.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
using Auth0.AspNetCore.Authentication;
using Microsoft.AspNetCore.Authentication;
using Microsoft.AspNetCore.Authentication.Cookies;
using Microsoft.AspNetCore.Authentication.OpenIdConnect;
using Microsoft.AspNetCore.Components.Authorization;
namespace Todo.Web.Server;
public static class AuthenticationExtensions
{
private delegate void ExternalAuthProvider(AuthenticationBuilder authenticationBuilder, Action<object> configure);
public static WebApplicationBuilder AddAuthentication(this WebApplicationBuilder builder)
{
// Our default scheme is cookies
var authenticationBuilder = builder.Services.AddAuthentication(CookieAuthenticationDefaults.AuthenticationScheme);
// Add the default authentication cookie that will be used between the front end and
// the backend.
authenticationBuilder.AddCookie();
// This is the cookie that will store the user information from the external login provider
authenticationBuilder.AddCookie(AuthenticationSchemes.ExternalScheme);
// Add external auth providers based on configuration
//{
// "Authentication": {
// "Schemes": {
// "<scheme>": {
// "ClientId": "xxx",
// "ClientSecret": "xxxx"
// etc..
// }
// }
// }
//}
// These are the list of external providers available to the application.
// Many more are available from https://github.com/aspnet-contrib/AspNet.Security.OAuth.Providers
var externalProviders = new Dictionary<string, ExternalAuthProvider>
{
["GitHub"] = static (builder, configure) => builder.AddGitHub(configure),
["Google"] = static (builder, configure) => builder.AddGoogle(configure),
["Microsoft"] = static (builder, configure) => builder.AddMicrosoftAccount(configure),
["Auth0"] = static (builder, configure) => builder.AddAuth0WebAppAuthentication(configure)
.WithAccessToken(configure),
};
foreach (var (providerName, provider) in externalProviders)
{
var section = builder.Configuration.GetSection($"Authentication:Schemes:{providerName}");
if (section.Exists())
{
provider(authenticationBuilder, options =>
{
// Bind this section to the specified options
section.Bind(options);
// This will save the information in the external cookie
if (options is RemoteAuthenticationOptions remoteAuthenticationOptions)
{
remoteAuthenticationOptions.SignInScheme = AuthenticationSchemes.ExternalScheme;
}
else if (options is Auth0WebAppOptions auth0WebAppOptions)
{
// Skip the cookie handler since we already add it
auth0WebAppOptions.SkipCookieMiddleware = true;
}
});
if (providerName is "Auth0")
{
// Set this up once
SetAuth0SignInScheme(builder);
}
}
}
// Add the service that resolves external providers so we can show them in the UI
builder.Services.AddSingleton<ExternalProviders>();
// Blazor auth services
builder.Services.AddSingleton<AuthenticationStateProvider, HttpAuthenticationStateProvider>();
builder.Services.AddHttpContextAccessor();
return builder;
static void SetAuth0SignInScheme(WebApplicationBuilder builder)
{
builder.Services.AddOptions<OpenIdConnectOptions>(Auth0Constants.AuthenticationScheme)
.PostConfigure(o =>
{
// The Auth0 APIs don't let you set the sign in scheme, it defaults to the default sign in scheme.
// Use named options to configure the underlying OpenIdConnectOptions's sign in scheme instead.
o.SignInScheme = AuthenticationSchemes.ExternalScheme;
});
}
}
private static readonly string ExternalProviderKey = "ExternalProviderName";
public static string? GetExternalProvider(this AuthenticationProperties properties) =>
properties.GetString(ExternalProviderKey);
public static void SetExternalProvider(this AuthenticationProperties properties, string providerName) =>
properties.SetString(ExternalProviderKey, providerName);
}