fix(auth): hash stored api keys

This commit is contained in:
shuaiplus
2026-07-02 16:27:20 +08:00
parent 680e287c8d
commit 1545881eae
3 changed files with 58 additions and 33 deletions
+2 -13
View File
@@ -22,6 +22,7 @@ import {
} from './account-passkeys';
import { isAuthRequestExpired } from '../services/storage-auth-request-repo';
import { createPasskeyUserVerificationToken } from '../utils/user-verification-token';
import { constantTimeEquals, verifyApiKey } from '../utils/api-key';
const TWO_FACTOR_REMEMBER_TTL_MS = 30 * 24 * 60 * 60 * 1000;
const TWO_FACTOR_PROVIDER_AUTHENTICATOR = 0;
@@ -106,18 +107,6 @@ function parseCookieValue(request: Request, name: string): string | null {
return null;
}
function constantTimeEquals(a: string, b: string): boolean {
const encA = new TextEncoder().encode(a);
const encB = new TextEncoder().encode(b);
if (encA.length !== encB.length) return false;
let diff = 0;
for (let i = 0; i < encA.length; i++) {
diff |= encA[i] ^ encB[i];
}
return diff === 0;
}
function readBodyValue(body: Record<string, string>, names: string[]): string | undefined {
for (const name of names) {
const value = body[name];
@@ -688,7 +677,7 @@ export async function handleToken(request: Request, env: Env): Promise<Response>
return identityErrorResponse('Account is disabled', 'invalid_grant', 400);
}
if (!user.apiKey || !constantTimeEquals(clientSecret, user.apiKey)) {
if (!user.apiKey || !(await verifyApiKey(clientSecret, user.apiKey))) {
await rateLimit.recordFailedLogin(loginIdentifier);
await safeWriteAuditEvent(env, {
actorUserId: user.id,