tgstation-server 6.9.2
The /tg/station 13 server suite
Loading...
Searching...
No Matches
AuthenticationContextFactory.cs
Go to the documentation of this file.
1using System;
2using System.Linq;
3using System.Threading;
4using System.Threading.Tasks;
5
6using Microsoft.EntityFrameworkCore;
7using Microsoft.Extensions.Logging;
8using Microsoft.Extensions.Options;
9
13
15{
18 {
23
28
33
37 readonly ILogger<AuthenticationContextFactory> logger;
38
43
48
53
64 IOptions<SwarmConfiguration> swarmConfigurationOptions,
65 ILogger<AuthenticationContextFactory> logger)
66 {
67 this.databaseContext = databaseContext ?? throw new ArgumentNullException(nameof(databaseContext));
68 this.identityCache = identityCache ?? throw new ArgumentNullException(nameof(identityCache));
69 swarmConfiguration = swarmConfigurationOptions?.Value ?? throw new ArgumentNullException(nameof(swarmConfigurationOptions));
70 this.logger = logger ?? throw new ArgumentNullException(nameof(logger));
71
73 }
74
77
79 public async ValueTask<IAuthenticationContext> CreateAuthenticationContext(long userId, long? instanceId, DateTimeOffset notBefore, CancellationToken cancellationToken)
80 {
81 if (Interlocked.Exchange(ref initialized, 1) != 0)
82 throw new InvalidOperationException("Authentication context has already been loaded");
83
84 var user = await databaseContext
85 .Users
86 .AsQueryable()
87 .Where(x => x.Id == userId)
88 .Include(x => x.CreatedBy)
89 .Include(x => x.PermissionSet)
90 .Include(x => x.Group)
91 .ThenInclude(x => x!.PermissionSet)
92 .Include(x => x.OAuthConnections)
93 .FirstOrDefaultAsync(cancellationToken);
94 if (user == default)
95 {
96 logger.LogWarning("Unable to find user with ID {userId}!", userId);
98 }
99
100 ISystemIdentity? systemIdentity;
101 if (user.SystemIdentifier != null)
102 systemIdentity = identityCache.LoadCachedIdentity(user);
103 else
104 {
105 if (user.LastPasswordUpdate.HasValue && user.LastPasswordUpdate >= notBefore)
106 {
107 logger.LogDebug("Rejecting token for user {userId} created before last password update: {lastPasswordUpdate}", userId, user.LastPasswordUpdate.Value);
109 }
110
111 systemIdentity = null;
112 }
113
114 var userPermissionSet = user.PermissionSet ?? user.Group!.PermissionSet;
115 try
116 {
117 InstancePermissionSet? instancePermissionSet = null;
118 if (instanceId.HasValue)
119 {
120 instancePermissionSet = await databaseContext.InstancePermissionSets
121 .AsQueryable()
122 .Where(x => x.PermissionSetId == userPermissionSet!.Id && x.InstanceId == instanceId && x.Instance!.SwarmIdentifer == swarmConfiguration.Identifier)
123 .Include(x => x.Instance)
124 .FirstOrDefaultAsync(cancellationToken);
125
126 if (instancePermissionSet == null)
127 logger.LogDebug("User {userId} does not have permissions on instance {instanceId}!", userId, instanceId.Value);
128 }
129
131 systemIdentity,
132 user,
133 instancePermissionSet);
135 }
136 catch
137 {
138 systemIdentity?.Dispose();
139 throw;
140 }
141 }
142 }
143}
string? Identifier
The server's identifier.
Configuration for the server swarm system.
IAuthenticationContext CurrentAuthenticationContext
The IAuthenticationContext the AuthenticationContextFactory created.
readonly IDatabaseContext databaseContext
The IDatabaseContext for the AuthenticationContextFactory.
AuthenticationContextFactory(IDatabaseContext databaseContext, IIdentityCache identityCache, IOptions< SwarmConfiguration > swarmConfigurationOptions, ILogger< AuthenticationContextFactory > logger)
Initializes a new instance of the AuthenticationContextFactory class.
async ValueTask< IAuthenticationContext > CreateAuthenticationContext(long userId, long? instanceId, DateTimeOffset notBefore, CancellationToken cancellationToken)
Create an IAuthenticationContext in the request pipeline for a given userId and instanceId ....
readonly ILogger< AuthenticationContextFactory > logger
The ILogger for the AuthenticationContextFactory.
int initialized
1 if currentAuthenticationContext was initialized, 0 otherwise.
readonly SwarmConfiguration swarmConfiguration
The SwarmConfiguration for the AuthenticationContextFactory.
readonly IIdentityCache identityCache
The IIdentityCache for the AuthenticationContextFactory.
readonly AuthenticationContext currentAuthenticationContext
Backing field for CurrentAuthenticationContext.
void Initialize(ISystemIdentity? systemIdentity, User user, InstancePermissionSet? instanceUser)
Initializes the AuthenticationContext.
IDatabaseCollection< User > Users
The Users in the IDatabaseContext.
Represents the currently authenticated Models.User.
ISystemIdentity LoadCachedIdentity(User user)
Attempt to load a cached ISystemIdentity.
Represents a user on the current global::System.Runtime.InteropServices.OSPlatform.