[backend/razor] Allow logging in as users that the frontend has already authenticated (ISH-406)
This reduces friction when logging in to multiple apps.
This commit is contained in:
parent
1ace285d35
commit
e5e66e8a3d
3 changed files with 59 additions and 21 deletions
|
@ -29,11 +29,28 @@
|
|||
<input type="checkbox" name="autoDetectQuotes" id="autoDetectQuotes" value="1"/>
|
||||
<label for="autoDetectQuotes">Automatically detect quotes</label>
|
||||
</div>
|
||||
<div class="margin-bottom-5px margin-top-10px">
|
||||
Log in below to confirm this:
|
||||
@if (Model.AuthenticatedUsers.Count > 0)
|
||||
{
|
||||
<div class="margin-top-5px">
|
||||
@foreach (var user in Model.AuthenticatedUsers)
|
||||
{
|
||||
<button type="submit" name="userId" value="@user.Id">Log in as @@@user.Username</button>
|
||||
}
|
||||
</div>
|
||||
<div class="margin-bottom-5px margin-top-5px">
|
||||
Alternatively, sign in with to a different account below:
|
||||
</div>
|
||||
<input type="text" placeholder="Username" name="username"/>
|
||||
<input type="password" placeholder="Password" name="password"/>
|
||||
}
|
||||
else
|
||||
{
|
||||
<div class="margin-bottom-5px margin-top-10px">
|
||||
Log in below to confirm this:
|
||||
</div>
|
||||
<input type="text" placeholder="Username" name="username" required/>
|
||||
<input type="password" placeholder="Password" name="password" required/>
|
||||
}
|
||||
<button type="submit">Submit</button>
|
||||
</form>
|
||||
</div>
|
||||
|
|
|
@ -16,6 +16,7 @@ public class AuthorizeModel(DatabaseContext db) : PageModel
|
|||
|
||||
public List<string> Scopes = [];
|
||||
public OauthToken? Token;
|
||||
public List<User> AuthenticatedUsers = [];
|
||||
[FromQuery(Name = "response_type")] public string ResponseType { get; set; } = null!;
|
||||
[FromQuery(Name = "client_id")] public string ClientId { get; set; } = null!;
|
||||
[FromQuery(Name = "redirect_uri")] public string RedirectUri { get; set; } = null!;
|
||||
|
@ -41,25 +42,41 @@ public class AuthorizeModel(DatabaseContext db) : PageModel
|
|||
throw GracefulException.BadRequest("Invalid response_type");
|
||||
if (!App.RedirectUris.Contains(RedirectUri))
|
||||
throw GracefulException.BadRequest("Cannot request redirect_uri not sent during app registration");
|
||||
if (Request.Cookies.TryGetValue("sessions", out var sessions))
|
||||
{
|
||||
var tokens = sessions.Split(',');
|
||||
AuthenticatedUsers = await db.Sessions
|
||||
.Where(p => tokens.Contains(p.Token) && p.Active)
|
||||
.Select(p => p.User)
|
||||
.ToListAsync();
|
||||
}
|
||||
}
|
||||
|
||||
public async Task OnPost(
|
||||
[FromForm] string username, [FromForm] string password, [FromForm] bool supportsHtmlFormatting,
|
||||
[FromForm] bool autoDetectQuotes
|
||||
[FromForm] string? username, [FromForm] string? password, [FromForm] string? userId,
|
||||
[FromForm] bool supportsHtmlFormatting, [FromForm] bool autoDetectQuotes
|
||||
)
|
||||
{
|
||||
// Validate query parameters first
|
||||
// Validate query parameters & populate model first
|
||||
await OnGet();
|
||||
|
||||
var user = await db.Users.FirstOrDefaultAsync(p => p.IsLocalUser &&
|
||||
p.UsernameLower == username.ToLowerInvariant());
|
||||
var user = AuthenticatedUsers.FirstOrDefault(p => p.Id == userId);
|
||||
|
||||
if (user == null)
|
||||
throw GracefulException.Forbidden("Invalid username or password");
|
||||
{
|
||||
Exception Forbidden() => GracefulException.Forbidden("Invalid username or password");
|
||||
if (username == null || password == null)
|
||||
throw Forbidden();
|
||||
|
||||
user = await db.Users.FirstOrDefaultAsync(p => p.IsLocalUser &&
|
||||
p.UsernameLower == username.ToLowerInvariant()) ??
|
||||
throw Forbidden();
|
||||
var userSettings = await db.UserSettings.FirstOrDefaultAsync(p => p.User == user);
|
||||
if (userSettings?.Password == null)
|
||||
throw GracefulException.Forbidden("Invalid username or password");
|
||||
throw Forbidden();
|
||||
if (AuthHelpers.ComparePassword(password, userSettings.Password) == false)
|
||||
throw GracefulException.Forbidden("Invalid username or password");
|
||||
throw Forbidden();
|
||||
}
|
||||
|
||||
var token = new OauthToken
|
||||
{
|
||||
|
|
|
@ -6,6 +6,10 @@
|
|||
margin-bottom: 5px;
|
||||
}
|
||||
|
||||
.margin-top-5px {
|
||||
margin-top: 5px;
|
||||
}
|
||||
|
||||
.margin-top-10px {
|
||||
margin-top: 10px;
|
||||
}
|
Loading…
Add table
Reference in a new issue