feat: alert operators on paid intake leads
All checks were successful
CI and Production Smoke / smoke (push) Successful in 6s
All checks were successful
CI and Production Smoke / smoke (push) Successful in 6s
This commit is contained in:
@@ -23,6 +23,13 @@ const stripe = process.env.STRIPE_SECRET_KEY
|
||||
})
|
||||
: null;
|
||||
|
||||
const TELEGRAM_BOT_TOKEN = process.env.TELEGRAM_BOT_TOKEN?.trim();
|
||||
const TELEGRAM_CHAT_ID = (
|
||||
process.env.A2A_GROWTH_TELEGRAM_CHAT_ID ||
|
||||
process.env.A2A_TELEGRAM_CHAT_ID ||
|
||||
process.env.TELEGRAM_CHAT_ID
|
||||
)?.trim();
|
||||
|
||||
function getString(formData: FormData, key: string) {
|
||||
const value = formData.get(key);
|
||||
return typeof value === "string" ? value.trim() : "";
|
||||
@@ -72,6 +79,57 @@ function buildCancelUrl(referralAgent: string, packageId: string) {
|
||||
return url.toString();
|
||||
}
|
||||
|
||||
async function notifyPaidIntakeLead(params: {
|
||||
taskId: string;
|
||||
proposerEmail: string;
|
||||
referralAgent: string;
|
||||
packageName: string;
|
||||
packageLabel: string;
|
||||
paymentMethod: string;
|
||||
checkoutUrl: string;
|
||||
source: string;
|
||||
campaign: string;
|
||||
quickMode: boolean;
|
||||
}) {
|
||||
if (!TELEGRAM_BOT_TOKEN || !TELEGRAM_CHAT_ID) return;
|
||||
|
||||
const text = [
|
||||
"VibeWork paid intake lead",
|
||||
`Package: ${params.packageName} (${params.packageLabel})`,
|
||||
`Payment: ${params.paymentMethod}`,
|
||||
`Email: ${params.proposerEmail}`,
|
||||
`Referral: ${params.referralAgent || "direct"}`,
|
||||
`Source: ${params.source}`,
|
||||
`Campaign: ${params.campaign}`,
|
||||
`Quick mode: ${params.quickMode ? "yes" : "no"}`,
|
||||
`Proposal: ${params.taskId}`,
|
||||
`Checkout: ${params.checkoutUrl}`,
|
||||
"",
|
||||
"Action: follow up if wallet payment is not confirmed.",
|
||||
].join("\n");
|
||||
|
||||
try {
|
||||
const controller = new AbortController();
|
||||
const timeout = setTimeout(() => controller.abort(), 1500);
|
||||
try {
|
||||
await fetch(`https://api.telegram.org/bot${TELEGRAM_BOT_TOKEN}/sendMessage`, {
|
||||
method: "POST",
|
||||
headers: { "content-type": "application/json" },
|
||||
body: JSON.stringify({
|
||||
chat_id: TELEGRAM_CHAT_ID,
|
||||
text,
|
||||
disable_web_page_preview: false,
|
||||
}),
|
||||
signal: controller.signal,
|
||||
});
|
||||
} finally {
|
||||
clearTimeout(timeout);
|
||||
}
|
||||
} catch (error) {
|
||||
console.warn("[propose] paid intake Telegram alert failed", error);
|
||||
}
|
||||
}
|
||||
|
||||
export async function createDemandProposal(formData: FormData) {
|
||||
const requestHeaders = await headers();
|
||||
const packageId = getString(formData, "packageId");
|
||||
@@ -257,10 +315,25 @@ export async function createDemandProposal(formData: FormData) {
|
||||
});
|
||||
}
|
||||
|
||||
redirect(buildSuccessUrl(task.id, {
|
||||
const checkoutUrl = buildSuccessUrl(task.id, {
|
||||
payment: "wallet",
|
||||
package: proposalPackage.id,
|
||||
}));
|
||||
});
|
||||
|
||||
await notifyPaidIntakeLead({
|
||||
taskId: task.id,
|
||||
proposerEmail,
|
||||
referralAgent,
|
||||
packageName: proposalPackage.name,
|
||||
packageLabel: proposalPackage.label,
|
||||
paymentMethod: "wallet",
|
||||
checkoutUrl,
|
||||
source,
|
||||
campaign,
|
||||
quickMode,
|
||||
});
|
||||
|
||||
redirect(checkoutUrl);
|
||||
}
|
||||
|
||||
const session = await stripe.checkout.sessions.create({
|
||||
@@ -326,5 +399,18 @@ export async function createDemandProposal(formData: FormData) {
|
||||
});
|
||||
}
|
||||
|
||||
await notifyPaidIntakeLead({
|
||||
taskId: task.id,
|
||||
proposerEmail,
|
||||
referralAgent,
|
||||
packageName: proposalPackage.name,
|
||||
packageLabel: proposalPackage.label,
|
||||
paymentMethod: "stripe",
|
||||
checkoutUrl: session.url,
|
||||
source,
|
||||
campaign,
|
||||
quickMode,
|
||||
});
|
||||
|
||||
redirect(session.url);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user