@infuro/cms-core 1.0.59 → 1.0.61

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 (33) hide show
  1. package/dist/admin.cjs +1020 -83
  2. package/dist/admin.js +1021 -84
  3. package/dist/api.cjs +38 -38
  4. package/dist/api.js +5 -5
  5. package/dist/auth.cjs +51 -51
  6. package/dist/auth.js +3 -3
  7. package/dist/{chunk-3EOM4V2M.cjs → chunk-4U6DATGZ.cjs} +7 -7
  8. package/dist/{chunk-BNKZNLEX.js → chunk-6DBDJ4VD.js} +2 -2
  9. package/dist/{chunk-UQWZUZ5X.cjs → chunk-73WVHINE.cjs} +30 -6
  10. package/dist/{chunk-UCKN4BBY.cjs → chunk-77I3KS7V.cjs} +4 -1
  11. package/dist/{chunk-MCCA7WLQ.cjs → chunk-CNAHVRRU.cjs} +533 -167
  12. package/dist/{chunk-77NUXO6A.cjs → chunk-J7FMZK66.cjs} +10 -2
  13. package/dist/{chunk-BC22I7C7.cjs → chunk-KM2I6AFP.cjs} +9 -9
  14. package/dist/{chunk-JIWUVQ6B.js → chunk-MVHDC3XF.js} +10 -2
  15. package/dist/{chunk-RK5ETF2I.js → chunk-NR44CK5E.js} +1 -1
  16. package/dist/{chunk-MXIWUFBP.js → chunk-O2642WVS.js} +28 -4
  17. package/dist/{chunk-HCIRL37O.js → chunk-T3HPSF7K.js} +4 -1
  18. package/dist/{chunk-BTUEUA5H.js → chunk-UHT4INVW.js} +453 -87
  19. package/dist/{chunk-HYW3MUXT.js → chunk-URN7GS23.js} +30 -16
  20. package/dist/{chunk-HXLC56ZK.cjs → chunk-YSYX4GUD.cjs} +32 -18
  21. package/dist/{emit-order-notification-trigger-HZQPPSFB.js → emit-order-notification-trigger-CZU3V2WE.js} +2 -2
  22. package/dist/{emit-order-notification-trigger-NR3VN6C6.cjs → emit-order-notification-trigger-TNEZOYEE.cjs} +4 -4
  23. package/dist/index.cjs +614 -333
  24. package/dist/index.d.cts +31 -0
  25. package/dist/index.d.ts +31 -0
  26. package/dist/index.js +329 -48
  27. package/dist/migrations/1782800000000-AddPaymentSuccessFailedRefundTriggers.ts +32 -0
  28. package/dist/migrations/1782900000000-AddEnableTurnstileToForms.ts +29 -0
  29. package/dist/{order-notification-dispatcher-2FCZFZUD.cjs → order-notification-dispatcher-KJVGLK5E.cjs} +5 -5
  30. package/dist/{order-notification-dispatcher-64WDCHHG.js → order-notification-dispatcher-ZSFKEYMP.js} +2 -2
  31. package/dist/{rbac-debug-db-6EMIVMGF.js → rbac-debug-db-5R6XFPSV.js} +1 -1
  32. package/dist/{rbac-debug-db-6PWTLBEL.cjs → rbac-debug-db-JKK2MCWF.cjs} +2 -2
  33. package/package.json +1 -1
package/dist/index.js CHANGED
@@ -1,12 +1,12 @@
1
- export { emitOrderNotificationTrigger, fireOrderNotificationTrigger } from './chunk-MXIWUFBP.js';
2
- import { checkMultiVendorEnabled, loadUserVendorContext, getPublicSettingsGroup, BlogGeneratorService } from './chunk-BTUEUA5H.js';
3
- export { Address, Attendee, Attribute, BLOG_GENERATOR_AGENT_NAME, BLOG_GENERATOR_DEFAULT_SYSTEM_INSTRUCTION, BLOG_GENERATOR_DEFAULT_VALIDATION_RULES, BLOG_GENERATOR_LLM_AGENT_SLUG, BLOG_GENERATOR_MARKDOWN_ARTICLE_SEPARATOR, BLOG_METADATA_ENRICHER_AGENT_NAME, BLOG_METADATA_ENRICHER_DEFAULT_SYSTEM_INSTRUCTION, BLOG_METADATA_ENRICHER_DEFAULT_VALIDATION_RULES, BLOG_METADATA_ENRICHER_LLM_AGENT_SLUG, Blog, BlogGeneratorService, Brand, CMS_ENTITY_MAP, Cart, CartItem, Category, ChatConversation, ChatMessage, Collection, Combo, ComboItem, Comment, Config, Contact, Currency, CurrencyExchange, Customer, Customer_Contacts, Discount, DiscountRules, Event, EventProduct, Form, FormField, FormSubmission, JobSchedule, JobScheduleRun, KnowledgeBaseChunk, KnowledgeBaseDocument, LlmAgent, LlmAgentKnowledgeDocument, Media, MessageTemplate, Order, OrderAddresses, OrderDiscounts, OrderItem, OrderNotificationBinding, OrderNotificationTrigger, OtpChallenge, Page, PasswordResetToken, Payment, Permission, Product, ProductAttribute, ProductCategory, ProductConfig, ProductVariant, RefundPolicy, RefundRequest, RssArticle, RssFeed, Seo, Tag, Tax, User, UserDeviceToken, UserGroup, Vendor, VendorCustomer, VendorRole, VendorRolePermission, VendorUser, VendorUserProfile, Wishlist, WishlistItem, ZIP_MIME_TYPES, applyApprovalStatusSideEffects, applyEventApprovalStatusSideEffects, applyRotatingVendorInvite, applyVendorCustomersContactFilter, applyVendorEventCreateApproval, applyVendorProductCreateApproval, assertCaptchaOk, assertContactAllowedForVendorOrder, assertEventApprovalUpdate, assertProductApprovalUpdate, autoExpireOrderIfPaymentTimeExceeded, buildBlogMetadataUserPrompt, buildCronFromSchedule, buildRssUserPromptFromFeeds, buildUserInviteLink, buildVendorInviteLink, calculateOrderRefundPreview, calculateRefundFromPolicy, checkAndIncrementDiscountUsage, checkEventsEnabled, checkMultiVendorEnabled, completeUserInviteAccept, consumeAppliedDiscountUsages, contactIsVendorCustomer, countDiscountOrdersForContact, countRecentOtpSends, createAnalyticsHandlers, createBlogBySlugHandler, createChangePasswordHandler, createCmsApiHandler, createCmsApp, createCmsAppWithMessaging, createCrudByIdHandler, createCrudHandler, createDashboardStatsHandler, createEcommerceAnalyticsHandler, createEventOrderMessageTemplateHandlers, createForgotPasswordHandler, createFormBySlugHandler, createInviteAcceptHandler, createJobScheduleHandlers, createLlmAgentKnowledgeHandlers, createMediaZipExtractHandler, createMessageTemplateRowLoader, createOtpChallenge, createSetPasswordHandler, createSettingsApiHandlers, createSocialMediaHandlers, createStorefrontApiHandler, createUploadHandler, createUserAuthApiRouter, createUserAvatarHandler, createUserProfileHandler, createUsersApiHandlers, createVendorDashboardHandler, createVendorOnboardHandlers, daysBeforeEventStart, decrementDiscountUsage, describeEventTierPolicy, ensureMessagingPluginsOnCms, ensureScheduleQueueWorker, ensureVendorCustomerForOrderContact, ensureVendorCustomersForOrder, findActiveRefundPolicyForVendor, findUserByInviteToken, findVendorByInviteToken, formatTierRange, generateNumericOtp, getPublicSettingsGroup, getRequireEventApproval, getRequireProductApproval, getRssArticleSummaryFromItem, getVendorCatalogCreateFlags, hashOtpCode, hydrateVendorSessionUser, invalidateEventsCache, invalidateMultiVendorCache, invalidateRequireEventApprovalCache, invalidateRequireProductApprovalCache, invalidateVendorCatalogCreateFlagsCache, isCustomerTypeContact, isMaxPerUserUsageReached, isMaxTotalUsageReached, isZipMedia, llmAgentToChatAgentOptions, loadSettingsGroupFromDb, loadUserVendorContext, mergeGuardrailsIntoSystemPrompt, messagingPlugins, metaFetchUserManagedPages, metaPostPageFeed, metaPostPagePhoto, metaResolvePageAccessToken, newUserInviteToken, normalizePhoneE164, normalizeRefundTiers, overlayCmsPlugins, parseBlogGeneratorAgentContent, parseBlogGeneratorModelOutput, parseBlogMetadataEnrichmentJson, parseLlmAgentValidationRules, pgBossScheduleNameForId, queueErpCreateContactIfEnabled, queueJobScheduleNow, queuePlugin, queueSms, recordDiscountUsage, registerJobRunnerWorker, registerMessagingQueueProcessors, registerSmsQueueProcessor, relativePathFromMediaParentId, resolveBlogCategoryIdByName, resolveSettingsEncryptionKey, resolveVendorIdForContactCheck, sanitizeMediaFolderPath, sanitizeStorageSegment, sendVendorOnboardEmails, simpleDecrypt, simpleEncrypt, syncJobScheduleToPgBoss, validateRefundTiers, validateScheduleInput, validateUserMessageAgainstAgentRules, validateUserMessageAgainstStructuredRules, verifyAndConsumeOtpChallenge, verifyOtpCodeHash, whatsappPlugin, wrapGetCmsWithMessaging } from './chunk-BTUEUA5H.js';
1
+ export { emitOrderNotificationTrigger, fireOrderNotificationTrigger } from './chunk-O2642WVS.js';
2
+ import { checkMultiVendorEnabled, loadUserVendorContext, getPublicSettingsGroup, BlogGeneratorService } from './chunk-UHT4INVW.js';
3
+ export { Address, Attendee, Attribute, BLOG_GENERATOR_AGENT_NAME, BLOG_GENERATOR_DEFAULT_SYSTEM_INSTRUCTION, BLOG_GENERATOR_DEFAULT_VALIDATION_RULES, BLOG_GENERATOR_LLM_AGENT_SLUG, BLOG_GENERATOR_MARKDOWN_ARTICLE_SEPARATOR, BLOG_METADATA_ENRICHER_AGENT_NAME, BLOG_METADATA_ENRICHER_DEFAULT_SYSTEM_INSTRUCTION, BLOG_METADATA_ENRICHER_DEFAULT_VALIDATION_RULES, BLOG_METADATA_ENRICHER_LLM_AGENT_SLUG, Blog, BlogGeneratorService, Brand, CMS_ENTITY_MAP, Cart, CartItem, Category, ChatConversation, ChatMessage, Collection, Combo, ComboItem, Comment, Config, Contact, Currency, CurrencyExchange, Customer, Customer_Contacts, Discount, DiscountRules, Event, EventProduct, Form, FormField, FormSubmission, JobSchedule, JobScheduleRun, KnowledgeBaseChunk, KnowledgeBaseDocument, LlmAgent, LlmAgentKnowledgeDocument, Media, MessageTemplate, Order, OrderAddresses, OrderDiscounts, OrderItem, OrderNotificationBinding, OrderNotificationTrigger, OtpChallenge, Page, PasswordResetToken, Payment, Permission, Product, ProductAttribute, ProductCategory, ProductConfig, ProductVariant, RefundPolicy, RefundRequest, RssArticle, RssFeed, Seo, Tag, Tax, User, UserDeviceToken, UserGroup, Vendor, VendorCustomer, VendorRole, VendorRolePermission, VendorUser, VendorUserProfile, Wishlist, WishlistItem, ZIP_MIME_TYPES, applyApprovalStatusSideEffects, applyEventApprovalStatusSideEffects, applyRotatingVendorInvite, applyVendorCustomersContactFilter, applyVendorEventCreateApproval, applyVendorProductCreateApproval, assertCaptchaOk, assertContactAllowedForVendorOrder, assertEventApprovalUpdate, assertProductApprovalUpdate, autoExpireOrderIfPaymentTimeExceeded, buildBlogMetadataUserPrompt, buildCronFromSchedule, buildRssUserPromptFromFeeds, buildUserInviteLink, buildVendorInviteLink, calculateOrderRefundPreview, calculateRefundFromPolicy, checkAndIncrementDiscountUsage, checkEventsEnabled, checkMultiVendorEnabled, completeUserInviteAccept, consumeAppliedDiscountUsages, contactIsVendorCustomer, countDiscountOrdersForContact, countRecentOtpSends, createAnalyticsHandlers, createBlogBySlugHandler, createChangePasswordHandler, createCmsApiHandler, createCmsApp, createCmsAppWithMessaging, createCrudByIdHandler, createCrudHandler, createDashboardStatsHandler, createEcommerceAnalyticsHandler, createEventOrderMessageTemplateHandlers, createForgotPasswordHandler, createFormBySlugHandler, createInviteAcceptHandler, createJobScheduleHandlers, createLlmAgentKnowledgeHandlers, createMediaZipExtractHandler, createMessageTemplateRowLoader, createOtpChallenge, createSetPasswordHandler, createSettingsApiHandlers, createSocialMediaHandlers, createStorefrontApiHandler, createUploadHandler, createUserAuthApiRouter, createUserAvatarHandler, createUserProfileHandler, createUsersApiHandlers, createVendorDashboardHandler, createVendorOnboardHandlers, daysBeforeEventStart, decrementDiscountUsage, describeEventTierPolicy, ensureMessagingPluginsOnCms, ensureScheduleQueueWorker, ensureVendorCustomerForOrderContact, ensureVendorCustomersForOrder, findActiveRefundPolicyForVendor, findUserByInviteToken, findVendorByInviteToken, formatTierRange, generateNumericOtp, getPublicSettingsGroup, getRequireEventApproval, getRequireProductApproval, getRssArticleSummaryFromItem, getVendorCatalogCreateFlags, hashOtpCode, hydrateVendorSessionUser, invalidateEventsCache, invalidateMultiVendorCache, invalidateRequireEventApprovalCache, invalidateRequireProductApprovalCache, invalidateVendorCatalogCreateFlagsCache, isCustomerTypeContact, isMaxPerUserUsageReached, isMaxTotalUsageReached, isZipMedia, llmAgentToChatAgentOptions, loadSettingsGroupFromDb, loadUserVendorContext, mergeGuardrailsIntoSystemPrompt, messagingPlugins, metaFetchUserManagedPages, metaPostPageFeed, metaPostPagePhoto, metaResolvePageAccessToken, newUserInviteToken, normalizePhoneE164, normalizeRefundTiers, overlayCmsPlugins, parseBlogGeneratorAgentContent, parseBlogGeneratorModelOutput, parseBlogMetadataEnrichmentJson, parseLlmAgentValidationRules, pgBossScheduleNameForId, queueErpCreateContactIfEnabled, queueJobScheduleNow, queuePlugin, queueSms, recordDiscountUsage, registerJobRunnerWorker, registerMessagingQueueProcessors, registerSmsQueueProcessor, relativePathFromMediaParentId, resolveBlogCategoryIdByName, resolveSettingsEncryptionKey, resolveVendorIdForContactCheck, sanitizeMediaFolderPath, sanitizeStorageSegment, sendVendorOnboardEmails, simpleDecrypt, simpleEncrypt, syncJobScheduleToPgBoss, validateRefundTiers, validateScheduleInput, validateUserMessageAgainstAgentRules, validateUserMessageAgainstStructuredRules, verifyAndConsumeOtpChallenge, verifyOtpCodeHash, whatsappPlugin, wrapGetCmsWithMessaging } from './chunk-UHT4INVW.js';
4
4
  import { PgBossService } from './chunk-GO7PPYNU.js';
5
5
  export { JOB_RUNNER_QUEUE, PgBossService } from './chunk-GO7PPYNU.js';
6
6
  export { deductInventoryForConfirmedOrder, mergeInventoryLines, orderInventorySnapshotFromRow, orderStatusHoldsStock, reconcileOrderInventoryBetweenSnapshots, restoreInventoryForCancelledOrder, validateInventoryForConfirmedOrderLines, validateInventoryForOrderBecomingConfirmed } from './chunk-3K5AIEIZ.js';
7
- import { parseEmailRecipientsFromConfig } from './chunk-HYW3MUXT.js';
8
- export { EmailService, buildEventOrderTemplateVariables, emailPlugin, emailTemplates, initWhatsappTriggerDispatcher, joinRecipientsForSend, parseEmailRecipientsFromConfig, queueWhatsApp, registerWhatsAppQueueProcessor, renderEmail, renderLayout, resendOrderNotification, serializeEmailRecipients } from './chunk-HYW3MUXT.js';
9
- export { KNOWN_NOTIFICATION_TRIGGERS, notificationTriggerEmitter } from './chunk-HCIRL37O.js';
7
+ import { parseEmailRecipientsFromConfig } from './chunk-URN7GS23.js';
8
+ export { EmailService, buildEventOrderTemplateVariables, emailPlugin, emailTemplates, initWhatsappTriggerDispatcher, joinRecipientsForSend, parseEmailRecipientsFromConfig, queueWhatsApp, registerWhatsAppQueueProcessor, renderEmail, renderLayout, resendOrderNotification, serializeEmailRecipients } from './chunk-URN7GS23.js';
9
+ export { KNOWN_NOTIFICATION_TRIGGERS, notificationTriggerEmitter } from './chunk-T3HPSF7K.js';
10
10
  import './chunk-JXF23MPG.js';
11
11
  import { queueOrderPlacedEmails } from './chunk-L3525VXI.js';
12
12
  export { queueEmail, queueOrderPlacedEmails, queueVendorOnboardEmails, registerEmailQueueProcessor } from './chunk-L3525VXI.js';
@@ -16,11 +16,11 @@ import './chunk-JC6DLWTE.js';
16
16
  import './chunk-MQBT33IV.js';
17
17
  import './chunk-CRFV5WJK.js';
18
18
  export { EVENT_ORDER_MESSAGE_TEMPLATE_DEFAULTS, EVENT_ORDER_TEMPLATE_KEY, EVENT_ORDER_TEMPLATE_VARIABLES, resolveEventOrderTemplate } from './chunk-AYERBA7I.js';
19
- export { AUTH_PROVIDERS_SETTINGS_GROUP, buildNextAuthOptions, buildStorefrontNextAuthOptions, createCustomerUserFromGoogleOAuth, getNextAuthOptions, getStorefrontNextAuthOptions, googleOAuthRedirectUri, isGoogleAuthPubliclyEnabled, resolveGoogleAuthConfig, seedAdministratorPermissions } from './chunk-BNKZNLEX.js';
20
- export { OPEN_ENDPOINTS, PERMISSION_REQUIRED_ENDPOINTS, RBAC_ADMIN_ONLY_ENTITIES, canManageRoles, createAuthHelpers, createCmsAuthBundle, customerPhoneForEmail, customerPhoneForUser, ensureCustomerForUser, ensureCustomerRecord, getRequiredPermission, isOpenEndpoint, isPublicMethod, isSyntheticCustomerPhone, linkUnclaimedContactToUser, normalizeCustomerPhone, sessionHasEntityAccess } from './chunk-RK5ETF2I.js';
19
+ export { AUTH_PROVIDERS_SETTINGS_GROUP, buildNextAuthOptions, buildStorefrontNextAuthOptions, createCustomerUserFromGoogleOAuth, getNextAuthOptions, getStorefrontNextAuthOptions, googleOAuthRedirectUri, isGoogleAuthPubliclyEnabled, resolveGoogleAuthConfig, seedAdministratorPermissions } from './chunk-6DBDJ4VD.js';
20
+ export { OPEN_ENDPOINTS, PERMISSION_REQUIRED_ENDPOINTS, RBAC_ADMIN_ONLY_ENTITIES, canManageRoles, createAuthHelpers, createCmsAuthBundle, customerPhoneForEmail, customerPhoneForUser, ensureCustomerForUser, ensureCustomerRecord, getRequiredPermission, isOpenEndpoint, isPublicMethod, isSyntheticCustomerPhone, linkUnclaimedContactToUser, normalizeCustomerPhone, sessionHasEntityAccess } from './chunk-NR44CK5E.js';
21
21
  export { activeUniqueValueExists, retireSoftDeletedUniqueValue } from './chunk-DBPSJYLZ.js';
22
- import { isSuperAdmin, isVendorGroupName } from './chunk-JIWUVQ6B.js';
23
- export { ADMIN_GROUP_NAME, SUPER_ADMIN_GROUP_ID, VENDOR_ADMIN_GROUP_ID, VENDOR_GROUP_NAME, VENDOR_OWNER_GROUP_NAME, VENDOR_SCOPED_STORE_ENTITIES, VENDOR_STORE_RBAC_ENTITIES, canManageVendorRoles, canManageVendorTeam, canOnboardVendors, explainSessionEntityAccess, getPermissionableEntityKeys, hasEntityPermission, isPlatformAdministrator, isRbacDebugEnabled, isSuperAdmin, isSuperAdminGroupName, isVendorAdmin, isVendorGroupName, isVendorOwner, isVendorPortalUser, isVendorStaff, logEntityAccessDecision, logRbac, permissionRowsToRecord, resolveVendorScopeFromSessionUser, summarizeEntityPerms, vendorPortalFlagsFromUser } from './chunk-JIWUVQ6B.js';
22
+ import { isSuperAdmin, isVendorGroupName } from './chunk-MVHDC3XF.js';
23
+ export { ADMIN_GROUP_NAME, SUPER_ADMIN_GROUP_ID, VENDOR_ADMIN_GROUP_ID, VENDOR_GROUP_NAME, VENDOR_OWNER_GROUP_NAME, VENDOR_SCOPED_STORE_ENTITIES, VENDOR_STORE_RBAC_ENTITIES, canManageVendorRoles, canManageVendorTeam, canOnboardVendors, explainSessionEntityAccess, getPermissionableEntityKeys, hasEntityPermission, isPlatformAdministrator, isRbacDebugEnabled, isSuperAdmin, isSuperAdminGroupName, isVendorAdmin, isVendorGroupName, isVendorOwner, isVendorPortalUser, isVendorStaff, logEntityAccessDecision, logRbac, permissionRowsToRecord, resolveVendorScopeFromSessionUser, summarizeEntityPerms, vendorPortalFlagsFromUser } from './chunk-MVHDC3XF.js';
24
24
  export { createCmsMiddleware, defaultPublicApiMethods, isAuthDebugClientEnabled, isAuthDebugEnabled, logAuth, logAuthClient, nextAuthCookieDebugInfo, summarizeSessionUserForLog } from './chunk-WUQAOTHA.js';
25
25
  export { queueErpPaidOrderForOrderId } from './chunk-TDV6EJHV.js';
26
26
  import { erpSafeWebhookUrl, logErp, warnErp, errorErp } from './chunk-SYBOCAWB.js';
@@ -1050,37 +1050,91 @@ var LOG = "[s3]";
1050
1050
  function serializeS3Error(err) {
1051
1051
  if (!err || typeof err !== "object") {
1052
1052
  return {
1053
- error: String(err)
1053
+ error: String(err),
1054
+ errorType: typeof err
1054
1055
  };
1055
1056
  }
1056
1057
  const e = err;
1057
- return {
1058
+ const out = {
1058
1059
  name: e.name,
1059
1060
  message: e.message,
1060
1061
  code: e.Code ?? e.code,
1062
+ fault: e.$fault,
1061
1063
  httpStatus: e.$metadata?.httpStatusCode,
1062
1064
  requestId: e.$metadata?.requestId,
1063
1065
  extendedRequestId: e.$metadata?.extendedRequestId,
1064
- cfId: e.$metadata?.cfId
1066
+ cfId: e.$metadata?.cfId,
1067
+ attempts: e.$metadata?.attempts,
1068
+ totalRetryDelay: e.$metadata?.totalRetryDelay,
1069
+ stack: e.stack
1065
1070
  };
1071
+ if (e.cause != null) {
1072
+ out.cause = serializeS3Error(e.cause);
1073
+ }
1074
+ try {
1075
+ const extras = {};
1076
+ for (const k of Object.keys(e)) {
1077
+ if (k === "name" || k === "message" || k === "Code" || k === "code" || k === "$fault" || k === "$metadata" || k === "stack" || k === "cause") {
1078
+ continue;
1079
+ }
1080
+ const v = e[k];
1081
+ if (typeof v === "string" || typeof v === "number" || typeof v === "boolean" || v == null) {
1082
+ extras[k] = v;
1083
+ } else {
1084
+ extras[k] = String(v);
1085
+ }
1086
+ }
1087
+ if (Object.keys(extras).length > 0) out.extras = extras;
1088
+ } catch {
1089
+ }
1090
+ return out;
1066
1091
  }
1067
1092
  __name(serializeS3Error, "serializeS3Error");
1068
1093
  function publicObjectUrl(config, fullKey) {
1094
+ console.info(LOG, "build public URL", {
1095
+ fullKey,
1096
+ hasBaseUrl: Boolean(config.baseUrl),
1097
+ baseUrl: config.baseUrl ?? null,
1098
+ bucket: config.bucket,
1099
+ region: config.region
1100
+ });
1069
1101
  if (config.baseUrl) {
1070
- return `${config.baseUrl.replace(/\/$/, "")}/${fullKey}`;
1102
+ const url2 = `${config.baseUrl.replace(/\/$/, "")}/${fullKey}`;
1103
+ console.info(LOG, "public URL from baseUrl", {
1104
+ fullKey,
1105
+ url: url2
1106
+ });
1107
+ return url2;
1071
1108
  }
1072
- return `https://s3.${config.region}.amazonaws.com/${config.bucket}/${fullKey}`;
1109
+ const url = `https://s3.${config.region}.amazonaws.com/${config.bucket}/${fullKey}`;
1110
+ console.info(LOG, "public URL from default S3 endpoint", {
1111
+ fullKey,
1112
+ url
1113
+ });
1114
+ return url;
1073
1115
  }
1074
1116
  __name(publicObjectUrl, "publicObjectUrl");
1075
1117
  function describeS3Config(config) {
1076
- const base = config.baseUrl ? new URL(config.baseUrl).host : null;
1118
+ let baseUrlHost = null;
1119
+ try {
1120
+ baseUrlHost = config.baseUrl ? new URL(config.baseUrl).host : null;
1121
+ } catch (err) {
1122
+ console.error(LOG, "invalid baseUrl while describing config", {
1123
+ baseUrl: config.baseUrl,
1124
+ ...serializeS3Error(err)
1125
+ });
1126
+ baseUrlHost = config.baseUrl ?? null;
1127
+ }
1077
1128
  return {
1078
1129
  bucket: config.bucket,
1079
1130
  region: config.region,
1080
1131
  prefix: config.prefix ?? "uploads",
1081
1132
  hasBaseUrl: Boolean(config.baseUrl),
1082
- baseUrlHost: base,
1083
- accessKeyIdLast4: config.accessKeyId.slice(-4),
1133
+ baseUrl: config.baseUrl ?? null,
1134
+ baseUrlHost,
1135
+ accessKeyIdLast4: config.accessKeyId ? config.accessKeyId.slice(-4) : null,
1136
+ accessKeyIdLength: config.accessKeyId?.length ?? 0,
1137
+ secretAccessKeyLength: config.secretAccessKey?.length ?? 0,
1084
1138
  envSummary: {
1085
1139
  AWS_BUCKET_NAME: Boolean(config.bucket),
1086
1140
  AWS_REGION: Boolean(config.region),
@@ -1091,7 +1145,11 @@ function describeS3Config(config) {
1091
1145
  };
1092
1146
  }
1093
1147
  __name(describeS3Config, "describeS3Config");
1094
- async function probePublicUrl(url) {
1148
+ async function probePublicUrl(url, fullKey) {
1149
+ console.info(LOG, "probe public URL start", {
1150
+ url,
1151
+ fullKey
1152
+ });
1095
1153
  try {
1096
1154
  const head = await fetch(url, {
1097
1155
  method: "HEAD",
@@ -1099,15 +1157,25 @@ async function probePublicUrl(url) {
1099
1157
  });
1100
1158
  const headInfo = {
1101
1159
  url,
1160
+ fullKey,
1102
1161
  status: head.status,
1103
1162
  ok: head.ok,
1104
1163
  contentType: head.headers.get("content-type"),
1105
- location: head.headers.get("location")
1164
+ contentLength: head.headers.get("content-length"),
1165
+ location: head.headers.get("location"),
1166
+ cacheControl: head.headers.get("cache-control"),
1167
+ etag: head.headers.get("etag")
1106
1168
  };
1169
+ console.info(LOG, "probe HEAD result", headInfo);
1107
1170
  if (head.ok) {
1108
1171
  console.info(LOG, "public URL reachable (HEAD)", headInfo);
1109
1172
  return;
1110
1173
  }
1174
+ console.warn(LOG, "probe HEAD not ok \u2014 trying ranged GET", {
1175
+ url,
1176
+ fullKey,
1177
+ status: head.status
1178
+ });
1111
1179
  const getRes = await fetch(url, {
1112
1180
  method: "GET",
1113
1181
  headers: {
@@ -1118,19 +1186,26 @@ async function probePublicUrl(url) {
1118
1186
  let bodySnippet = "";
1119
1187
  try {
1120
1188
  bodySnippet = (await getRes.text()).slice(0, 400);
1121
- } catch {
1189
+ } catch (bodyErr) {
1190
+ console.error(LOG, "probe GET body read failed", {
1191
+ url,
1192
+ fullKey,
1193
+ ...serializeS3Error(bodyErr)
1194
+ });
1122
1195
  }
1123
1196
  console.error(LOG, "public URL not readable \u2014 admin images will not display", {
1124
1197
  ...headInfo,
1125
1198
  getStatus: getRes.status,
1126
1199
  getOk: getRes.ok,
1127
1200
  getContentType: getRes.headers.get("content-type"),
1201
+ getContentLength: getRes.headers.get("content-length"),
1128
1202
  bodySnippet
1129
1203
  });
1130
1204
  } catch (err) {
1131
1205
  console.error(LOG, "public URL probe failed", {
1132
1206
  url,
1133
- error: err instanceof Error ? err.message : String(err)
1207
+ fullKey,
1208
+ ...serializeS3Error(err)
1134
1209
  });
1135
1210
  }
1136
1211
  }
@@ -1138,9 +1213,69 @@ __name(probePublicUrl, "probePublicUrl");
1138
1213
  function getS3Storage(config) {
1139
1214
  const prefix = (config.prefix ?? "uploads").replace(/\/$/, "");
1140
1215
  const keyPrefix = prefix ? `${prefix}/` : "";
1216
+ console.info(LOG, "storage service created", {
1217
+ ...describeS3Config(config),
1218
+ keyPrefix,
1219
+ resolvedPrefix: prefix
1220
+ });
1141
1221
  return {
1142
1222
  async upload(buffer, key, contentType) {
1143
- const { S3Client, PutObjectCommand } = await import('@aws-sdk/client-s3');
1223
+ const uploadId = `upl-${Date.now()}-${Math.random().toString(36).slice(2, 8)}`;
1224
+ const started = Date.now();
1225
+ console.info(LOG, "upload() called", {
1226
+ uploadId,
1227
+ incomingKey: key,
1228
+ contentType,
1229
+ bytes: buffer?.length ?? null,
1230
+ isBuffer: Buffer.isBuffer(buffer),
1231
+ ...describeS3Config(config)
1232
+ });
1233
+ if (!buffer || !Buffer.isBuffer(buffer)) {
1234
+ console.error(LOG, "upload aborted \u2014 invalid buffer", {
1235
+ uploadId,
1236
+ incomingKey: key,
1237
+ bufferType: typeof buffer,
1238
+ isBuffer: Buffer.isBuffer(buffer)
1239
+ });
1240
+ throw new Error("S3 upload: invalid buffer");
1241
+ }
1242
+ if (!key || typeof key !== "string") {
1243
+ console.error(LOG, "upload aborted \u2014 invalid key", {
1244
+ uploadId,
1245
+ key,
1246
+ keyType: typeof key
1247
+ });
1248
+ throw new Error("S3 upload: invalid key");
1249
+ }
1250
+ console.info(LOG, "importing @aws-sdk/client-s3", {
1251
+ uploadId,
1252
+ key
1253
+ });
1254
+ let S3Client;
1255
+ let PutObjectCommand;
1256
+ let HeadObjectCommand;
1257
+ try {
1258
+ const sdk = await import('@aws-sdk/client-s3');
1259
+ S3Client = sdk.S3Client;
1260
+ PutObjectCommand = sdk.PutObjectCommand;
1261
+ HeadObjectCommand = sdk.HeadObjectCommand;
1262
+ console.info(LOG, "AWS SDK import ok", {
1263
+ uploadId,
1264
+ key
1265
+ });
1266
+ } catch (err) {
1267
+ console.error(LOG, "AWS SDK import failed", {
1268
+ uploadId,
1269
+ key,
1270
+ ...serializeS3Error(err)
1271
+ });
1272
+ throw err;
1273
+ }
1274
+ console.info(LOG, "creating S3Client", {
1275
+ uploadId,
1276
+ region: config.region,
1277
+ accessKeyIdLast4: config.accessKeyId.slice(-4)
1278
+ });
1144
1279
  const client = new S3Client({
1145
1280
  region: config.region,
1146
1281
  credentials: {
@@ -1151,47 +1286,114 @@ function getS3Storage(config) {
1151
1286
  const rawKey = key.replace(/^\/+/, "");
1152
1287
  const fullKey = keyPrefix + rawKey;
1153
1288
  const publicUrl = publicObjectUrl(config, fullKey);
1154
- const started = Date.now();
1155
- console.info(LOG, "upload start", {
1156
- ...describeS3Config(config),
1157
- key: rawKey,
1289
+ console.info(LOG, "resolved S3 object key", {
1290
+ uploadId,
1291
+ incomingKey: key,
1292
+ rawKey,
1293
+ keyPrefix,
1158
1294
  fullKey,
1295
+ bucket: config.bucket,
1296
+ region: config.region,
1159
1297
  publicUrl,
1160
1298
  contentType,
1161
- bytes: buffer.length
1299
+ bytes: buffer.length,
1300
+ note: "PutObject will use Bucket + Key (= fullKey)"
1301
+ });
1302
+ const putInput = {
1303
+ Bucket: config.bucket,
1304
+ Key: fullKey,
1305
+ Body: buffer,
1306
+ ContentType: contentType
1307
+ };
1308
+ console.info(LOG, "PutObjectCommand prepared", {
1309
+ uploadId,
1310
+ Bucket: putInput.Bucket,
1311
+ Key: putInput.Key,
1312
+ ContentType: putInput.ContentType,
1313
+ BodyBytes: buffer.length,
1314
+ BodyIsBuffer: Buffer.isBuffer(putInput.Body)
1162
1315
  });
1316
+ let putResult;
1163
1317
  try {
1164
- await client.send(new PutObjectCommand({
1165
- Bucket: config.bucket,
1166
- Key: fullKey,
1167
- Body: buffer,
1168
- ContentType: contentType
1169
- }));
1318
+ console.info(LOG, "PutObject send start", {
1319
+ uploadId,
1320
+ bucket: config.bucket,
1321
+ fullKey,
1322
+ msElapsed: Date.now() - started
1323
+ });
1324
+ putResult = await client.send(new PutObjectCommand(putInput));
1325
+ console.info(LOG, "PutObject send returned", {
1326
+ uploadId,
1327
+ bucket: config.bucket,
1328
+ fullKey,
1329
+ ETag: putResult?.ETag,
1330
+ VersionId: putResult?.VersionId,
1331
+ httpStatus: putResult?.$metadata?.httpStatusCode,
1332
+ requestId: putResult?.$metadata?.requestId,
1333
+ ms: Date.now() - started
1334
+ });
1170
1335
  } catch (err) {
1171
- const errorDump = serializeS3Error(err);
1172
1336
  console.error(LOG, "PutObject failed", {
1337
+ uploadId,
1173
1338
  ...describeS3Config(config),
1174
- key: rawKey,
1339
+ incomingKey: key,
1340
+ rawKey,
1341
+ keyPrefix,
1175
1342
  fullKey,
1176
1343
  publicUrl,
1177
1344
  contentType,
1178
1345
  bytes: buffer.length,
1179
- ...errorDump,
1346
+ ms: Date.now() - started,
1347
+ ...serializeS3Error(err),
1180
1348
  rawError: err instanceof Error ? err.message : String(err)
1181
1349
  });
1182
1350
  throw err;
1183
1351
  }
1184
- console.info(LOG, "PutObject ok", {
1352
+ console.info(LOG, "PutObject ok \u2014 verifying with HeadObject", {
1353
+ uploadId,
1354
+ bucket: config.bucket,
1355
+ fullKey,
1356
+ publicUrl
1357
+ });
1358
+ try {
1359
+ const head = await client.send(new HeadObjectCommand({
1360
+ Bucket: config.bucket,
1361
+ Key: fullKey
1362
+ }));
1363
+ console.info(LOG, "HeadObject ok \u2014 object exists in bucket", {
1364
+ uploadId,
1365
+ bucket: config.bucket,
1366
+ fullKey,
1367
+ contentType: head.ContentType,
1368
+ contentLength: head.ContentLength,
1369
+ etag: head.ETag,
1370
+ lastModified: head.LastModified?.toISOString?.() ?? head.LastModified,
1371
+ httpStatus: head.$metadata?.httpStatusCode,
1372
+ requestId: head.$metadata?.requestId
1373
+ });
1374
+ } catch (headErr) {
1375
+ console.error(LOG, "HeadObject failed after PutObject \u2014 key may be wrong or ACL/permission issue", {
1376
+ uploadId,
1377
+ bucket: config.bucket,
1378
+ fullKey,
1379
+ publicUrl,
1380
+ ...serializeS3Error(headErr)
1381
+ });
1382
+ }
1383
+ console.info(LOG, "upload complete", {
1384
+ uploadId,
1185
1385
  ...describeS3Config(config),
1186
- key: rawKey,
1386
+ incomingKey: key,
1387
+ rawKey,
1187
1388
  fullKey,
1188
1389
  publicUrl,
1189
1390
  contentType,
1190
1391
  bytes: buffer.length,
1191
1392
  ms: Date.now() - started,
1393
+ ETag: putResult?.ETag,
1192
1394
  hasCustomBaseUrl: Boolean(config.baseUrl)
1193
1395
  });
1194
- void probePublicUrl(publicUrl);
1396
+ void probePublicUrl(publicUrl, fullKey);
1195
1397
  return publicUrl;
1196
1398
  }
1197
1399
  };
@@ -1202,26 +1404,66 @@ function s3StoragePlugin(config) {
1202
1404
  name: "storage",
1203
1405
  version: "1.0.0",
1204
1406
  async init(context) {
1407
+ console.info(LOG, "plugin init start", {
1408
+ configKeys: Object.keys(config ?? {}),
1409
+ hasContextConfig: Boolean(context?.config),
1410
+ contextConfigKeys: context?.config ? Object.keys(context.config) : []
1411
+ });
1205
1412
  const region = config.region ?? context.config.AWS_REGION ?? "";
1206
1413
  const accessKeyId = config.accessKeyId ?? context.config.AWS_ACCESS_KEY_ID ?? "";
1207
1414
  const secretAccessKey = config.secretAccessKey ?? context.config.AWS_SECRET_ACCESS_KEY ?? "";
1208
1415
  const bucket = config.bucket ?? context.config.AWS_BUCKET_NAME ?? "";
1209
1416
  const baseUrl = config.baseUrl ?? context.config.S3_MEDIA_URL ?? context.config.S3_CUSTOM_DOMAIN;
1417
+ console.info(LOG, "plugin init resolved raw values", {
1418
+ region: region || "(empty)",
1419
+ bucket: bucket || "(empty)",
1420
+ prefix: config.prefix ?? "uploads",
1421
+ hasAccessKeyId: Boolean(accessKeyId),
1422
+ accessKeyIdLast4: accessKeyId ? accessKeyId.slice(-4) : null,
1423
+ hasSecretAccessKey: Boolean(secretAccessKey),
1424
+ secretAccessKeyLength: secretAccessKey?.length ?? 0,
1425
+ baseUrlRaw: baseUrl ?? null,
1426
+ fromPluginConfig: {
1427
+ region: Boolean(config.region),
1428
+ accessKeyId: Boolean(config.accessKeyId),
1429
+ secretAccessKey: Boolean(config.secretAccessKey),
1430
+ bucket: Boolean(config.bucket),
1431
+ baseUrl: Boolean(config.baseUrl)
1432
+ },
1433
+ fromContext: {
1434
+ AWS_REGION: Boolean(context.config.AWS_REGION),
1435
+ AWS_ACCESS_KEY_ID: Boolean(context.config.AWS_ACCESS_KEY_ID),
1436
+ AWS_SECRET_ACCESS_KEY: Boolean(context.config.AWS_SECRET_ACCESS_KEY),
1437
+ AWS_BUCKET_NAME: Boolean(context.config.AWS_BUCKET_NAME),
1438
+ S3_MEDIA_URL: Boolean(context.config.S3_MEDIA_URL),
1439
+ S3_CUSTOM_DOMAIN: Boolean(context.config.S3_CUSTOM_DOMAIN)
1440
+ }
1441
+ });
1210
1442
  const resolvedBaseUrl = typeof baseUrl === "string" && baseUrl ? baseUrl.startsWith("http") ? baseUrl : `https://${baseUrl}` : void 0;
1443
+ console.info(LOG, "plugin init baseUrl resolution", {
1444
+ baseUrlRaw: baseUrl ?? null,
1445
+ resolvedBaseUrl: resolvedBaseUrl ?? null
1446
+ });
1211
1447
  if (!region || !accessKeyId || !secretAccessKey || !bucket) {
1212
1448
  console.error(LOG, "plugin init missing config", {
1213
1449
  hasRegion: Boolean(region),
1214
1450
  hasAccessKeyId: Boolean(accessKeyId),
1215
1451
  hasSecretAccessKey: Boolean(secretAccessKey),
1216
1452
  hasBucket: Boolean(bucket),
1217
- hasBaseUrl: Boolean(resolvedBaseUrl)
1453
+ hasBaseUrl: Boolean(resolvedBaseUrl),
1454
+ regionValue: region || null,
1455
+ bucketValue: bucket || null
1218
1456
  });
1219
1457
  throw new Error("S3 storage plugin: missing region, accessKeyId, secretAccessKey or bucket");
1220
1458
  }
1221
1459
  let baseUrlHost = null;
1222
1460
  try {
1223
1461
  baseUrlHost = resolvedBaseUrl ? new URL(resolvedBaseUrl).host : null;
1224
- } catch {
1462
+ } catch (err) {
1463
+ console.error(LOG, "plugin init invalid resolvedBaseUrl", {
1464
+ resolvedBaseUrl,
1465
+ ...serializeS3Error(err)
1466
+ });
1225
1467
  baseUrlHost = resolvedBaseUrl ?? null;
1226
1468
  }
1227
1469
  console.info(LOG, "plugin ready", {
@@ -1229,6 +1471,7 @@ function s3StoragePlugin(config) {
1229
1471
  bucket,
1230
1472
  prefix: config.prefix ?? "uploads",
1231
1473
  hasBaseUrl: Boolean(resolvedBaseUrl),
1474
+ baseUrl: resolvedBaseUrl ?? null,
1232
1475
  baseUrlHost,
1233
1476
  accessKeyIdLast4: accessKeyId.slice(-4),
1234
1477
  envSummary: {
@@ -2491,6 +2734,27 @@ var DEFAULT_ORDER_NOTIFICATION_TRIGGER_SEEDS = [
2491
2734
  description: "Fires when an order is cancelled (includes refund amount when applicable).",
2492
2735
  category: "order",
2493
2736
  sortOrder: 2
2737
+ },
2738
+ {
2739
+ triggerKey: "payment_success",
2740
+ label: "Payment success",
2741
+ description: "Fires when order is placed and payment status is paid.",
2742
+ category: "order",
2743
+ sortOrder: 3
2744
+ },
2745
+ {
2746
+ triggerKey: "payment_failed",
2747
+ label: "Payment failed",
2748
+ description: "Fires when payment status is pending, unpaid, or failed, or when order is cancelled without payment.",
2749
+ category: "order",
2750
+ sortOrder: 4
2751
+ },
2752
+ {
2753
+ triggerKey: "payment_refund_initiated",
2754
+ label: "Payment refund initiated",
2755
+ description: "Fires when order is cancelled and its payment status is paid (refund initiated).",
2756
+ category: "order",
2757
+ sortOrder: 5
2494
2758
  }
2495
2759
  ];
2496
2760
 
@@ -2503,6 +2767,18 @@ var ORDER_NOTIFICATION_TRIGGERS = [
2503
2767
  {
2504
2768
  key: "order_cancelled",
2505
2769
  label: "Order cancelled"
2770
+ },
2771
+ {
2772
+ key: "payment_success",
2773
+ label: "Payment success"
2774
+ },
2775
+ {
2776
+ key: "payment_failed",
2777
+ label: "Payment failed"
2778
+ },
2779
+ {
2780
+ key: "payment_refund_initiated",
2781
+ label: "Payment refund initiated"
2506
2782
  }
2507
2783
  ];
2508
2784
  function disablePgNative() {
@@ -2749,13 +3025,18 @@ __name(withAdminRlsContext, "withAdminRlsContext");
2749
3025
 
2750
3026
  // src/plugins/captcha/captcha-service.ts
2751
3027
  function resolveKeys(config) {
2752
- const turnstile = config.TURNSTILE_SITE_KEY?.trim() && config.TURNSTILE_SECRET_KEY?.trim() ? {
2753
- site: config.TURNSTILE_SITE_KEY.trim(),
2754
- secret: config.TURNSTILE_SECRET_KEY.trim()
3028
+ const isTurnstileDisabled = config.enabled === "false" || config.turnstile_enabled === "false";
3029
+ const turnstileSite = (config.TURNSTILE_SITE_KEY ?? config.siteKey ?? config.site_key ?? "").trim();
3030
+ const turnstileSecret = (config.TURNSTILE_SECRET_KEY ?? config.secretKey ?? config.secret_key ?? "").trim();
3031
+ const turnstile = !isTurnstileDisabled && turnstileSite && turnstileSecret ? {
3032
+ site: turnstileSite,
3033
+ secret: turnstileSecret
2755
3034
  } : null;
2756
- const recaptcha = config.RECAPTCHA_SITE_KEY?.trim() && config.RECAPTCHA_SECRET_KEY?.trim() ? {
2757
- site: config.RECAPTCHA_SITE_KEY.trim(),
2758
- secret: config.RECAPTCHA_SECRET_KEY.trim()
3035
+ const recaptchaSite = (config.RECAPTCHA_SITE_KEY ?? config.recaptchaSiteKey ?? "").trim();
3036
+ const recaptchaSecret = (config.RECAPTCHA_SECRET_KEY ?? config.recaptchaSecretKey ?? "").trim();
3037
+ const recaptcha = recaptchaSite && recaptchaSecret ? {
3038
+ site: recaptchaSite,
3039
+ secret: recaptchaSecret
2759
3040
  } : null;
2760
3041
  const raw = config.CAPTCHA_PROVIDER?.trim().toLowerCase();
2761
3042
  let envDefaultProvider = null;
@@ -0,0 +1,32 @@
1
+ import type { MigrationInterface, QueryRunner } from 'typeorm';
2
+
3
+ /** Add 3 new order notification triggers: payment_success, payment_failed, and payment_refund_initiated. */
4
+ export class AddPaymentSuccessFailedRefundTriggers1782800000000 implements MigrationInterface {
5
+ name = 'AddPaymentSuccessFailedRefundTriggers1782800000000';
6
+
7
+ public async up(queryRunner: QueryRunner): Promise<void> {
8
+ await queryRunner.query(`
9
+ INSERT INTO "order_notification_triggers" ("triggerKey", "label", "description", "category", "sortOrder")
10
+ VALUES
11
+ ('payment_success', 'Payment success', 'Fires when order is placed and payment status is paid.', 'order', 3),
12
+ ('payment_failed', 'Payment failed', 'Fires when payment status is pending, unpaid, or failed, or when order is cancelled without payment.', 'order', 4),
13
+ ('payment_refund_initiated', 'Payment refund initiated', 'Fires when order is cancelled and its payment status is paid (refund initiated).', 'order', 5)
14
+ ON CONFLICT ("triggerKey") DO UPDATE SET
15
+ "label" = EXCLUDED."label",
16
+ "description" = EXCLUDED."description",
17
+ "sortOrder" = EXCLUDED."sortOrder",
18
+ "updatedAt" = now();
19
+ `);
20
+ }
21
+
22
+ public async down(queryRunner: QueryRunner): Promise<void> {
23
+ await queryRunner.query(`
24
+ DELETE FROM "order_notification_bindings"
25
+ WHERE "triggerKey" IN ('payment_success', 'payment_failed', 'payment_refund_initiated');
26
+ `);
27
+ await queryRunner.query(`
28
+ DELETE FROM "order_notification_triggers"
29
+ WHERE "triggerKey" IN ('payment_success', 'payment_failed', 'payment_refund_initiated');
30
+ `);
31
+ }
32
+ }
@@ -0,0 +1,29 @@
1
+ import { MigrationInterface, QueryRunner, TableColumn } from 'typeorm';
2
+
3
+ export class AddEnableTurnstileToForms1782800000000 implements MigrationInterface {
4
+ public async up(queryRunner: QueryRunner): Promise<void> {
5
+ const hasTable = await queryRunner.hasTable('forms');
6
+ if (!hasTable) return;
7
+ const hasCol = await queryRunner.hasColumn('forms', 'enable_turnstile');
8
+ if (!hasCol) {
9
+ await queryRunner.addColumn(
10
+ 'forms',
11
+ new TableColumn({
12
+ name: 'enable_turnstile',
13
+ type: 'boolean',
14
+ default: false,
15
+ isNullable: true,
16
+ })
17
+ );
18
+ }
19
+ }
20
+
21
+ public async down(queryRunner: QueryRunner): Promise<void> {
22
+ const hasTable = await queryRunner.hasTable('forms');
23
+ if (!hasTable) return;
24
+ const hasCol = await queryRunner.hasColumn('forms', 'enable_turnstile');
25
+ if (hasCol) {
26
+ await queryRunner.dropColumn('forms', 'enable_turnstile');
27
+ }
28
+ }
29
+ }
@@ -1,7 +1,7 @@
1
1
  'use strict';
2
2
 
3
- var chunkHXLC56ZK_cjs = require('./chunk-HXLC56ZK.cjs');
4
- require('./chunk-UCKN4BBY.cjs');
3
+ var chunkYSYX4GUD_cjs = require('./chunk-YSYX4GUD.cjs');
4
+ require('./chunk-77I3KS7V.cjs');
5
5
  require('./chunk-V25RDUOU.cjs');
6
6
  require('./chunk-BXYZDMTZ.cjs');
7
7
  require('./chunk-UPLVMVRX.cjs');
@@ -12,13 +12,13 @@ require('./chunk-USNT2KNT.cjs');
12
12
 
13
13
  Object.defineProperty(exports, "getSettingsGroup", {
14
14
  enumerable: true,
15
- get: function () { return chunkHXLC56ZK_cjs.getSettingsGroup; }
15
+ get: function () { return chunkYSYX4GUD_cjs.getSettingsGroup; }
16
16
  });
17
17
  Object.defineProperty(exports, "initWhatsappTriggerDispatcher", {
18
18
  enumerable: true,
19
- get: function () { return chunkHXLC56ZK_cjs.initWhatsappTriggerDispatcher; }
19
+ get: function () { return chunkYSYX4GUD_cjs.initWhatsappTriggerDispatcher; }
20
20
  });
21
21
  Object.defineProperty(exports, "resendOrderNotification", {
22
22
  enumerable: true,
23
- get: function () { return chunkHXLC56ZK_cjs.resendOrderNotification; }
23
+ get: function () { return chunkYSYX4GUD_cjs.resendOrderNotification; }
24
24
  });
@@ -1,5 +1,5 @@
1
- export { getSettingsGroup, initWhatsappTriggerDispatcher, resendOrderNotification } from './chunk-HYW3MUXT.js';
2
- import './chunk-HCIRL37O.js';
1
+ export { getSettingsGroup, initWhatsappTriggerDispatcher, resendOrderNotification } from './chunk-URN7GS23.js';
2
+ import './chunk-T3HPSF7K.js';
3
3
  import './chunk-L3525VXI.js';
4
4
  import './chunk-2KUCQVAQ.js';
5
5
  import './chunk-JC6DLWTE.js';