fix(auth): fix SQLite DateTimeOffset comparison crash in trusted-device checks

The sessions unit's live smoke test caught the same bug it fixed in
SessionsController also present in TrustedDeviceService and
TwoFactorController's device list: SQLite/Pomelo's EF Core provider
cannot translate DateTimeOffset relational comparisons or ORDER BY to
SQL, so IsDeviceTrustedAsync (the check that skips 2FA for a trusted
browser) and ListTrustedDevices would 500 on real SQLite despite
passing on EF's InMemory test provider. Same fix: equality-only in
the DB query, expiry comparison and sort after materializing.
This commit is contained in:
cesnimda
2026-07-13 01:49:25 +02:00
parent c6918cbeea
commit fb04088d62
2 changed files with 8 additions and 4 deletions
@@ -222,13 +222,14 @@ public sealed class TwoFactorController : ControllerBase
if (user is null) return Unauthorized();
var currentHash = TrustedDeviceService.CurrentDeviceTokenHash(Request);
// SQLite/Pomelo cannot translate DateTimeOffset ORDER BY to SQL (same issue as the
// expiry check in TrustedDeviceService), so sort after materializing.
var devices = await _db.TrustedDevices
.Where(x => x.UserId == user.Id)
.OrderByDescending(x => x.LastSeenAtUtc)
.Select(x => new TrustedDeviceDto(x.Id, x.DeviceLabel, x.CreatedAtUtc, x.LastSeenAtUtc, x.ExpiresAtUtc, currentHash != null && x.TokenHash == currentHash))
.ToListAsync(cancellationToken);
return Ok(devices);
return Ok(devices.OrderByDescending(x => x.LastSeenAtUtc).ToList());
}
[HttpDelete("trusted-devices/{id:int}")]