Add Web Push warning notification backend
This commit is contained in:
59
app/api/notifications/subscriptions/route.ts
Normal file
59
app/api/notifications/subscriptions/route.ts
Normal file
@@ -0,0 +1,59 @@
|
||||
import { NextResponse } from "next/server";
|
||||
import { upsertPushSubscription, removePushSubscription } from "@/lib/push-store";
|
||||
import { isWebPushConfigured } from "@/lib/push-service";
|
||||
import { normalizeProvinceName } from "@/lib/provinces";
|
||||
import type { Language } from "@/lib/i18n";
|
||||
import type { BrowserPushSubscription } from "@/types/notifications";
|
||||
|
||||
export const runtime = "nodejs";
|
||||
|
||||
function isBrowserPushSubscription(value: unknown): value is BrowserPushSubscription {
|
||||
if (!value || typeof value !== "object") return false;
|
||||
const subscription = value as Partial<BrowserPushSubscription>;
|
||||
return typeof subscription.endpoint === "string"
|
||||
&& subscription.endpoint.startsWith("https://")
|
||||
&& typeof subscription.keys?.p256dh === "string"
|
||||
&& typeof subscription.keys.auth === "string";
|
||||
}
|
||||
|
||||
export async function POST(request: Request) {
|
||||
if (!isWebPushConfigured()) {
|
||||
return NextResponse.json({ error: "Web Push is not configured." }, { status: 503 });
|
||||
}
|
||||
|
||||
const body = await request.json().catch(() => null) as {
|
||||
subscription?: unknown;
|
||||
province?: unknown;
|
||||
language?: unknown;
|
||||
enabled?: unknown;
|
||||
} | null;
|
||||
const subscription = body?.subscription;
|
||||
const province = normalizeProvinceName(typeof body?.province === "string" ? body.province : null);
|
||||
const language: Language = body?.language === "en" ? "en" : "pl";
|
||||
|
||||
if (!isBrowserPushSubscription(subscription) || !province) {
|
||||
return NextResponse.json({ error: "Invalid push subscription." }, { status: 400 });
|
||||
}
|
||||
|
||||
const now = new Date().toISOString();
|
||||
upsertPushSubscription({
|
||||
endpoint: subscription.endpoint,
|
||||
subscription,
|
||||
province,
|
||||
language,
|
||||
enabled: body?.enabled !== false,
|
||||
createdAt: now,
|
||||
updatedAt: now,
|
||||
});
|
||||
|
||||
return NextResponse.json({ ok: true });
|
||||
}
|
||||
|
||||
export async function DELETE(request: Request) {
|
||||
const body = await request.json().catch(() => null) as { endpoint?: unknown } | null;
|
||||
if (typeof body?.endpoint !== "string" || !body.endpoint) {
|
||||
return NextResponse.json({ error: "Invalid push subscription endpoint." }, { status: 400 });
|
||||
}
|
||||
removePushSubscription(body.endpoint);
|
||||
return NextResponse.json({ ok: true });
|
||||
}
|
||||
Reference in New Issue
Block a user