@infuro/cms-core 1.0.58 → 1.0.60

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (35) hide show
  1. package/dist/admin.cjs +442 -37
  2. package/dist/admin.js +443 -38
  3. package/dist/api.cjs +41 -37
  4. package/dist/api.d.cts +2 -1
  5. package/dist/api.d.ts +2 -1
  6. package/dist/api.js +5 -5
  7. package/dist/auth.cjs +51 -51
  8. package/dist/auth.js +3 -3
  9. package/dist/{chunk-3EOM4V2M.cjs → chunk-4U6DATGZ.cjs} +7 -7
  10. package/dist/{chunk-BNKZNLEX.js → chunk-6DBDJ4VD.js} +2 -2
  11. package/dist/{chunk-UQWZUZ5X.cjs → chunk-73WVHINE.cjs} +30 -6
  12. package/dist/{chunk-UCKN4BBY.cjs → chunk-77I3KS7V.cjs} +4 -1
  13. package/dist/{chunk-BHUEXLD2.cjs → chunk-BSLNXKV2.cjs} +415 -131
  14. package/dist/{chunk-77NUXO6A.cjs → chunk-J7FMZK66.cjs} +10 -2
  15. package/dist/{chunk-AGU3B5JW.js → chunk-JAEUYYGA.js} +335 -52
  16. package/dist/{chunk-BC22I7C7.cjs → chunk-KM2I6AFP.cjs} +9 -9
  17. package/dist/{chunk-JIWUVQ6B.js → chunk-MVHDC3XF.js} +10 -2
  18. package/dist/{chunk-RK5ETF2I.js → chunk-NR44CK5E.js} +1 -1
  19. package/dist/{chunk-MXIWUFBP.js → chunk-O2642WVS.js} +28 -4
  20. package/dist/{chunk-HCIRL37O.js → chunk-T3HPSF7K.js} +4 -1
  21. package/dist/{chunk-HYW3MUXT.js → chunk-URN7GS23.js} +30 -16
  22. package/dist/{chunk-HXLC56ZK.cjs → chunk-YSYX4GUD.cjs} +32 -18
  23. package/dist/{emit-order-notification-trigger-HZQPPSFB.js → emit-order-notification-trigger-CZU3V2WE.js} +2 -2
  24. package/dist/{emit-order-notification-trigger-NR3VN6C6.cjs → emit-order-notification-trigger-TNEZOYEE.cjs} +4 -4
  25. package/dist/index.cjs +342 -300
  26. package/dist/index.d.cts +33 -1
  27. package/dist/index.d.ts +33 -1
  28. package/dist/index.js +54 -16
  29. package/dist/migrations/1782800000000-AddPaymentSuccessFailedRefundTriggers.ts +32 -0
  30. package/dist/migrations/1782900000000-AddEnableTurnstileToForms.ts +29 -0
  31. package/dist/{order-notification-dispatcher-2FCZFZUD.cjs → order-notification-dispatcher-KJVGLK5E.cjs} +5 -5
  32. package/dist/{order-notification-dispatcher-64WDCHHG.js → order-notification-dispatcher-ZSFKEYMP.js} +2 -2
  33. package/dist/{rbac-debug-db-6EMIVMGF.js → rbac-debug-db-5R6XFPSV.js} +1 -1
  34. package/dist/{rbac-debug-db-6PWTLBEL.cjs → rbac-debug-db-JKK2MCWF.cjs} +2 -2
  35. package/package.json +1 -1
@@ -2,16 +2,16 @@
2
2
 
3
3
  var chunkXQ3QUHWR_cjs = require('./chunk-XQ3QUHWR.cjs');
4
4
  var chunkHY3AXLOI_cjs = require('./chunk-HY3AXLOI.cjs');
5
- var chunkHXLC56ZK_cjs = require('./chunk-HXLC56ZK.cjs');
5
+ var chunkYSYX4GUD_cjs = require('./chunk-YSYX4GUD.cjs');
6
6
  var chunk7NMT3GBR_cjs = require('./chunk-7NMT3GBR.cjs');
7
7
  var chunkV25RDUOU_cjs = require('./chunk-V25RDUOU.cjs');
8
8
  var chunkBXYZDMTZ_cjs = require('./chunk-BXYZDMTZ.cjs');
9
9
  var chunkUPLVMVRX_cjs = require('./chunk-UPLVMVRX.cjs');
10
10
  var chunk3DZRIZOD_cjs = require('./chunk-3DZRIZOD.cjs');
11
11
  var chunkTJ2MIQUT_cjs = require('./chunk-TJ2MIQUT.cjs');
12
- var chunk3EOM4V2M_cjs = require('./chunk-3EOM4V2M.cjs');
12
+ var chunk4U6DATGZ_cjs = require('./chunk-4U6DATGZ.cjs');
13
13
  var chunkOY2YTBMP_cjs = require('./chunk-OY2YTBMP.cjs');
14
- var chunk77NUXO6A_cjs = require('./chunk-77NUXO6A.cjs');
14
+ var chunkJ7FMZK66_cjs = require('./chunk-J7FMZK66.cjs');
15
15
  var chunkD5FBNKQM_cjs = require('./chunk-D5FBNKQM.cjs');
16
16
  var chunkUSNT2KNT_cjs = require('./chunk-USNT2KNT.cjs');
17
17
  var typeorm = require('typeorm');
@@ -120,7 +120,7 @@ async function loadUserVendorContext(dataSource, userId, preferredVendorId) {
120
120
  `, [
121
121
  primary.vendorRoleId
122
122
  ]);
123
- vendorEntityPerms = chunk77NUXO6A_cjs.permissionRowsToRecord(permRows);
123
+ vendorEntityPerms = chunkJ7FMZK66_cjs.permissionRowsToRecord(permRows);
124
124
  } catch (err) {
125
125
  if (!isMissingVendorRoleSchemaError(err)) throw err;
126
126
  }
@@ -227,7 +227,7 @@ async function hydrateVendorSessionUser(dataSource, user) {
227
227
  ]);
228
228
  const resolvedId = Number(byEmailRows[0]?.id);
229
229
  if (!Number.isFinite(resolvedId)) {
230
- chunk77NUXO6A_cjs.logRbac("hydrateVendorSessionUser: unable to resolve numeric user id", {
230
+ chunkJ7FMZK66_cjs.logRbac("hydrateVendorSessionUser: unable to resolve numeric user id", {
231
231
  email: user.email,
232
232
  rawSessionId: user.id ?? null
233
233
  });
@@ -247,7 +247,7 @@ async function hydrateVendorSessionUser(dataSource, user) {
247
247
  const groupName = rows[0]?.groupName ?? user.groupName ?? null;
248
248
  const groupId = rows[0]?.groupId ?? user.groupId ?? void 0;
249
249
  const adminAccess = rows[0]?.adminAccess ?? user.adminAccess;
250
- const isRBACAdmin = user.isRBACAdmin ?? chunk77NUXO6A_cjs.isSuperAdmin({
250
+ const isRBACAdmin = user.isRBACAdmin ?? chunkJ7FMZK66_cjs.isSuperAdmin({
251
251
  groupId,
252
252
  groupName,
253
253
  isRBACAdmin: user.isRBACAdmin
@@ -260,7 +260,7 @@ async function hydrateVendorSessionUser(dataSource, user) {
260
260
  };
261
261
  if (multiVendorEnabled) {
262
262
  ctx = await loadUserVendorContext(dataSource, id, user.activeVendorId);
263
- flags = chunk77NUXO6A_cjs.vendorPortalFlagsFromUser({
263
+ flags = chunkJ7FMZK66_cjs.vendorPortalFlagsFromUser({
264
264
  email: user.email,
265
265
  isRBACAdmin,
266
266
  groupName,
@@ -295,7 +295,7 @@ async function hydrateVendorSessionUser(dataSource, user) {
295
295
  isVendorPortal: flags.isVendorPortal,
296
296
  isVendorOwner: flags.isVendorOwner
297
297
  };
298
- chunk77NUXO6A_cjs.logRbac("hydrateVendorSessionUser", {
298
+ chunkJ7FMZK66_cjs.logRbac("hydrateVendorSessionUser", {
299
299
  email: user.email,
300
300
  userId: id,
301
301
  groupName,
@@ -908,7 +908,7 @@ function repoHasVendorIdColumn(repo) {
908
908
  }
909
909
  chunkUSNT2KNT_cjs.__name(repoHasVendorIdColumn, "repoHasVendorIdColumn");
910
910
  function resourceUsesVendorScope(resource) {
911
- return resource === "vendors" || chunk77NUXO6A_cjs.VENDOR_SCOPED_STORE_ENTITIES.has(resource);
911
+ return resource === "vendors" || chunkJ7FMZK66_cjs.VENDOR_SCOPED_STORE_ENTITIES.has(resource);
912
912
  }
913
913
  chunkUSNT2KNT_cjs.__name(resourceUsesVendorScope, "resourceUsesVendorScope");
914
914
  function mergeWhereClause(where, extra) {
@@ -1398,7 +1398,7 @@ async function ensureVendorCustomersForOrder(dataSource, entityMap, vendorIds, c
1398
1398
  }
1399
1399
  let customerId = null;
1400
1400
  if (entityMap.customer) {
1401
- const ensured = await chunk3EOM4V2M_cjs.ensureCustomerRecord(dataSource, entityMap.customer, {
1401
+ const ensured = await chunk4U6DATGZ_cjs.ensureCustomerRecord(dataSource, entityMap.customer, {
1402
1402
  name,
1403
1403
  email,
1404
1404
  phone,
@@ -1520,6 +1520,36 @@ async function validateLlmAgentScopeForWrite(dataSource, entityMap, scope, exclu
1520
1520
  chunkUSNT2KNT_cjs.__name(validateLlmAgentScopeForWrite, "validateLlmAgentScopeForWrite");
1521
1521
 
1522
1522
  // src/api/crud.ts
1523
+ async function autoExpireOrderIfPaymentTimeExceeded(dataSource, entityMap, order) {
1524
+ if (!order || typeof order !== "object") return order;
1525
+ const status = String(order.status ?? "").toLowerCase();
1526
+ if (status !== "pending") return order;
1527
+ const meta = typeof order.metadata === "object" && order.metadata ? order.metadata : {};
1528
+ const expiresAtStr = meta.paymentExpiresAt ? String(meta.paymentExpiresAt) : null;
1529
+ if (!expiresAtStr) return order;
1530
+ const expiresMs = new Date(expiresAtStr).getTime();
1531
+ if (Number.isNaN(expiresMs) || Date.now() <= expiresMs) return order;
1532
+ try {
1533
+ const orderId = Number(order.id);
1534
+ if (orderId && entityMap.orders) {
1535
+ const orderRepo = dataSource.getRepository(entityMap.orders);
1536
+ const updatedMeta = {
1537
+ ...meta,
1538
+ cancelReason: "Payment window expired (10 minutes)"
1539
+ };
1540
+ await orderRepo.update(orderId, {
1541
+ status: "cancelled",
1542
+ metadata: updatedMeta
1543
+ });
1544
+ order.status = "cancelled";
1545
+ order.metadata = updatedMeta;
1546
+ }
1547
+ } catch (err) {
1548
+ console.error("[payment-expiry] Auto-cancelling expired order failed", err);
1549
+ }
1550
+ return order;
1551
+ }
1552
+ chunkUSNT2KNT_cjs.__name(autoExpireOrderIfPaymentTimeExceeded, "autoExpireOrderIfPaymentTimeExceeded");
1523
1553
  var CRUD_LOG = "[cms-crud]";
1524
1554
  function logCrudClientError(op, detail) {
1525
1555
  console.warn(CRUD_LOG, op, detail);
@@ -2424,13 +2454,46 @@ function discountCompare(cartValue, op, ruleValue) {
2424
2454
  }
2425
2455
  }
2426
2456
  chunkUSNT2KNT_cjs.__name(discountCompare, "discountCompare");
2427
- function discountEvaluateRule(rule, cartLines, cartTotal) {
2428
- if (rule.conditionType === "group") return discountEvaluateGroup(rule, cartLines, cartTotal);
2457
+ async function getExchangeRate(dataSource, entityMap, fromCurrency, toCurrency) {
2458
+ const from = (fromCurrency || "INR").trim().toUpperCase();
2459
+ const to = (toCurrency || "INR").trim().toUpperCase();
2460
+ if (from === to) return 1;
2461
+ if (entityMap["currency_exchange"]) {
2462
+ try {
2463
+ const exchangeRepo = dataSource.getRepository(entityMap["currency_exchange"]);
2464
+ const direct = await exchangeRepo.findOne({
2465
+ where: {
2466
+ fromCurrency: from,
2467
+ toCurrency: to
2468
+ }
2469
+ });
2470
+ if (direct && Number(direct.rate) > 0) {
2471
+ return Number(direct.rate);
2472
+ }
2473
+ const inverse = await exchangeRepo.findOne({
2474
+ where: {
2475
+ fromCurrency: to,
2476
+ toCurrency: from
2477
+ }
2478
+ });
2479
+ if (inverse && Number(inverse.rate) > 0) {
2480
+ return 1 / Number(inverse.rate);
2481
+ }
2482
+ } catch {
2483
+ }
2484
+ }
2485
+ return 1;
2486
+ }
2487
+ chunkUSNT2KNT_cjs.__name(getExchangeRate, "getExchangeRate");
2488
+ function discountEvaluateRule(rule, cartLines, cartTotal, exchangeRate = 1) {
2489
+ if (rule.conditionType === "group") return discountEvaluateGroup(rule, cartLines, cartTotal, exchangeRate);
2429
2490
  if (rule.type === "reward") return true;
2430
- const ruleValue = discountExtractValue(rule.value);
2491
+ const rawRuleValue = discountExtractValue(rule.value);
2431
2492
  switch (rule.type) {
2432
- case "minAmount":
2433
- return discountCompare(cartTotal, rule.comparisonOperator, ruleValue);
2493
+ case "minAmount": {
2494
+ const convertedValue = typeof rawRuleValue === "number" ? rawRuleValue * exchangeRate : !isNaN(Number(rawRuleValue)) ? Number(rawRuleValue) * exchangeRate : rawRuleValue;
2495
+ return discountCompare(cartTotal, rule.comparisonOperator, convertedValue);
2496
+ }
2434
2497
  case "quantity": {
2435
2498
  if (rule.subType === "productId" && rule.value?.productId) {
2436
2499
  const targetProductId = Number(rule.value.productId);
@@ -2439,11 +2502,11 @@ function discountEvaluateRule(rule, cartLines, cartTotal) {
2439
2502
  return discountCompare(productQty, rule.comparisonOperator, requiredQty);
2440
2503
  }
2441
2504
  const totalQty = cartLines.reduce((s, l) => s + l.quantity, 0);
2442
- return discountCompare(totalQty, rule.comparisonOperator, ruleValue);
2505
+ return discountCompare(totalQty, rule.comparisonOperator, rawRuleValue);
2443
2506
  }
2444
2507
  case "product":
2445
2508
  if (rule.subType === "productId") {
2446
- return cartLines.some((l) => discountCompare(l.productId, rule.comparisonOperator, ruleValue));
2509
+ return cartLines.some((l) => discountCompare(l.productId, rule.comparisonOperator, rawRuleValue));
2447
2510
  }
2448
2511
  return false;
2449
2512
  // These require external context (user session, payment method, time) —
@@ -2467,11 +2530,11 @@ function discountEvaluateRule(rule, cartLines, cartTotal) {
2467
2530
  }
2468
2531
  }
2469
2532
  chunkUSNT2KNT_cjs.__name(discountEvaluateRule, "discountEvaluateRule");
2470
- function discountEvaluateGroup(group, cartLines, cartTotal) {
2533
+ function discountEvaluateGroup(group, cartLines, cartTotal, exchangeRate = 1) {
2471
2534
  if (!group.children?.length) return true;
2472
2535
  const op = (group.conditionOperator ?? "and").toLowerCase();
2473
- if (op === "and") return group.children.every((child) => discountEvaluateRule(child, cartLines, cartTotal));
2474
- if (op === "or") return group.children.some((child) => discountEvaluateRule(child, cartLines, cartTotal));
2536
+ if (op === "and") return group.children.every((child) => discountEvaluateRule(child, cartLines, cartTotal, exchangeRate));
2537
+ if (op === "or") return group.children.some((child) => discountEvaluateRule(child, cartLines, cartTotal, exchangeRate));
2475
2538
  return true;
2476
2539
  }
2477
2540
  chunkUSNT2KNT_cjs.__name(discountEvaluateGroup, "discountEvaluateGroup");
@@ -2518,19 +2581,19 @@ function discountExtractBuyProductId(nodes) {
2518
2581
  return null;
2519
2582
  }
2520
2583
  chunkUSNT2KNT_cjs.__name(discountExtractBuyProductId, "discountExtractBuyProductId");
2521
- function discountBuildUniversalResult(discount, cartLines) {
2584
+ function discountBuildUniversalResult(discount, cartLines, effectiveValue) {
2522
2585
  return {
2523
2586
  rewardLines: cartLines.map((l) => ({
2524
2587
  productId: l.productId,
2525
2588
  quantity: l.quantity,
2526
- discountRate: Number(discount.value),
2589
+ discountRate: effectiveValue,
2527
2590
  discountType: discount.discountType
2528
2591
  })),
2529
2592
  conditionsMet: true
2530
2593
  };
2531
2594
  }
2532
2595
  chunkUSNT2KNT_cjs.__name(discountBuildUniversalResult, "discountBuildUniversalResult");
2533
- function evaluateDiscount(discount, cartLines) {
2596
+ function evaluateDiscount(discount, cartLines, exchangeRate = 1) {
2534
2597
  const empty = {
2535
2598
  rewardLines: [],
2536
2599
  conditionsMet: false
@@ -2554,16 +2617,17 @@ function evaluateDiscount(discount, cartLines) {
2554
2617
  reason: "discount usage limit reached"
2555
2618
  };
2556
2619
  }
2620
+ const effectiveValue = discount.discountType === "FLAT" ? Number(discount.value) * exchangeRate : Number(discount.value);
2557
2621
  const cartTotal = cartLines.reduce((s, l) => s + l.subtotal, 0);
2558
2622
  const tree = discountBuildTree(discount.rules ?? []);
2559
- if (tree.length === 0) return discountBuildUniversalResult(discount, cartLines);
2560
- const conditionsMet = tree.every((node) => discountEvaluateRule(node, cartLines, cartTotal));
2623
+ if (tree.length === 0) return discountBuildUniversalResult(discount, cartLines, effectiveValue);
2624
+ const conditionsMet = tree.every((node) => discountEvaluateRule(node, cartLines, cartTotal, exchangeRate));
2561
2625
  if (!conditionsMet) return {
2562
2626
  ...empty,
2563
2627
  reason: "conditions not met"
2564
2628
  };
2565
2629
  const rewardRules = discountCollectRewardRules(tree);
2566
- if (rewardRules.length === 0) return discountBuildUniversalResult(discount, cartLines);
2630
+ if (rewardRules.length === 0) return discountBuildUniversalResult(discount, cartLines, effectiveValue);
2567
2631
  const requiredBuyQty = discountExtractRequiredBuyQty(tree);
2568
2632
  const buyProductId = discountExtractBuyProductId(tree);
2569
2633
  let dealMultiplier = 1;
@@ -2581,7 +2645,7 @@ function evaluateDiscount(discount, cartLines) {
2581
2645
  rewardLines.push({
2582
2646
  productId: rewardProductId,
2583
2647
  quantity: dealMultiplier,
2584
- discountRate: Number(discount.value),
2648
+ discountRate: effectiveValue,
2585
2649
  discountType: discount.discountType
2586
2650
  });
2587
2651
  } else {
@@ -2590,7 +2654,7 @@ function evaluateDiscount(discount, cartLines) {
2590
2654
  rewardLines.push({
2591
2655
  productId: rewardProductId,
2592
2656
  quantity: rewardQty,
2593
- discountRate: Number(discount.value),
2657
+ discountRate: effectiveValue,
2594
2658
  discountType: discount.discountType
2595
2659
  });
2596
2660
  }
@@ -2601,8 +2665,9 @@ function evaluateDiscount(discount, cartLines) {
2601
2665
  };
2602
2666
  }
2603
2667
  chunkUSNT2KNT_cjs.__name(evaluateDiscount, "evaluateDiscount");
2604
- function applyDiscountToOrderLines(lines, evalResult, maxDiscountAmount) {
2668
+ function applyDiscountToOrderLines(lines, evalResult, maxDiscountAmount, exchangeRate = 1) {
2605
2669
  if (!evalResult.conditionsMet || evalResult.rewardLines.length === 0) return 0;
2670
+ const effectiveMaxDiscountAmount = maxDiscountAmount != null ? Number(maxDiscountAmount) * exchangeRate : null;
2606
2671
  let totalDiscountApplied = 0;
2607
2672
  for (const reward of evalResult.rewardLines) {
2608
2673
  const line = lines.find((l) => l.productId === reward.productId);
@@ -2619,8 +2684,8 @@ function applyDiscountToOrderLines(lines, evalResult, maxDiscountAmount) {
2619
2684
  line.subtotal = line.unitPrice * line.quantity;
2620
2685
  line.total = Math.max(0, line.subtotal - (line.discount ?? 0));
2621
2686
  }
2622
- if (maxDiscountAmount != null && totalDiscountApplied > maxDiscountAmount) {
2623
- const excess = totalDiscountApplied - maxDiscountAmount;
2687
+ if (effectiveMaxDiscountAmount != null && totalDiscountApplied > effectiveMaxDiscountAmount) {
2688
+ const excess = totalDiscountApplied - effectiveMaxDiscountAmount;
2624
2689
  for (let i = evalResult.rewardLines.length - 1; i >= 0; i--) {
2625
2690
  const reward = evalResult.rewardLines[i];
2626
2691
  const line = lines.find((l) => l.productId === reward.productId);
@@ -2630,7 +2695,7 @@ function applyDiscountToOrderLines(lines, evalResult, maxDiscountAmount) {
2630
2695
  line.total = Math.max(0, line.total + rollback);
2631
2696
  if (rollback > 0) break;
2632
2697
  }
2633
- totalDiscountApplied = maxDiscountAmount;
2698
+ totalDiscountApplied = effectiveMaxDiscountAmount;
2634
2699
  }
2635
2700
  return totalDiscountApplied;
2636
2701
  }
@@ -2736,7 +2801,9 @@ async function validateCoupon(dataSource, entityMap, couponCode, orderLines, cur
2736
2801
  unitPrice: l.unitPrice,
2737
2802
  subtotal: l.subtotal
2738
2803
  }));
2739
- const evalResult = evaluateDiscount(discountForEval, cartLines);
2804
+ const dCurrency = d.currency || "INR";
2805
+ const exchangeRate = await getExchangeRate(dataSource, entityMap, dCurrency, currency);
2806
+ const evalResult = evaluateDiscount(discountForEval, cartLines, exchangeRate);
2740
2807
  if (!evalResult.conditionsMet) {
2741
2808
  return {
2742
2809
  valid: false,
@@ -2746,7 +2813,7 @@ async function validateCoupon(dataSource, entityMap, couponCode, orderLines, cur
2746
2813
  const clonedLines = lines.map((l) => ({
2747
2814
  ...l
2748
2815
  }));
2749
- const calculatedDiscount = applyDiscountToOrderLines(clonedLines, evalResult, d.maxDiscountAmount);
2816
+ const calculatedDiscount = applyDiscountToOrderLines(clonedLines, evalResult, d.maxDiscountAmount, exchangeRate);
2750
2817
  const rewardProductIds = evalResult.rewardLines.map((r) => r.productId);
2751
2818
  return {
2752
2819
  valid: true,
@@ -3031,9 +3098,11 @@ async function calculateOrderTotalsFromLines(dataSource, entityMap, lineInputs,
3031
3098
  unitPrice: l.unitPrice,
3032
3099
  subtotal: l.subtotal
3033
3100
  }));
3034
- const evalResult = evaluateDiscount(discountForEval, cartLines);
3101
+ const dCurrency = discountRow.currency || "INR";
3102
+ const exchangeRate2 = await getExchangeRate(dataSource, entityMap, dCurrency, currency);
3103
+ const evalResult = evaluateDiscount(discountForEval, cartLines, exchangeRate2);
3035
3104
  if (evalResult.conditionsMet) {
3036
- const totalDiscountApplied = applyDiscountToOrderLines(lines, evalResult, discountRow.maxDiscountAmount);
3105
+ const totalDiscountApplied = applyDiscountToOrderLines(lines, evalResult, discountRow.maxDiscountAmount, exchangeRate2);
3037
3106
  orderDiscount += totalDiscountApplied;
3038
3107
  }
3039
3108
  }
@@ -3146,9 +3215,25 @@ async function calculateOrderTotals(dataSource, entityMap, itemsSummary, discoun
3146
3215
  unitPrice: l.unitPrice,
3147
3216
  subtotal: l.subtotal
3148
3217
  }));
3149
- const evalResult = evaluateDiscount(discountForEval, cartLines);
3218
+ const dCurrency = discountRow.currency || "INR";
3219
+ let storeCurrency = "INR";
3220
+ if (entityMap["configs"]) {
3221
+ try {
3222
+ const configRepo = dataSource.getRepository(entityMap["configs"]);
3223
+ const curr = await configRepo.findOne({
3224
+ where: {
3225
+ settings: "store",
3226
+ key: "currency"
3227
+ }
3228
+ });
3229
+ storeCurrency = curr?.value?.toUpperCase() ?? "INR";
3230
+ } catch {
3231
+ }
3232
+ }
3233
+ const exchangeRate = await getExchangeRate(dataSource, entityMap, dCurrency, storeCurrency);
3234
+ const evalResult = evaluateDiscount(discountForEval, cartLines, exchangeRate);
3150
3235
  if (evalResult.conditionsMet) {
3151
- const totalDiscountApplied = applyDiscountToOrderLines(lines, evalResult, discountRow.maxDiscountAmount);
3236
+ const totalDiscountApplied = applyDiscountToOrderLines(lines, evalResult, discountRow.maxDiscountAmount, exchangeRate);
3152
3237
  for (const line of lines) {
3153
3238
  if (!line.found || line.taxRate === 0) continue;
3154
3239
  const discountedAmount = line.subtotal - (line.discount ?? 0);
@@ -3564,6 +3649,12 @@ function createCrudHandler(dataSource, entityMap, options) {
3564
3649
  }
3565
3650
  const itemsSummary = parts.join(", ") || "\u2014";
3566
3651
  const { payments: _payments, ...orderWithoutPayments } = order;
3652
+ const rawPayStatus = String(orderPayments[0]?.status ?? "unpaid").toLowerCase();
3653
+ const orderStatus = String(order.status ?? "").toLowerCase();
3654
+ let paymentStatus2 = rawPayStatus;
3655
+ if (orderStatus === "cancelled" && rawPayStatus !== "paid" && rawPayStatus !== "captured" && rawPayStatus !== "refunded") {
3656
+ paymentStatus2 = "unpaid";
3657
+ }
3567
3658
  return {
3568
3659
  ...orderWithoutPayments,
3569
3660
  contact: contact ? {
@@ -3573,7 +3664,7 @@ function createCrudHandler(dataSource, entityMap, options) {
3573
3664
  phone: contact.phone
3574
3665
  } : null,
3575
3666
  itemsSummary,
3576
- paymentStatus: orderPayments[0]?.status ?? "unpaid"
3667
+ paymentStatus: paymentStatus2
3577
3668
  };
3578
3669
  }));
3579
3670
  return json({
@@ -4312,7 +4403,7 @@ function createCrudHandler(dataSource, entityMap, options) {
4312
4403
  });
4313
4404
  }
4314
4405
  }
4315
- const savedCustomer = await chunk3EOM4V2M_cjs.ensureCustomerRecord(dataSource, entityMap["customer"], {
4406
+ const savedCustomer = await chunk4U6DATGZ_cjs.ensureCustomerRecord(dataSource, entityMap["customer"], {
4316
4407
  name,
4317
4408
  email,
4318
4409
  phone,
@@ -5091,11 +5182,18 @@ function createCrudHandler(dataSource, entityMap, options) {
5091
5182
  await recordDiscountUsage2(dataSource, entityMap, created.id, orderDiscountId, persistBody.contactId, discount);
5092
5183
  }
5093
5184
  const orderIdForNotify = created.id;
5094
- void import('./emit-order-notification-trigger-NR3VN6C6.cjs').then(({ fireOrderNotificationTrigger }) => {
5185
+ const initialPayStatus = String(persistBody.paymentStatus ?? "unpaid").toLowerCase();
5186
+ void import('./emit-order-notification-trigger-TNEZOYEE.cjs').then(({ fireOrderNotificationTrigger }) => {
5095
5187
  fireOrderNotificationTrigger("order_placed", orderIdForNotify, {
5096
5188
  dataSource,
5097
5189
  entityMap
5098
5190
  });
5191
+ if (initialPayStatus === "paid" || initialPayStatus === "captured") {
5192
+ fireOrderNotificationTrigger("payment_success", orderIdForNotify, {
5193
+ dataSource,
5194
+ entityMap
5195
+ });
5196
+ }
5099
5197
  });
5100
5198
  }
5101
5199
  } catch (err) {
@@ -5458,6 +5556,9 @@ function createCrudByIdHandler(dataSource, entityMap, options) {
5458
5556
  "payments"
5459
5557
  ]
5460
5558
  });
5559
+ if (order) {
5560
+ await autoExpireOrderIfPaymentTimeExceeded(dataSource, entityMap, order);
5561
+ }
5461
5562
  const orderDenied = await vendorScopeAccessJson(order, scope2, resource);
5462
5563
  if (orderDenied) return orderDenied;
5463
5564
  const relatedOrders = await repo.find({
@@ -6559,6 +6660,43 @@ function createCrudByIdHandler(dataSource, entityMap, options) {
6559
6660
  await retireSoftDeletedUniquesFromBody(repo, updatePayload);
6560
6661
  try {
6561
6662
  await repo.update(numericId, updatePayload);
6663
+ if (resource === "payments" && updatePayload.status) {
6664
+ const updatedPay = await repo.findOne({
6665
+ where: {
6666
+ id: numericId
6667
+ }
6668
+ });
6669
+ const pOrder = updatedPay?.orderId;
6670
+ const newPayStatus = String(updatePayload.status).toLowerCase();
6671
+ if (pOrder && Number.isFinite(pOrder)) {
6672
+ if (newPayStatus === "paid" || newPayStatus === "captured") {
6673
+ if (entityMap.orders) {
6674
+ await dataSource.getRepository(entityMap.orders).update(pOrder, {
6675
+ status: "confirmed"
6676
+ });
6677
+ }
6678
+ void import('./emit-order-notification-trigger-TNEZOYEE.cjs').then(({ fireOrderNotificationTrigger }) => {
6679
+ fireOrderNotificationTrigger("order_placed", pOrder, {
6680
+ dataSource,
6681
+ entityMap
6682
+ });
6683
+ fireOrderNotificationTrigger("payment_success", pOrder, {
6684
+ dataSource,
6685
+ entityMap
6686
+ });
6687
+ }).catch(() => {
6688
+ });
6689
+ } else if (newPayStatus === "failed") {
6690
+ void import('./emit-order-notification-trigger-TNEZOYEE.cjs').then(({ fireOrderNotificationTrigger }) => {
6691
+ fireOrderNotificationTrigger("payment_failed", pOrder, {
6692
+ dataSource,
6693
+ entityMap
6694
+ });
6695
+ }).catch(() => {
6696
+ });
6697
+ }
6698
+ }
6699
+ }
6562
6700
  } catch (err) {
6563
6701
  if (resource === "events" && isSlugUniqueViolation(err)) {
6564
6702
  return json({
@@ -7242,7 +7380,7 @@ function createInviteAcceptHandler(config) {
7242
7380
  }
7243
7381
  const { userId, email, vendorId } = validation.target;
7244
7382
  if (entityMap.contacts) {
7245
- await chunk3EOM4V2M_cjs.linkUnclaimedContactToUser(dataSource, entityMap.contacts, userId, email);
7383
+ await chunk4U6DATGZ_cjs.linkUnclaimedContactToUser(dataSource, entityMap.contacts, userId, email);
7246
7384
  }
7247
7385
  if (beforeActivate) await beforeActivate(email, userId);
7248
7386
  const hashedPassword = await hashPassword(password);
@@ -8335,7 +8473,7 @@ function createVendorDashboardHandler(config) {
8335
8473
  if (pe) return pe;
8336
8474
  }
8337
8475
  const user = await getSessionUser();
8338
- if (!user || !chunk77NUXO6A_cjs.isVendorPortalUser(user)) {
8476
+ if (!user || !chunkJ7FMZK66_cjs.isVendorPortalUser(user)) {
8339
8477
  return json({
8340
8478
  error: "Forbidden"
8341
8479
  }, {
@@ -9113,7 +9251,9 @@ function createFormSaveHandlers(config) {
9113
9251
  "description",
9114
9252
  "campaign",
9115
9253
  "slug",
9116
- "published"
9254
+ "published",
9255
+ "enableTurnstile",
9256
+ "enable_turnstile"
9117
9257
  ]) {
9118
9258
  if (body[key] !== void 0) formRow[key] = body[key];
9119
9259
  }
@@ -9704,11 +9844,11 @@ function createUsersApiHandlers(config) {
9704
9844
  adminAccess
9705
9845
  }));
9706
9846
  if (entityMap.contacts) {
9707
- await chunk3EOM4V2M_cjs.linkUnclaimedContactToUser(dataSource, entityMap.contacts, newUser.id, newUser.email);
9847
+ await chunk4U6DATGZ_cjs.linkUnclaimedContactToUser(dataSource, entityMap.contacts, newUser.id, newUser.email);
9708
9848
  }
9709
9849
  if (entityMap.customer) {
9710
9850
  const phone = typeof body.phone === "string" && body.phone.trim() ? body.phone.trim() : null;
9711
- await chunk3EOM4V2M_cjs.ensureCustomerForUser(dataSource, entityMap.customer, {
9851
+ await chunk4U6DATGZ_cjs.ensureCustomerForUser(dataSource, entityMap.customer, {
9712
9852
  id: newUser.id,
9713
9853
  name: String(newUser.name ?? body.name),
9714
9854
  email: String(newUser.email),
@@ -10798,7 +10938,7 @@ function createChatHandlers(config) {
10798
10938
  const notifyEmailAgent = await findLlmAgentByScope(dataSource, entityMap, LLM_AGENT_SCOPE_EMAIL_INTENT_CHATBOT, {
10799
10939
  enabledOnly: false
10800
10940
  });
10801
- const emailTool = chunkHXLC56ZK_cjs.resolveChatEmailToolSettings(llmSettings, {
10941
+ const emailTool = chunkYSYX4GUD_cjs.resolveChatEmailToolSettings(llmSettings, {
10802
10942
  chatbotValidationRules: agentRow?.validationRules ?? null,
10803
10943
  notifyAgent: notifyEmailAgent ? {
10804
10944
  systemInstruction: notifyEmailAgent.systemInstruction,
@@ -10808,7 +10948,7 @@ function createChatHandlers(config) {
10808
10948
  const emailPlugin2 = cms.getPlugin("email");
10809
10949
  const convLeadSent = conv.leadEmailSentAt;
10810
10950
  const chatAgentFn = llm.chatAgent?.bind(llm);
10811
- console.info(chunkHXLC56ZK_cjs.CHAT_EMAIL_LOG, "pipeline check", {
10951
+ console.info(chunkYSYX4GUD_cjs.CHAT_EMAIL_LOG, "pipeline check", {
10812
10952
  conversationId,
10813
10953
  enabled: emailTool.enabled,
10814
10954
  intentCount: emailTool.intents.length,
@@ -10822,27 +10962,27 @@ function createChatHandlers(config) {
10822
10962
  mergedPromptIncludesNotify: Boolean(notifyEmailAgent?.systemInstruction?.trim())
10823
10963
  });
10824
10964
  if (!emailTool.enabled) {
10825
- console.info(chunkHXLC56ZK_cjs.CHAT_EMAIL_LOG, "pipeline skipped", {
10965
+ console.info(chunkYSYX4GUD_cjs.CHAT_EMAIL_LOG, "pipeline skipped", {
10826
10966
  conversationId,
10827
10967
  reason: "email_tool_disabled"
10828
10968
  });
10829
10969
  } else if (emailTool.intents.length === 0) {
10830
- console.info(chunkHXLC56ZK_cjs.CHAT_EMAIL_LOG, "pipeline skipped", {
10970
+ console.info(chunkYSYX4GUD_cjs.CHAT_EMAIL_LOG, "pipeline skipped", {
10831
10971
  conversationId,
10832
10972
  reason: "no_intents_configured"
10833
10973
  });
10834
10974
  } else if (!emailPlugin2) {
10835
- console.info(chunkHXLC56ZK_cjs.CHAT_EMAIL_LOG, "pipeline skipped", {
10975
+ console.info(chunkYSYX4GUD_cjs.CHAT_EMAIL_LOG, "pipeline skipped", {
10836
10976
  conversationId,
10837
10977
  reason: "email_plugin_missing"
10838
10978
  });
10839
10979
  } else if (!chatAgentFn) {
10840
- console.info(chunkHXLC56ZK_cjs.CHAT_EMAIL_LOG, "pipeline skipped", {
10980
+ console.info(chunkYSYX4GUD_cjs.CHAT_EMAIL_LOG, "pipeline skipped", {
10841
10981
  conversationId,
10842
10982
  reason: "llm_chat_agent_unavailable"
10843
10983
  });
10844
10984
  } else if (convLeadSent) {
10845
- console.info(chunkHXLC56ZK_cjs.CHAT_EMAIL_LOG, "pipeline skipped", {
10985
+ console.info(chunkYSYX4GUD_cjs.CHAT_EMAIL_LOG, "pipeline skipped", {
10846
10986
  conversationId,
10847
10987
  reason: "lead_email_already_sent",
10848
10988
  leadEmailSentAt: convLeadSent
@@ -10855,7 +10995,7 @@ function createChatHandlers(config) {
10855
10995
  }
10856
10996
  });
10857
10997
  if (!contactRow) {
10858
- console.warn(chunkHXLC56ZK_cjs.CHAT_EMAIL_LOG, "pipeline skipped", {
10998
+ console.warn(chunkYSYX4GUD_cjs.CHAT_EMAIL_LOG, "pipeline skipped", {
10859
10999
  conversationId,
10860
11000
  reason: "contact_not_found",
10861
11001
  contactId
@@ -10863,7 +11003,7 @@ function createChatHandlers(config) {
10863
11003
  } else {
10864
11004
  const c = contactRow;
10865
11005
  try {
10866
- const intent = await chunkHXLC56ZK_cjs.detectChatLeadIntent({
11006
+ const intent = await chunkYSYX4GUD_cjs.detectChatLeadIntent({
10867
11007
  chatAgent: chatAgentFn
10868
11008
  }, {
10869
11009
  settings: emailTool,
@@ -10877,15 +11017,15 @@ function createChatHandlers(config) {
10877
11017
  model: agentRow?.model?.trim() || notifyEmailAgent?.model?.trim() || void 0
10878
11018
  });
10879
11019
  if (!intent.intent || !intent.emailTo) {
10880
- console.info(chunkHXLC56ZK_cjs.CHAT_EMAIL_LOG, "no email sent", {
11020
+ console.info(chunkYSYX4GUD_cjs.CHAT_EMAIL_LOG, "no email sent", {
10881
11021
  conversationId,
10882
11022
  reason: intent.intent ? "missing_email_to" : "no_intent_match",
10883
11023
  intentLabel: intent.intentLabel,
10884
11024
  classifierReason: intent.reason
10885
11025
  });
10886
11026
  } else {
10887
- const intentRecipients = chunkHXLC56ZK_cjs.parseIntentRecipientEmails(intent.emailTo);
10888
- console.info(chunkHXLC56ZK_cjs.CHAT_EMAIL_LOG, "intent matched \u2014 sending", {
11027
+ const intentRecipients = chunkYSYX4GUD_cjs.parseIntentRecipientEmails(intent.emailTo);
11028
+ console.info(chunkYSYX4GUD_cjs.CHAT_EMAIL_LOG, "intent matched \u2014 sending", {
10889
11029
  conversationId,
10890
11030
  intent: intent.intent,
10891
11031
  emailTo: intent.emailTo,
@@ -10895,7 +11035,7 @@ function createChatHandlers(config) {
10895
11035
  const emailSettings = await loadSettingsGroupMap(dataSource, entityMap, "email");
10896
11036
  const brandingSettings = await loadSettingsGroupMap(dataSource, entityMap, "branding");
10897
11037
  const companyDetails = chunkBXYZDMTZ_cjs.mergeEmailLayoutCompanyDetails(brandingSettings, emailSettings);
10898
- const leadResult = await chunkHXLC56ZK_cjs.sendChatLeadEmail(cms, emailSettings, brandingSettings, {
11038
+ const leadResult = await chunkYSYX4GUD_cjs.sendChatLeadEmail(cms, emailSettings, brandingSettings, {
10899
11039
  contactName: String(c.name ?? "").trim() || "Visitor",
10900
11040
  contactEmail: String(c.email ?? "").trim(),
10901
11041
  contactPhone: c.phone ?? null,
@@ -10903,7 +11043,7 @@ function createChatHandlers(config) {
10903
11043
  latestMessage: message,
10904
11044
  intentCode: intent.intent,
10905
11045
  intentReason: intent.intentLabel || intent.reason,
10906
- transcript: chunkHXLC56ZK_cjs.buildTranscriptForLeadEmail(history, message),
11046
+ transcript: chunkYSYX4GUD_cjs.buildTranscriptForLeadEmail(history, message),
10907
11047
  companyDetails,
10908
11048
  recipients: intentRecipients.length > 0 ? intentRecipients : void 0
10909
11049
  });
@@ -10911,13 +11051,13 @@ function createChatHandlers(config) {
10911
11051
  await convRepo().update(conversationId, {
10912
11052
  leadEmailSentAt: /* @__PURE__ */ new Date()
10913
11053
  });
10914
- console.info(chunkHXLC56ZK_cjs.CHAT_EMAIL_LOG, "lead email recorded", {
11054
+ console.info(chunkYSYX4GUD_cjs.CHAT_EMAIL_LOG, "lead email recorded", {
10915
11055
  conversationId,
10916
11056
  sent: true,
10917
11057
  recipients: leadResult.recipients
10918
11058
  });
10919
11059
  } else {
10920
- console.warn(chunkHXLC56ZK_cjs.CHAT_EMAIL_LOG, "lead email not sent", {
11060
+ console.warn(chunkYSYX4GUD_cjs.CHAT_EMAIL_LOG, "lead email not sent", {
10921
11061
  conversationId,
10922
11062
  sent: false,
10923
11063
  error: leadResult.error ?? "unknown",
@@ -10926,7 +11066,7 @@ function createChatHandlers(config) {
10926
11066
  }
10927
11067
  }
10928
11068
  } catch (intentErr) {
10929
- console.warn(chunkHXLC56ZK_cjs.CHAT_EMAIL_LOG, "pipeline error", {
11069
+ console.warn(chunkYSYX4GUD_cjs.CHAT_EMAIL_LOG, "pipeline error", {
10930
11070
  conversationId,
10931
11071
  error: intentErr instanceof Error ? intentErr.message : String(intentErr)
10932
11072
  });
@@ -10943,7 +11083,7 @@ function createChatHandlers(config) {
10943
11083
  });
10944
11084
  if (agentRow && llm.chatAgent) {
10945
11085
  const fromAgent = llmAgentToChatAgentOptions(agentRow);
10946
- const systemPrompt = chunkHXLC56ZK_cjs.buildChatbotSystemPromptWithEmailTool(fromAgent.systemPrompt, parsedValidation.guardrailsForPrompt, emailTool);
11086
+ const systemPrompt = chunkYSYX4GUD_cjs.buildChatbotSystemPromptWithEmailTool(fromAgent.systemPrompt, parsedValidation.guardrailsForPrompt, emailTool);
10947
11087
  const res = await llm.chatAgent({
10948
11088
  ...fromAgent,
10949
11089
  systemPrompt: systemPrompt || void 0,
@@ -10964,7 +11104,7 @@ ${contextParts.join("\n\n")}` : "";
10964
11104
  agentRow.systemInstruction?.trim(),
10965
11105
  ragSystem
10966
11106
  ].filter(Boolean).join("\n\n");
10967
- systemContent = chunkHXLC56ZK_cjs.buildChatbotSystemPromptWithEmailTool(mergedBase || defaultSystem, parsedValidation.guardrailsForPrompt, emailTool) || defaultSystem;
11107
+ systemContent = chunkYSYX4GUD_cjs.buildChatbotSystemPromptWithEmailTool(mergedBase || defaultSystem, parsedValidation.guardrailsForPrompt, emailTool) || defaultSystem;
10968
11108
  } else {
10969
11109
  systemContent = ragSystem || defaultSystem;
10970
11110
  }
@@ -12219,7 +12359,7 @@ function createDeviceTokensHandlers(config) {
12219
12359
  const title = body.title?.trim() || "Test Push Notification";
12220
12360
  const msgBody = body.body?.trim() || "Firebase Push Notification setup is working!";
12221
12361
  if (!token || token === "validate" || token === "validate_only") {
12222
- const valRes = await chunkHXLC56ZK_cjs.validateFcmCredentials(dataSource, entityMap);
12362
+ const valRes = await chunkYSYX4GUD_cjs.validateFcmCredentials(dataSource, entityMap);
12223
12363
  if (!valRes.success) {
12224
12364
  return json({
12225
12365
  success: false,
@@ -12236,7 +12376,7 @@ function createDeviceTokensHandlers(config) {
12236
12376
  clientEmail: valRes.clientEmail
12237
12377
  });
12238
12378
  }
12239
- const res = await chunkHXLC56ZK_cjs.sendFcmPushNotification(dataSource, entityMap, {
12379
+ const res = await chunkYSYX4GUD_cjs.sendFcmPushNotification(dataSource, entityMap, {
12240
12380
  token,
12241
12381
  title,
12242
12382
  body: msgBody,
@@ -12790,7 +12930,7 @@ chunkUSNT2KNT_cjs.__name(findActiveRefundPolicyForVendor, "findActiveRefundPolic
12790
12930
  // src/api/admin-roles-handlers.ts
12791
12931
  function createAdminRolesHandlers(config) {
12792
12932
  const { dataSource, entityMap, json, getSessionUser } = config;
12793
- const baseEntities = chunk77NUXO6A_cjs.getPermissionableEntityKeys(entityMap);
12933
+ const baseEntities = chunkJ7FMZK66_cjs.getPermissionableEntityKeys(entityMap);
12794
12934
  const allowEntities = /* @__PURE__ */ new Set([
12795
12935
  ...baseEntities,
12796
12936
  "users"
@@ -12805,7 +12945,7 @@ function createAdminRolesHandlers(config) {
12805
12945
  }, {
12806
12946
  status: 401
12807
12947
  });
12808
- if (!chunk3EOM4V2M_cjs.canManageRoles(u) && !chunk77NUXO6A_cjs.canManageVendorRoles(u)) {
12948
+ if (!chunk4U6DATGZ_cjs.canManageRoles(u) && !chunkJ7FMZK66_cjs.canManageVendorRoles(u)) {
12809
12949
  return json({
12810
12950
  error: "Forbidden"
12811
12951
  }, {
@@ -12816,11 +12956,11 @@ function createAdminRolesHandlers(config) {
12816
12956
  }
12817
12957
  chunkUSNT2KNT_cjs.__name(gate, "gate");
12818
12958
  function isVendorRolesOnly(u) {
12819
- return chunk77NUXO6A_cjs.canManageVendorRoles(u) && !chunk3EOM4V2M_cjs.canManageRoles(u);
12959
+ return chunkJ7FMZK66_cjs.canManageVendorRoles(u) && !chunk4U6DATGZ_cjs.canManageRoles(u);
12820
12960
  }
12821
12961
  chunkUSNT2KNT_cjs.__name(isVendorRolesOnly, "isVendorRolesOnly");
12822
12962
  const vendorRoleEntities = [
12823
- ...chunk77NUXO6A_cjs.VENDOR_STORE_RBAC_ENTITIES,
12963
+ ...chunkJ7FMZK66_cjs.VENDOR_STORE_RBAC_ENTITIES,
12824
12964
  "dashboard",
12825
12965
  "settings"
12826
12966
  ].sort();
@@ -12977,7 +13117,7 @@ function createAdminRolesHandlers(config) {
12977
13117
  }, {
12978
13118
  status: 404
12979
13119
  });
12980
- if (chunk77NUXO6A_cjs.isSuperAdminGroupName(g.name) && !chunk77NUXO6A_cjs.isSuperAdminGroupName(name)) {
13120
+ if (chunkJ7FMZK66_cjs.isSuperAdminGroupName(g.name) && !chunkJ7FMZK66_cjs.isSuperAdminGroupName(name)) {
12981
13121
  return json({
12982
13122
  error: "Cannot rename the administrator group"
12983
13123
  }, {
@@ -13034,7 +13174,7 @@ function createAdminRolesHandlers(config) {
13034
13174
  }, {
13035
13175
  status: 404
13036
13176
  });
13037
- if (chunk77NUXO6A_cjs.isSuperAdminGroupName(g.name)) return json({
13177
+ if (chunkJ7FMZK66_cjs.isSuperAdminGroupName(g.name)) return json({
13038
13178
  error: "Cannot delete the administrator group"
13039
13179
  }, {
13040
13180
  status: 400
@@ -13231,7 +13371,7 @@ async function sendVendorOnboardEmails(input, deps) {
13231
13371
  getVendorEmails(deps)
13232
13372
  ]);
13233
13373
  const companyDetails = chunkBXYZDMTZ_cjs.mergeEmailLayoutCompanyDetails(branding, emailSettings);
13234
- const configuredNotify = chunkHXLC56ZK_cjs.parseEmailRecipientsFromConfig(emailSettings.salesTeamEmails ?? emailSettings.salesTeamEmail);
13374
+ const configuredNotify = chunkYSYX4GUD_cjs.parseEmailRecipientsFromConfig(emailSettings.salesTeamEmails ?? emailSettings.salesTeamEmail);
13235
13375
  const ownerEmail = input.ownerEmail?.trim() || "";
13236
13376
  const ownerEmailLower = ownerEmail.toLowerCase();
13237
13377
  const sendToOwner = input.sendToOwner !== false;
@@ -13265,7 +13405,7 @@ chunkUSNT2KNT_cjs.__name(sendVendorOnboardEmails, "sendVendorOnboardEmails");
13265
13405
 
13266
13406
  // src/lib/seed-vendor-roles.ts
13267
13407
  async function insertRolePermissions(exec, vendorRoleId, permissions) {
13268
- for (const entity of chunk77NUXO6A_cjs.VENDOR_RBAC_ENTITIES) {
13408
+ for (const entity of chunkJ7FMZK66_cjs.VENDOR_RBAC_ENTITIES) {
13269
13409
  const flags = permissions[entity];
13270
13410
  if (!flags) continue;
13271
13411
  await exec.query(`
@@ -13296,7 +13436,7 @@ async function seedVendorDefaultRoles(em, vendorId) {
13296
13436
  for (const r of existing) {
13297
13437
  roleIdsByName2[r.name] = Number(r.id);
13298
13438
  if (r.isOwnerRole) ownerRoleId2 = Number(r.id);
13299
- if (r.name === chunk77NUXO6A_cjs.VENDOR_VIEWER_ROLE_NAME) viewerRoleId2 = Number(r.id);
13439
+ if (r.name === chunkJ7FMZK66_cjs.VENDOR_VIEWER_ROLE_NAME) viewerRoleId2 = Number(r.id);
13300
13440
  }
13301
13441
  return {
13302
13442
  roleIdsByName: roleIdsByName2,
@@ -13307,7 +13447,7 @@ async function seedVendorDefaultRoles(em, vendorId) {
13307
13447
  const roleIdsByName = {};
13308
13448
  let ownerRoleId = 0;
13309
13449
  let viewerRoleId = 0;
13310
- for (const def of chunk77NUXO6A_cjs.DEFAULT_VENDOR_ROLE_DEFS) {
13450
+ for (const def of chunkJ7FMZK66_cjs.DEFAULT_VENDOR_ROLE_DEFS) {
13311
13451
  const inserted = await exec.query(`
13312
13452
  INSERT INTO "vendor_roles"
13313
13453
  ("vendorId", "name", "description", "isSystem", "isOwnerRole")
@@ -13324,7 +13464,7 @@ async function seedVendorDefaultRoles(em, vendorId) {
13324
13464
  if (!roleId) continue;
13325
13465
  roleIdsByName[def.name] = roleId;
13326
13466
  if (def.isOwnerRole) ownerRoleId = roleId;
13327
- if (def.name === chunk77NUXO6A_cjs.VENDOR_VIEWER_ROLE_NAME) viewerRoleId = roleId;
13467
+ if (def.name === chunkJ7FMZK66_cjs.VENDOR_VIEWER_ROLE_NAME) viewerRoleId = roleId;
13328
13468
  await insertRolePermissions(exec, roleId, def.permissions);
13329
13469
  }
13330
13470
  return {
@@ -13354,7 +13494,7 @@ async function backfillVendorUserRoleIds(em, vendorId, seeded) {
13354
13494
  vendorId
13355
13495
  ]);
13356
13496
  }
13357
- const viewerId = seeded.viewerRoleId || seeded.roleIdsByName[chunk77NUXO6A_cjs.VENDOR_VIEWER_ROLE_NAME];
13497
+ const viewerId = seeded.viewerRoleId || seeded.roleIdsByName[chunkJ7FMZK66_cjs.VENDOR_VIEWER_ROLE_NAME];
13358
13498
  if (viewerId) {
13359
13499
  await em.query(`
13360
13500
  UPDATE "vendor_users"
@@ -13380,7 +13520,7 @@ async function getDefaultStaffRoleIdForVendor(em, vendorId) {
13380
13520
  LIMIT 1
13381
13521
  `, [
13382
13522
  vendorId,
13383
- chunk77NUXO6A_cjs.VENDOR_VIEWER_ROLE_NAME
13523
+ chunkJ7FMZK66_cjs.VENDOR_VIEWER_ROLE_NAME
13384
13524
  ]);
13385
13525
  const id = rows[0]?.id;
13386
13526
  return id != null ? Number(id) : null;
@@ -13741,7 +13881,7 @@ function createVendorOnboardHandlers(config) {
13741
13881
  }, {
13742
13882
  status: 401
13743
13883
  });
13744
- if (!chunk77NUXO6A_cjs.isPlatformAdministrator(u)) return json({
13884
+ if (!chunkJ7FMZK66_cjs.isPlatformAdministrator(u)) return json({
13745
13885
  error: "Forbidden",
13746
13886
  reason: "admin_only"
13747
13887
  }, {
@@ -13751,7 +13891,7 @@ function createVendorOnboardHandlers(config) {
13751
13891
  }
13752
13892
  chunkUSNT2KNT_cjs.__name(gateAdmin, "gateAdmin");
13753
13893
  async function resolveActiveVendorId(u) {
13754
- const scope = chunk77NUXO6A_cjs.resolveVendorScopeFromSessionUser(u);
13894
+ const scope = chunkJ7FMZK66_cjs.resolveVendorScopeFromSessionUser(u);
13755
13895
  const candidates = [];
13756
13896
  if (scope.type === "vendor") candidates.push(scope.vendorId);
13757
13897
  if (scope.type === "all" || scope.type === "vendor") {
@@ -13805,7 +13945,7 @@ function createVendorOnboardHandlers(config) {
13805
13945
  }, {
13806
13946
  status: 401
13807
13947
  });
13808
- if (!chunk77NUXO6A_cjs.isVendorPortalUser(u) && !chunk77NUXO6A_cjs.isPlatformAdministrator(u)) {
13948
+ if (!chunkJ7FMZK66_cjs.isVendorPortalUser(u) && !chunkJ7FMZK66_cjs.isPlatformAdministrator(u)) {
13809
13949
  return json({
13810
13950
  error: "Forbidden"
13811
13951
  }, {
@@ -13833,7 +13973,7 @@ function createVendorOnboardHandlers(config) {
13833
13973
  }, {
13834
13974
  status: 401
13835
13975
  });
13836
- if (!chunk77NUXO6A_cjs.canManageVendorTeam(u)) return json({
13976
+ if (!chunkJ7FMZK66_cjs.canManageVendorTeam(u)) return json({
13837
13977
  error: "Forbidden"
13838
13978
  }, {
13839
13979
  status: 403
@@ -14051,7 +14191,7 @@ function createVendorOnboardHandlers(config) {
14051
14191
  await chunkOY2YTBMP_cjs.retireSoftDeletedUniqueValue(vendorRepo, "slug", slug);
14052
14192
  let ownerGroup = await groupRepo.findOne({
14053
14193
  where: {
14054
- name: chunk77NUXO6A_cjs.VENDOR_GROUP_NAME,
14194
+ name: chunkJ7FMZK66_cjs.VENDOR_GROUP_NAME,
14055
14195
  deleted: false
14056
14196
  }
14057
14197
  });
@@ -14066,12 +14206,12 @@ function createVendorOnboardHandlers(config) {
14066
14206
  if (!ownerGroup) {
14067
14207
  try {
14068
14208
  await groupRepo.save(groupRepo.create({
14069
- name: chunk77NUXO6A_cjs.VENDOR_GROUP_NAME,
14209
+ name: chunkJ7FMZK66_cjs.VENDOR_GROUP_NAME,
14070
14210
  deleted: false
14071
14211
  }));
14072
14212
  ownerGroup = await groupRepo.findOne({
14073
14213
  where: {
14074
- name: chunk77NUXO6A_cjs.VENDOR_GROUP_NAME,
14214
+ name: chunkJ7FMZK66_cjs.VENDOR_GROUP_NAME,
14075
14215
  deleted: false
14076
14216
  }
14077
14217
  });
@@ -14188,7 +14328,7 @@ function createVendorOnboardHandlers(config) {
14188
14328
  }
14189
14329
  if (entityMap.customer) {
14190
14330
  try {
14191
- await chunk3EOM4V2M_cjs.ensureCustomerForUser(em, entityMap.customer, {
14331
+ await chunk4U6DATGZ_cjs.ensureCustomerForUser(em, entityMap.customer, {
14192
14332
  id: newUser.id,
14193
14333
  name: userName,
14194
14334
  email: userEmail,
@@ -14688,7 +14828,7 @@ function createVendorOnboardHandlers(config) {
14688
14828
  if (!groupId) {
14689
14829
  const g = await groupRepo.findOne({
14690
14830
  where: {
14691
- name: chunk77NUXO6A_cjs.VENDOR_GROUP_NAME,
14831
+ name: chunkJ7FMZK66_cjs.VENDOR_GROUP_NAME,
14692
14832
  deleted: false
14693
14833
  }
14694
14834
  }) ?? await groupRepo.findOne({
@@ -14788,7 +14928,7 @@ function createVendorOnboardHandlers(config) {
14788
14928
  }
14789
14929
  if (entityMap.customer) {
14790
14930
  try {
14791
- await chunk3EOM4V2M_cjs.ensureCustomerForUser(em, entityMap.customer, {
14931
+ await chunk4U6DATGZ_cjs.ensureCustomerForUser(em, entityMap.customer, {
14792
14932
  id: newUser.id,
14793
14933
  name: userName,
14794
14934
  email: userEmail,
@@ -15325,10 +15465,10 @@ chunkUSNT2KNT_cjs.__name(createVendorOnboardHandlers, "createVendorOnboardHandle
15325
15465
  function createVendorRolesHandlers(config) {
15326
15466
  const { dataSource, entityMap, json, getSessionUser } = config;
15327
15467
  const vendorRoleEntities = [
15328
- ...chunk77NUXO6A_cjs.VENDOR_RBAC_ENTITIES
15468
+ ...chunkJ7FMZK66_cjs.VENDOR_RBAC_ENTITIES
15329
15469
  ].sort();
15330
15470
  async function resolveActiveVendorId(u) {
15331
- const scope = chunk77NUXO6A_cjs.resolveVendorScopeFromSessionUser(u);
15471
+ const scope = chunkJ7FMZK66_cjs.resolveVendorScopeFromSessionUser(u);
15332
15472
  if (scope.type === "vendor") return scope.vendorId;
15333
15473
  if (scope.type === "all") {
15334
15474
  const id = u.activeVendorId ?? u.vendorIds?.[0];
@@ -15344,7 +15484,7 @@ function createVendorRolesHandlers(config) {
15344
15484
  }, {
15345
15485
  status: 401
15346
15486
  });
15347
- if (!chunk77NUXO6A_cjs.canManageVendorRoles(u)) return json({
15487
+ if (!chunkJ7FMZK66_cjs.canManageVendorRoles(u)) return json({
15348
15488
  error: "Forbidden"
15349
15489
  }, {
15350
15490
  status: 403
@@ -17009,6 +17149,7 @@ exports.Form = class Form {
17009
17149
  campaign;
17010
17150
  slug;
17011
17151
  published;
17152
+ enableTurnstile;
17012
17153
  createdAt;
17013
17154
  updatedAt;
17014
17155
  deletedAt;
@@ -17051,6 +17192,14 @@ _ts_decorate14([
17051
17192
  }),
17052
17193
  _ts_metadata14("design:type", Boolean)
17053
17194
  ], exports.Form.prototype, "published", void 0);
17195
+ _ts_decorate14([
17196
+ typeorm.Column("boolean", {
17197
+ default: false,
17198
+ name: "enable_turnstile",
17199
+ nullable: true
17200
+ }),
17201
+ _ts_metadata14("design:type", Boolean)
17202
+ ], exports.Form.prototype, "enableTurnstile", void 0);
17054
17203
  _ts_decorate14([
17055
17204
  typeorm.Column({
17056
17205
  type: "timestamp",
@@ -27800,16 +27949,16 @@ function whatsappPlugin(config = {}) {
27800
27949
  db = await getWhatsAppSettings?.() ?? {};
27801
27950
  } catch {
27802
27951
  }
27803
- if (!chunkHXLC56ZK_cjs.isWhatsAppPluginEnabled(db)) {
27952
+ if (!chunkYSYX4GUD_cjs.isWhatsAppPluginEnabled(db)) {
27804
27953
  context.logger.warn("WhatsApp plugin skipped: disabled in Plugins \u2192 WhatsApp");
27805
27954
  return null;
27806
27955
  }
27807
- const merged = chunkHXLC56ZK_cjs.mergeWhatsAppConfigLayers(env, db, staticRest);
27808
- if (!getWhatsAppSettings && !chunkHXLC56ZK_cjs.whatsAppConfigured(merged)) {
27956
+ const merged = chunkYSYX4GUD_cjs.mergeWhatsAppConfigLayers(env, db, staticRest);
27957
+ if (!getWhatsAppSettings && !chunkYSYX4GUD_cjs.whatsAppConfigured(merged)) {
27809
27958
  context.logger.warn("WhatsApp plugin skipped: set WHATSAPP_ACCESS_TOKEN and WHATSAPP_PHONE_NUMBER_ID, or pass getWhatsAppSettings");
27810
27959
  return null;
27811
27960
  }
27812
- const svc = new chunkHXLC56ZK_cjs.WhatsAppService(env, staticRest, getWhatsAppSettings, getMessageTemplateRow);
27961
+ const svc = new chunkYSYX4GUD_cjs.WhatsAppService(env, staticRest, getWhatsAppSettings, getMessageTemplateRow);
27813
27962
  return {
27814
27963
  send: /* @__PURE__ */ chunkUSNT2KNT_cjs.__name((opts) => svc.send(opts), "send")
27815
27964
  };
@@ -27886,7 +28035,7 @@ function registerMessagingQueueProcessors(cms, entityMap) {
27886
28035
  getDataSource: /* @__PURE__ */ chunkUSNT2KNT_cjs.__name(async () => cms.dataSource, "getDataSource"),
27887
28036
  entityMap
27888
28037
  });
27889
- chunkHXLC56ZK_cjs.registerWhatsAppQueueProcessor(cms);
28038
+ chunkYSYX4GUD_cjs.registerWhatsAppQueueProcessor(cms);
27890
28039
  }
27891
28040
  chunkUSNT2KNT_cjs.__name(registerMessagingQueueProcessors, "registerMessagingQueueProcessors");
27892
28041
  async function ensureMessagingPluginsOnCms(base, options) {
@@ -27915,7 +28064,7 @@ async function ensureMessagingPluginsOnCms(base, options) {
27915
28064
  }
27916
28065
  if (!cms.getPlugin("email")) {
27917
28066
  try {
27918
- const instance = await chunkHXLC56ZK_cjs.emailPlugin({
28067
+ const instance = await chunkYSYX4GUD_cjs.emailPlugin({
27919
28068
  type: "SMTP",
27920
28069
  from: config.SMTP_FROM ?? "no-reply@localhost",
27921
28070
  to: config.SMTP_TO ?? ""
@@ -27956,7 +28105,7 @@ function messagingPlugins(options) {
27956
28105
  const config = options.config ?? (typeof process !== "undefined" ? process.env : {});
27957
28106
  return [
27958
28107
  queuePlugin(),
27959
- chunkHXLC56ZK_cjs.emailPlugin({
28108
+ chunkYSYX4GUD_cjs.emailPlugin({
27960
28109
  type: "SMTP",
27961
28110
  from: config.SMTP_FROM ?? "no-reply@localhost",
27962
28111
  to: config.SMTP_TO ?? ""
@@ -28090,7 +28239,7 @@ function createCmsApiHandler(config) {
28090
28239
  } : void 0;
28091
28240
  const entityMap = withLlmKnowledgeEntityFallbacks(rawEntityMap);
28092
28241
  if (getCms) {
28093
- chunkHXLC56ZK_cjs.initWhatsappTriggerDispatcher({
28242
+ chunkYSYX4GUD_cjs.initWhatsappTriggerDispatcher({
28094
28243
  dataSource,
28095
28244
  entityMap,
28096
28245
  getCms
@@ -28103,7 +28252,7 @@ function createCmsApiHandler(config) {
28103
28252
  ] : baseCrudResources;
28104
28253
  const requireEntityPermissionEffective = /* @__PURE__ */ chunkUSNT2KNT_cjs.__name(async (_req, entity, action) => {
28105
28254
  if (!resolveSessionUser) {
28106
- chunk77NUXO6A_cjs.logRbac("requireEntityPermission: getSessionUser not passed \u2014 vendor store APIs may 403", {
28255
+ chunkJ7FMZK66_cjs.logRbac("requireEntityPermission: getSessionUser not passed \u2014 vendor store APIs may 403", {
28107
28256
  entity,
28108
28257
  action,
28109
28258
  hint: "Pass getSessionUser: auth.getAuthenticatedUser from createCmsAuthBundle()"
@@ -28113,7 +28262,7 @@ function createCmsApiHandler(config) {
28113
28262
  const raw = await resolveSessionUser();
28114
28263
  const u = await hydrateVendorSessionUser(dataSource, raw);
28115
28264
  if (!u?.email) {
28116
- chunk77NUXO6A_cjs.logRbac("requireEntityPermission: no session user", {
28265
+ chunkJ7FMZK66_cjs.logRbac("requireEntityPermission: no session user", {
28117
28266
  entity,
28118
28267
  action
28119
28268
  });
@@ -28123,13 +28272,13 @@ function createCmsApiHandler(config) {
28123
28272
  status: 401
28124
28273
  });
28125
28274
  }
28126
- const allowed = chunk3EOM4V2M_cjs.sessionHasEntityAccess(u, entity, action);
28127
- await chunk77NUXO6A_cjs.logEntityAccessDecision(dataSource, "cmsApi.requireEntityPermission", u, entity, action, {
28275
+ const allowed = chunk4U6DATGZ_cjs.sessionHasEntityAccess(u, entity, action);
28276
+ await chunkJ7FMZK66_cjs.logEntityAccessDecision(dataSource, "cmsApi.requireEntityPermission", u, entity, action, {
28128
28277
  allowed,
28129
28278
  resolvePath: "hydrated_session"
28130
28279
  });
28131
28280
  if (allowed) return null;
28132
- const { reason } = chunk77NUXO6A_cjs.explainSessionEntityAccess(u, entity, action);
28281
+ const { reason } = chunkJ7FMZK66_cjs.explainSessionEntityAccess(u, entity, action);
28133
28282
  return config.json({
28134
28283
  error: "Forbidden",
28135
28284
  entity,
@@ -28140,7 +28289,7 @@ function createCmsApiHandler(config) {
28140
28289
  });
28141
28290
  }
28142
28291
  if (userRequireEntityPermission) {
28143
- chunk77NUXO6A_cjs.logRbac("requireEntityPermission: using app callback only (no getSessionUser)", {
28292
+ chunkJ7FMZK66_cjs.logRbac("requireEntityPermission: using app callback only (no getSessionUser)", {
28144
28293
  entity,
28145
28294
  action
28146
28295
  });
@@ -28227,10 +28376,10 @@ function createCmsApiHandler(config) {
28227
28376
  getVendorScope: /* @__PURE__ */ chunkUSNT2KNT_cjs.__name(async () => {
28228
28377
  const multiVendorEnabled = await checkMultiVendorEnabled(dataSource);
28229
28378
  if (!multiVendorEnabled) {
28230
- return chunk77NUXO6A_cjs.resolveDisabledMultiVendorScope(dataSource);
28379
+ return chunkJ7FMZK66_cjs.resolveDisabledMultiVendorScope(dataSource);
28231
28380
  }
28232
28381
  const u = await hydrateVendorSessionUser(dataSource, await resolveSessionUser());
28233
- return chunk77NUXO6A_cjs.resolveVendorScopeFromSessionUser(u ?? null);
28382
+ return chunkJ7FMZK66_cjs.resolveVendorScopeFromSessionUser(u ?? null);
28234
28383
  }, "getVendorScope"),
28235
28384
  getHydratedSessionUser: /* @__PURE__ */ chunkUSNT2KNT_cjs.__name(async () => {
28236
28385
  const u = await hydrateVendorSessionUser(dataSource, await resolveSessionUser());
@@ -29188,7 +29337,7 @@ function createCmsApiHandler(config) {
29188
29337
  }
29189
29338
  if (path2[0] === "settings" && path2.length === 2 && settingsHandlers) {
29190
29339
  const group = path2[1];
29191
- const isPublic = group === "multi_vendor" || settingsConfig?.publicGetGroups?.includes(group);
29340
+ const isPublic = group === "multi_vendor" || group === "turnstile" || group === "auth_providers" || settingsConfig?.publicGetGroups?.includes(group);
29192
29341
  if (m === "GET") {
29193
29342
  if (!isPublic) {
29194
29343
  const a = await config.requireAuth(req);
@@ -29564,7 +29713,7 @@ function createCmsApiHandler(config) {
29564
29713
  let vendorId = null;
29565
29714
  if (resolveSessionUser) {
29566
29715
  const u = await hydrateVendorSessionUser(dataSource, await resolveSessionUser());
29567
- const scope = chunk77NUXO6A_cjs.resolveVendorScopeFromSessionUser(u ?? null);
29716
+ const scope = chunkJ7FMZK66_cjs.resolveVendorScopeFromSessionUser(u ?? null);
29568
29717
  if (scope.type === "vendor") vendorId = scope.vendorId;
29569
29718
  }
29570
29719
  const result = await validateCoupon(dataSource, entityMap, couponCode, orderLinesNorm, currency, contactId, isAutomatic, discountId ?? void 0, vendorId);
@@ -29647,7 +29796,7 @@ function createCmsApiHandler(config) {
29647
29796
  let vendorId = null;
29648
29797
  if (resolveSessionUser) {
29649
29798
  const u = await hydrateVendorSessionUser(dataSource, await resolveSessionUser());
29650
- const scope = chunk77NUXO6A_cjs.resolveVendorScopeFromSessionUser(u ?? null);
29799
+ const scope = chunkJ7FMZK66_cjs.resolveVendorScopeFromSessionUser(u ?? null);
29651
29800
  if (scope.type === "vendor") vendorId = scope.vendorId;
29652
29801
  }
29653
29802
  const orderLinesNorm = normalizeOrderLinesInput(body?.orderLines);
@@ -29846,14 +29995,21 @@ function createCmsApiHandler(config) {
29846
29995
  body = {};
29847
29996
  }
29848
29997
  const triggerKey = String(body.triggerKey ?? "order_placed").trim() || "order_placed";
29849
- if (triggerKey !== "order_placed" && triggerKey !== "order_cancelled") {
29998
+ const validTriggers = [
29999
+ "order_placed",
30000
+ "order_cancelled",
30001
+ "payment_success",
30002
+ "payment_failed",
30003
+ "payment_refund_initiated"
30004
+ ];
30005
+ if (!validTriggers.includes(triggerKey)) {
29850
30006
  return config.json({
29851
- error: "Invalid triggerKey; use order_placed or order_cancelled"
30007
+ error: `Invalid triggerKey; use one of: ${validTriggers.join(", ")}`
29852
30008
  }, {
29853
30009
  status: 400
29854
30010
  });
29855
30011
  }
29856
- const { resendOrderNotification } = await import('./order-notification-dispatcher-2FCZFZUD.cjs');
30012
+ const { resendOrderNotification } = await import('./order-notification-dispatcher-KJVGLK5E.cjs');
29857
30013
  const result = await resendOrderNotification(triggerKey, orderId, {
29858
30014
  dataSource,
29859
30015
  entityMap,
@@ -29875,11 +30031,9 @@ function createCmsApiHandler(config) {
29875
30031
  if (path2[0] === "orders" && path2.length === 3 && path2[2] === "cancel" && m === "POST") {
29876
30032
  const a = await config.requireAuth(req);
29877
30033
  if (a) return a;
29878
- const pe = await requireEntityPermissionEffective(req, "orders", "update");
29879
- if (pe) return pe;
29880
- const orderId = Number(path2[1]);
29881
- if (!Number.isFinite(orderId)) return config.json({
29882
- error: "Invalid id"
30034
+ const orderId = parseInt(path2[1], 10);
30035
+ if (Number.isNaN(orderId)) return config.json({
30036
+ error: "Invalid order ID"
29883
30037
  }, {
29884
30038
  status: 400
29885
30039
  });
@@ -29896,9 +30050,10 @@ function createCmsApiHandler(config) {
29896
30050
  status: 404
29897
30051
  });
29898
30052
  const o = order;
29899
- if (o.status !== "confirmed" && o.status !== "completed") {
30053
+ const currentStatus = (o.status || "").toLowerCase();
30054
+ if (currentStatus === "cancelled") {
29900
30055
  return config.json({
29901
- error: "Only confirmed or completed orders can be cancelled"
30056
+ error: "Order is already cancelled"
29902
30057
  }, {
29903
30058
  status: 400
29904
30059
  });
@@ -29921,7 +30076,7 @@ function createCmsApiHandler(config) {
29921
30076
  }
29922
30077
  });
29923
30078
  if (payment) {
29924
- paymentStatus = String(payment.status ?? "unpaid");
30079
+ paymentStatus = String(payment.status ?? "unpaid").toLowerCase();
29925
30080
  paymentId = Number(payment.id);
29926
30081
  }
29927
30082
  }
@@ -29953,13 +30108,26 @@ function createCmsApiHandler(config) {
29953
30108
  status: "cancelled"
29954
30109
  });
29955
30110
  const fireOrderCancelledNotification = /* @__PURE__ */ chunkUSNT2KNT_cjs.__name((refundAmount) => {
29956
- void import('./emit-order-notification-trigger-NR3VN6C6.cjs').then(({ fireOrderNotificationTrigger }) => {
30111
+ void import('./emit-order-notification-trigger-TNEZOYEE.cjs').then(({ fireOrderNotificationTrigger }) => {
29957
30112
  fireOrderNotificationTrigger("order_cancelled", orderId, {
29958
30113
  dataSource,
29959
30114
  entityMap
29960
30115
  }, refundAmount != null && refundAmount > 0 ? {
29961
30116
  refundAmount
29962
30117
  } : void 0);
30118
+ if (paymentStatus === "paid" || paymentStatus === "captured") {
30119
+ fireOrderNotificationTrigger("payment_refund_initiated", orderId, {
30120
+ dataSource,
30121
+ entityMap
30122
+ }, refundAmount != null && refundAmount > 0 ? {
30123
+ refundAmount
30124
+ } : void 0);
30125
+ } else {
30126
+ fireOrderNotificationTrigger("payment_failed", orderId, {
30127
+ dataSource,
30128
+ entityMap
30129
+ });
30130
+ }
29963
30131
  });
29964
30132
  }, "fireOrderCancelledNotification");
29965
30133
  if (paymentStatus === "paid" && entityMap.payments && paymentId) {
@@ -30285,7 +30453,7 @@ function createCmsApiHandler(config) {
30285
30453
  if (resolveSessionUser) {
30286
30454
  const raw = await resolveSessionUser();
30287
30455
  const u = await hydrateVendorSessionUser(dataSource, raw);
30288
- const scope = chunk77NUXO6A_cjs.resolveVendorScopeFromSessionUser(u ?? null);
30456
+ const scope = chunkJ7FMZK66_cjs.resolveVendorScopeFromSessionUser(u ?? null);
30289
30457
  if (scope.type === "vendor") {
30290
30458
  scopedVendorIds = scope.vendorIds;
30291
30459
  }
@@ -30985,12 +31153,23 @@ function createStorefrontApiHandler(config) {
30985
31153
  const otpFlags = config.otpFlags;
30986
31154
  const otpPepper = config.otpPepper;
30987
31155
  const defaultPhoneCc = config.defaultPhoneCountryCode;
30988
- function fireOrderPlacedNotification(orderId) {
30989
- void import('./emit-order-notification-trigger-NR3VN6C6.cjs').then(({ fireOrderNotificationTrigger }) => {
31156
+ function fireOrderPlacedNotification(orderId, isPaid) {
31157
+ void import('./emit-order-notification-trigger-TNEZOYEE.cjs').then(({ fireOrderNotificationTrigger }) => {
30990
31158
  fireOrderNotificationTrigger("order_placed", orderId, {
30991
31159
  dataSource,
30992
31160
  entityMap
30993
31161
  });
31162
+ if (isPaid) {
31163
+ fireOrderNotificationTrigger("payment_success", orderId, {
31164
+ dataSource,
31165
+ entityMap
31166
+ });
31167
+ } else {
31168
+ fireOrderNotificationTrigger("payment_failed", orderId, {
31169
+ dataSource,
31170
+ entityMap
31171
+ });
31172
+ }
30994
31173
  }).catch((err) => console.error("[notification-triggers] import failed", err));
30995
31174
  }
30996
31175
  chunkUSNT2KNT_cjs.__name(fireOrderPlacedNotification, "fireOrderPlacedNotification");
@@ -32833,10 +33012,10 @@ function createStorefrontApiHandler(config) {
32833
33012
  adminAccess: false
32834
33013
  }));
32835
33014
  const userId = newUser.id;
32836
- await chunk3EOM4V2M_cjs.linkUnclaimedContactToUser(dataSource, entityMap.contacts, userId, email);
33015
+ await chunk4U6DATGZ_cjs.linkUnclaimedContactToUser(dataSource, entityMap.contacts, userId, email);
32837
33016
  if (entityMap.customer) {
32838
33017
  const phone = typeof b.phone === "string" && b.phone.trim() ? String(b.phone).trim() : null;
32839
- await chunk3EOM4V2M_cjs.ensureCustomerForUser(dataSource, entityMap.customer, {
33018
+ await chunk4U6DATGZ_cjs.ensureCustomerForUser(dataSource, entityMap.customer, {
32840
33019
  id: userId,
32841
33020
  name,
32842
33021
  email,
@@ -32894,6 +33073,23 @@ function createStorefrontApiHandler(config) {
32894
33073
  });
32895
33074
  return json(body);
32896
33075
  }
33076
+ if (path2[0] === "cart" && path2.length === 1 && method === "DELETE") {
33077
+ const { cart, err } = await getOrCreateCart(req);
33078
+ if (err) return err;
33079
+ const cartId = cart?.id;
33080
+ if (cartId && Number.isFinite(cartId) && cartId > 0) {
33081
+ await cartItemRepo().delete({
33082
+ cartId
33083
+ });
33084
+ await cartRepo().update(cartId, {
33085
+ updatedAt: /* @__PURE__ */ new Date()
33086
+ });
33087
+ }
33088
+ return json({
33089
+ ok: true,
33090
+ message: "Cart cleared"
33091
+ });
33092
+ }
32897
33093
  if (path2[0] === "cart" && path2[1] === "items" && path2.length === 2 && method === "POST") {
32898
33094
  const body = await req.json().catch(() => ({}));
32899
33095
  const capCart = await assertCaptchaOk(getCms, body, req, json);
@@ -33413,7 +33609,8 @@ function createStorefrontApiHandler(config) {
33413
33609
  total: prepOrd.orderTotal,
33414
33610
  currency: cart.currency || "INR",
33415
33611
  metadata: {
33416
- cartId
33612
+ cartId,
33613
+ paymentExpiresAt: new Date(Date.now() + 10 * 60 * 1e3).toISOString()
33417
33614
  }
33418
33615
  }));
33419
33616
  const oid = ord.id;
@@ -33486,7 +33683,11 @@ function createStorefrontApiHandler(config) {
33486
33683
  tax: prepChk.orderTax,
33487
33684
  discount: 0,
33488
33685
  total: prepChk.orderTotal,
33489
- currency: cart.currency || "INR"
33686
+ currency: cart.currency || "INR",
33687
+ metadata: {
33688
+ cartId: cart.id,
33689
+ paymentExpiresAt: new Date(Date.now() + 10 * 60 * 1e3).toISOString()
33690
+ }
33490
33691
  }));
33491
33692
  const oid = ord.id;
33492
33693
  await orderRepo().update(oid, {
@@ -33732,6 +33933,7 @@ function createStorefrontApiHandler(config) {
33732
33933
  status: 404
33733
33934
  });
33734
33935
  const o = order;
33936
+ await autoExpireOrderIfPaymentTimeExceeded(dataSource, entityMap, o);
33735
33937
  const lines = (o.items || []).map((line) => {
33736
33938
  const p = line.product;
33737
33939
  return {
@@ -33792,6 +33994,87 @@ function createStorefrontApiHandler(config) {
33792
33994
  fulfillmentPreview: fulfillmentPreview || void 0
33793
33995
  });
33794
33996
  }
33997
+ if (path2[0] === "orders" && path2.length === 3 && path2[2] === "cancel" && method === "POST") {
33998
+ const orderId = parseInt(path2[1], 10);
33999
+ if (!Number.isFinite(orderId)) return json({
34000
+ error: "Invalid order id"
34001
+ }, {
34002
+ status: 400
34003
+ });
34004
+ const order = await orderRepo().findOne({
34005
+ where: {
34006
+ id: orderId,
34007
+ deleted: false
34008
+ }
34009
+ });
34010
+ if (!order) return json({
34011
+ error: "Not found"
34012
+ }, {
34013
+ status: 404
34014
+ });
34015
+ const o = order;
34016
+ const status = String(o.status || "").toLowerCase();
34017
+ if (status === "pending") {
34018
+ const meta = typeof o.metadata === "object" && o.metadata ? o.metadata : {};
34019
+ const updatedMeta = {
34020
+ ...meta,
34021
+ cancelReason: "Cancelled by user during payment window"
34022
+ };
34023
+ await orderRepo().update(orderId, {
34024
+ status: "cancelled",
34025
+ metadata: updatedMeta
34026
+ });
34027
+ try {
34028
+ if (entityMap.payments) {
34029
+ const payRepo = dataSource.getRepository(entityMap.payments);
34030
+ const pendingPayment = await payRepo.findOne({
34031
+ where: {
34032
+ orderId,
34033
+ status: "pending"
34034
+ }
34035
+ });
34036
+ if (pendingPayment) {
34037
+ await payRepo.update(pendingPayment.id, {
34038
+ status: "unpaid"
34039
+ });
34040
+ }
34041
+ }
34042
+ } catch {
34043
+ }
34044
+ try {
34045
+ const { cart } = await getOrCreateCart(req);
34046
+ const cartId = cart?.id;
34047
+ if (cartId && Number.isFinite(cartId) && cartId > 0) {
34048
+ await cartItemRepo().delete({
34049
+ cartId
34050
+ });
34051
+ await cartRepo().update(cartId, {
34052
+ updatedAt: /* @__PURE__ */ new Date()
34053
+ });
34054
+ }
34055
+ } catch {
34056
+ }
34057
+ try {
34058
+ void import('./emit-order-notification-trigger-TNEZOYEE.cjs').then(({ fireOrderNotificationTrigger }) => {
34059
+ fireOrderNotificationTrigger("order_cancelled", orderId, {
34060
+ dataSource,
34061
+ entityMap
34062
+ });
34063
+ fireOrderNotificationTrigger("payment_failed", orderId, {
34064
+ dataSource,
34065
+ entityMap
34066
+ });
34067
+ }).catch(() => {
34068
+ });
34069
+ } catch {
34070
+ }
34071
+ }
34072
+ return json({
34073
+ ok: true,
34074
+ orderId,
34075
+ status: "cancelled"
34076
+ });
34077
+ }
33795
34078
  return json({
33796
34079
  error: "Not found"
33797
34080
  }, {
@@ -33831,6 +34114,7 @@ exports.assertCaptchaOk = assertCaptchaOk;
33831
34114
  exports.assertContactAllowedForVendorOrder = assertContactAllowedForVendorOrder;
33832
34115
  exports.assertEventApprovalUpdate = assertEventApprovalUpdate;
33833
34116
  exports.assertProductApprovalUpdate = assertProductApprovalUpdate;
34117
+ exports.autoExpireOrderIfPaymentTimeExceeded = autoExpireOrderIfPaymentTimeExceeded;
33834
34118
  exports.buildBlogMetadataUserPrompt = buildBlogMetadataUserPrompt;
33835
34119
  exports.buildCronFromSchedule = buildCronFromSchedule;
33836
34120
  exports.buildRssUserPromptFromFeeds = buildRssUserPromptFromFeeds;