mirror of
https://github.com/KuekHaoYang/KVideo.git
synced 2026-08-12 23:33:43 +08:00
fix: support Upstash Redis on Cloudflare Pages
This commit is contained in:
+19
-2
@@ -3,13 +3,24 @@ import {
|
||||
authenticateLogin,
|
||||
createLoginResponse,
|
||||
getPublicAuthConfig,
|
||||
ManagedAuthStorageError,
|
||||
validatePremiumAccess,
|
||||
} from '@/lib/server/auth';
|
||||
|
||||
export const runtime = 'edge';
|
||||
|
||||
export async function GET() {
|
||||
return NextResponse.json(await getPublicAuthConfig());
|
||||
try {
|
||||
return NextResponse.json(await getPublicAuthConfig());
|
||||
} catch (error) {
|
||||
if (error instanceof ManagedAuthStorageError) {
|
||||
return NextResponse.json(
|
||||
{ error: 'Managed authentication storage is unavailable' },
|
||||
{ status: 503 },
|
||||
);
|
||||
}
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
|
||||
export async function POST(request: NextRequest) {
|
||||
@@ -32,7 +43,13 @@ export async function POST(request: NextRequest) {
|
||||
}
|
||||
|
||||
return createLoginResponse(session, request);
|
||||
} catch {
|
||||
} catch (error) {
|
||||
if (error instanceof ManagedAuthStorageError) {
|
||||
return NextResponse.json(
|
||||
{ valid: false, message: 'Managed authentication storage is unavailable' },
|
||||
{ status: 503 },
|
||||
);
|
||||
}
|
||||
return NextResponse.json({ valid: false, message: 'Invalid request' }, { status: 400 });
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,10 +1,24 @@
|
||||
import { NextRequest } from 'next/server';
|
||||
import { createSessionStatusResponse, logoutResponse } from '@/lib/server/auth';
|
||||
import {
|
||||
createSessionStatusResponse,
|
||||
logoutResponse,
|
||||
ManagedAuthStorageError,
|
||||
} from '@/lib/server/auth';
|
||||
|
||||
export const runtime = 'edge';
|
||||
|
||||
export async function GET(request: NextRequest) {
|
||||
return createSessionStatusResponse(request);
|
||||
try {
|
||||
return await createSessionStatusResponse(request);
|
||||
} catch (error) {
|
||||
if (error instanceof ManagedAuthStorageError) {
|
||||
return Response.json(
|
||||
{ authenticated: false, error: 'Managed authentication storage is unavailable' },
|
||||
{ status: 503 },
|
||||
);
|
||||
}
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
|
||||
export async function DELETE(request: NextRequest) {
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* so they persist across browsers, devices, and PWA installs.
|
||||
*/
|
||||
|
||||
import { Redis } from '@upstash/redis';
|
||||
import { Redis } from '@upstash/redis/cloudflare';
|
||||
import { NextRequest, NextResponse } from 'next/server';
|
||||
import { authenticationRequiredResponse } from '@/lib/server/api-responses';
|
||||
import { getServerSession } from '@/lib/server/auth';
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { Redis } from '@upstash/redis';
|
||||
import { Redis } from '@upstash/redis/cloudflare';
|
||||
import { NextRequest, NextResponse } from 'next/server';
|
||||
import { authenticationRequiredResponse } from '@/lib/server/api-responses';
|
||||
import { getServerSession } from '@/lib/server/auth';
|
||||
|
||||
@@ -207,6 +207,12 @@ export function PasswordGate({
|
||||
});
|
||||
const data = await response.json();
|
||||
|
||||
if (response.status === 503) {
|
||||
setError('认证存储暂时不可用,请检查 Upstash Redis 配置');
|
||||
setIsValidating(false);
|
||||
return;
|
||||
}
|
||||
|
||||
if (data.valid && data.session) {
|
||||
setSession(toAuthSession(data.session), data.persistSession ?? persistSession);
|
||||
setIsLocked(false);
|
||||
|
||||
+21
-5
@@ -1,4 +1,4 @@
|
||||
import { Redis } from '@upstash/redis';
|
||||
import { Redis } from '@upstash/redis/cloudflare';
|
||||
import { NextRequest, NextResponse } from 'next/server';
|
||||
import { getRuntimeFeatures } from '@/lib/server/runtime-features';
|
||||
import {
|
||||
@@ -89,6 +89,13 @@ const effectiveAdminPassword = ADMIN_PASSWORD || ACCESS_PASSWORD;
|
||||
|
||||
let cachedRedis: Redis | null | undefined;
|
||||
|
||||
export class ManagedAuthStorageError extends Error {
|
||||
constructor(operation: 'read' | 'write', cause?: unknown) {
|
||||
super(`Managed auth storage ${operation} failed`, { cause });
|
||||
this.name = 'ManagedAuthStorageError';
|
||||
}
|
||||
}
|
||||
|
||||
function getRedisClient(): Redis | null {
|
||||
if (cachedRedis !== undefined) {
|
||||
return cachedRedis;
|
||||
@@ -99,7 +106,10 @@ function getRedisClient(): Redis | null {
|
||||
return cachedRedis;
|
||||
}
|
||||
|
||||
cachedRedis = Redis.fromEnv();
|
||||
cachedRedis = new Redis({
|
||||
url: process.env.UPSTASH_REDIS_REST_URL,
|
||||
token: process.env.UPSTASH_REDIS_REST_TOKEN,
|
||||
});
|
||||
return cachedRedis;
|
||||
}
|
||||
|
||||
@@ -140,8 +150,9 @@ async function readManagedAccounts(): Promise<StoredAccountRecord[]> {
|
||||
const stored = await redis.get(MANAGED_ACCOUNTS_KEY);
|
||||
if (!Array.isArray(stored)) return [];
|
||||
return stored.filter(isStoredAccountRecord).map(normalizeStoredAccount);
|
||||
} catch {
|
||||
return [];
|
||||
} catch (error) {
|
||||
console.error('Managed auth Redis read failed:', error);
|
||||
throw new ManagedAuthStorageError('read', error);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -151,7 +162,12 @@ async function saveManagedAccounts(accounts: StoredAccountRecord[]): Promise<voi
|
||||
throw new Error('Managed auth storage unavailable');
|
||||
}
|
||||
|
||||
await redis.set(MANAGED_ACCOUNTS_KEY, accounts);
|
||||
try {
|
||||
await redis.set(MANAGED_ACCOUNTS_KEY, accounts);
|
||||
} catch (error) {
|
||||
console.error('Managed auth Redis write failed:', error);
|
||||
throw new ManagedAuthStorageError('write', error);
|
||||
}
|
||||
}
|
||||
|
||||
function getBootstrapSeeds(): SeedAccountInput[] {
|
||||
|
||||
Reference in New Issue
Block a user