feat: add traffic analytics configuration (Umami/GA/Custom)
Add traffic analytics support to the admin panel with three provider options: - Umami (open-source, self-hosted) — script URL + website ID - Google Analytics 4 — Measurement ID (G-XXXXXXXXXX) - Custom — any third-party analytics script (百度统计, Plausible, 51la, etc.) Changes: - admin.types.ts: Add AnalyticsEnabled, AnalyticsProvider, AnalyticsScriptUrl, AnalyticsWebsiteId, AnalyticsCustomScript to SiteConfig interface - config.ts: Add default values in getInitConfig() and configSelfCheck() - api/admin/site/route.ts: Add analytics fields to destructuring, type validation, and SiteConfig update - admin/page.tsx: Add SiteConfig interface fields, state initialization, config sync, and analytics configuration UI with provider-specific input fields - layout.tsx: Inject analytics scripts into <head> based on provider type (Umami: async script with data-website-id; GA: gtag.js + config; Custom: dangerouslySetInnerHTML)
This commit is contained in:
@@ -83,6 +83,11 @@ export async function POST(request: NextRequest) {
|
||||
OIDCClientSecret,
|
||||
OIDCButtonText,
|
||||
OIDCMinTrustLevel,
|
||||
AnalyticsEnabled,
|
||||
AnalyticsProvider,
|
||||
AnalyticsScriptUrl,
|
||||
AnalyticsWebsiteId,
|
||||
AnalyticsCustomScript,
|
||||
} = body as {
|
||||
SiteName: string;
|
||||
Announcement: string;
|
||||
@@ -138,6 +143,11 @@ export async function POST(request: NextRequest) {
|
||||
OIDCClientSecret?: string;
|
||||
OIDCButtonText?: string;
|
||||
OIDCMinTrustLevel?: number;
|
||||
AnalyticsEnabled?: boolean;
|
||||
AnalyticsProvider?: 'umami' | 'google' | 'custom';
|
||||
AnalyticsScriptUrl?: string;
|
||||
AnalyticsWebsiteId?: string;
|
||||
AnalyticsCustomScript?: string;
|
||||
};
|
||||
|
||||
// 参数校验
|
||||
@@ -224,7 +234,15 @@ export async function POST(request: NextRequest) {
|
||||
(OIDCClientSecret !== undefined &&
|
||||
typeof OIDCClientSecret !== 'string') ||
|
||||
(OIDCButtonText !== undefined && typeof OIDCButtonText !== 'string') ||
|
||||
(OIDCMinTrustLevel !== undefined && typeof OIDCMinTrustLevel !== 'number')
|
||||
(OIDCMinTrustLevel !== undefined && typeof OIDCMinTrustLevel !== 'number') ||
|
||||
(AnalyticsEnabled !== undefined && typeof AnalyticsEnabled !== 'boolean') ||
|
||||
(AnalyticsProvider !== undefined &&
|
||||
AnalyticsProvider !== 'umami' &&
|
||||
AnalyticsProvider !== 'google' &&
|
||||
AnalyticsProvider !== 'custom') ||
|
||||
(AnalyticsScriptUrl !== undefined && typeof AnalyticsScriptUrl !== 'string') ||
|
||||
(AnalyticsWebsiteId !== undefined && typeof AnalyticsWebsiteId !== 'string') ||
|
||||
(AnalyticsCustomScript !== undefined && typeof AnalyticsCustomScript !== 'string')
|
||||
) {
|
||||
return NextResponse.json({ error: '参数格式错误' }, { status: 400 });
|
||||
}
|
||||
@@ -295,6 +313,11 @@ export async function POST(request: NextRequest) {
|
||||
OIDCClientSecret,
|
||||
OIDCButtonText,
|
||||
OIDCMinTrustLevel,
|
||||
AnalyticsEnabled,
|
||||
AnalyticsProvider,
|
||||
AnalyticsScriptUrl,
|
||||
AnalyticsWebsiteId,
|
||||
AnalyticsCustomScript,
|
||||
};
|
||||
|
||||
// 写入数据库
|
||||
|
||||
Reference in New Issue
Block a user