import { getHostUrl, validateEmail } from "../../../lib/utils.ts"; import { storage } from "../../../lib/storage.ts"; import { createAgreement } from "../../../lib/vipps/vipps.ts"; import { getAgreement } from "../../../lib/vipps/vipps.ts"; export const handler = async function (req: Request): Promise { const email = new URLSearchParams(req.url.split("?")[1] || "").get("email"); const errorPage = `${getHostUrl()}/donations-error`; if (!email) { console.error("Missing email in query params", req.url); return Response.redirect(errorPage); } const valid = validateEmail(email); if (!valid) { console.error("Invalid email server side", email); return Response.redirect(errorPage); } const existingAgreement = await storage.readVippsAgreement({ id: email }); const hasActiveAgreement = existingAgreement && existingAgreement.validAt !== null && existingAgreement.revokedAt === null; const agreementInVipps = existingAgreement && (await getAgreement(existingAgreement.agreementId)); if ( agreementInVipps && !(agreementInVipps instanceof Error) && agreementInVipps.status !== "ACTIVE" && hasActiveAgreement ) { // Somehow the Vipps agreement is not active in our system anymore. // We should reflect the new status in our system. await storage.writeVippsAgreement({ ...existingAgreement, revokedAt: new Date(), }); } else { // i.e. the agreement in our system was in sync with Vipps. if (hasActiveAgreement) { console.error("Agreement already exists", email); return Response.redirect(errorPage); } } const agreement = await createAgreement(email); if (agreement instanceof Error) { console.error("Failed to create Vipps agreement", agreement); return Response.redirect(errorPage); } // associate the agreement with the user here // so it can be updated in the success page await storage.writeVippsAgreement({ id: email, agreementId: agreement.agreementId, createdAt: new Date(), validAt: null, revokedAt: null, }); return Response.redirect(agreement.vippsConfirmationUrl); };