@sonicjs-cms/core 2.13.0 → 2.14.0

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 (45) hide show
  1. package/dist/{chunk-IYFSNRZN.js → chunk-23DP6TO5.js} +13 -10
  2. package/dist/chunk-23DP6TO5.js.map +1 -0
  3. package/dist/{chunk-DB2GJJTM.js → chunk-AFGOH2F6.js} +3 -3
  4. package/dist/{chunk-DB2GJJTM.js.map → chunk-AFGOH2F6.js.map} +1 -1
  5. package/dist/{chunk-HVTSE2SF.cjs → chunk-DRWSHIFG.cjs} +102 -99
  6. package/dist/chunk-DRWSHIFG.cjs.map +1 -0
  7. package/dist/{chunk-CO4B5EYF.js → chunk-GAVTTYMC.js} +3 -3
  8. package/dist/{chunk-CO4B5EYF.js.map → chunk-GAVTTYMC.js.map} +1 -1
  9. package/dist/{chunk-3VAKUFNQ.js → chunk-JKNKO6LA.js} +22 -5
  10. package/dist/chunk-JKNKO6LA.js.map +1 -0
  11. package/dist/{chunk-SER23XI4.cjs → chunk-KZ2MFGET.cjs} +22 -5
  12. package/dist/chunk-KZ2MFGET.cjs.map +1 -0
  13. package/dist/{chunk-XCP5GCBE.cjs → chunk-YULUPQZV.cjs} +3 -3
  14. package/dist/{chunk-XCP5GCBE.cjs.map → chunk-YULUPQZV.cjs.map} +1 -1
  15. package/dist/{chunk-EGUDIX6Q.cjs → chunk-YYMPHM3I.cjs} +4 -4
  16. package/dist/{chunk-EGUDIX6Q.cjs.map → chunk-YYMPHM3I.cjs.map} +1 -1
  17. package/dist/index.cjs +853 -99
  18. package/dist/index.cjs.map +1 -1
  19. package/dist/index.d.cts +2 -2
  20. package/dist/index.d.ts +2 -2
  21. package/dist/index.js +763 -9
  22. package/dist/index.js.map +1 -1
  23. package/dist/middleware.cjs +28 -28
  24. package/dist/middleware.js +2 -2
  25. package/dist/migrations-F7KVA74T.cjs +13 -0
  26. package/dist/{migrations-GMHTJI7D.cjs.map → migrations-F7KVA74T.cjs.map} +1 -1
  27. package/dist/migrations-WKONKRN7.js +4 -0
  28. package/dist/{migrations-IVFIDOSO.js.map → migrations-WKONKRN7.js.map} +1 -1
  29. package/dist/{plugin-bootstrap-DVGLQrcO.d.cts → plugin-bootstrap-BGwBraaN.d.cts} +1 -0
  30. package/dist/{plugin-bootstrap-CZ1GDum7.d.ts → plugin-bootstrap-Drns7X9w.d.ts} +1 -0
  31. package/dist/routes.cjs +27 -27
  32. package/dist/routes.js +4 -4
  33. package/dist/services.cjs +2 -2
  34. package/dist/services.d.cts +1 -1
  35. package/dist/services.d.ts +1 -1
  36. package/dist/services.js +1 -1
  37. package/dist/utils.cjs +11 -11
  38. package/dist/utils.js +1 -1
  39. package/package.json +1 -1
  40. package/dist/chunk-3VAKUFNQ.js.map +0 -1
  41. package/dist/chunk-HVTSE2SF.cjs.map +0 -1
  42. package/dist/chunk-IYFSNRZN.js.map +0 -1
  43. package/dist/chunk-SER23XI4.cjs.map +0 -1
  44. package/dist/migrations-GMHTJI7D.cjs +0 -13
  45. package/dist/migrations-IVFIDOSO.js +0 -4
package/dist/index.cjs CHANGED
@@ -1,15 +1,15 @@
1
1
  'use strict';
2
2
 
3
- var chunkHVTSE2SF_cjs = require('./chunk-HVTSE2SF.cjs');
3
+ var chunkDRWSHIFG_cjs = require('./chunk-DRWSHIFG.cjs');
4
4
  var chunkNZWFCUDA_cjs = require('./chunk-NZWFCUDA.cjs');
5
- var chunkEGUDIX6Q_cjs = require('./chunk-EGUDIX6Q.cjs');
5
+ var chunkYYMPHM3I_cjs = require('./chunk-YYMPHM3I.cjs');
6
6
  var chunkI6FFGQIT_cjs = require('./chunk-I6FFGQIT.cjs');
7
- var chunkSER23XI4_cjs = require('./chunk-SER23XI4.cjs');
7
+ var chunkKZ2MFGET_cjs = require('./chunk-KZ2MFGET.cjs');
8
8
  var chunk3QCEYJLK_cjs = require('./chunk-3QCEYJLK.cjs');
9
9
  var chunkQP3OHHON_cjs = require('./chunk-QP3OHHON.cjs');
10
10
  var chunk56GUBLJE_cjs = require('./chunk-56GUBLJE.cjs');
11
11
  var chunk6FHNRRJ3_cjs = require('./chunk-6FHNRRJ3.cjs');
12
- var chunkXCP5GCBE_cjs = require('./chunk-XCP5GCBE.cjs');
12
+ var chunkYULUPQZV_cjs = require('./chunk-YULUPQZV.cjs');
13
13
  require('./chunk-P3XDZL6Q.cjs');
14
14
  var chunkRCQ2HIQD_cjs = require('./chunk-RCQ2HIQD.cjs');
15
15
  var chunkMNWKYY5E_cjs = require('./chunk-MNWKYY5E.cjs');
@@ -559,7 +559,7 @@ function formatCellValue(value) {
559
559
  // src/plugins/core-plugins/database-tools-plugin/admin-routes.ts
560
560
  function createDatabaseToolsAdminRoutes() {
561
561
  const router3 = new hono.Hono();
562
- router3.use("*", chunkEGUDIX6Q_cjs.requireAuth());
562
+ router3.use("*", chunkYYMPHM3I_cjs.requireAuth());
563
563
  router3.get("/api/stats", async (c) => {
564
564
  try {
565
565
  const user = c.get("user");
@@ -1938,7 +1938,7 @@ function createOTPLoginPlugin() {
1938
1938
  error: "Account is deactivated"
1939
1939
  }, 403);
1940
1940
  }
1941
- const token = await chunkEGUDIX6Q_cjs.AuthManager.generateToken(user.id, user.email, user.role, c.env.JWT_SECRET);
1941
+ const token = await chunkYYMPHM3I_cjs.AuthManager.generateToken(user.id, user.email, user.role, c.env.JWT_SECRET);
1942
1942
  cookie.setCookie(c, "auth_token", token, {
1943
1943
  httpOnly: true,
1944
1944
  secure: true,
@@ -2408,13 +2408,13 @@ function createOAuthProvidersPlugin() {
2408
2408
  if (!user || !user.is_active) {
2409
2409
  return c.redirect("/auth/login?error=Account is deactivated");
2410
2410
  }
2411
- const jwt2 = await chunkEGUDIX6Q_cjs.AuthManager.generateToken(
2411
+ const jwt2 = await chunkYYMPHM3I_cjs.AuthManager.generateToken(
2412
2412
  user.id,
2413
2413
  user.email,
2414
2414
  user.role,
2415
2415
  c.env.JWT_SECRET
2416
2416
  );
2417
- chunkEGUDIX6Q_cjs.AuthManager.setAuthCookie(c, jwt2, { sameSite: "Lax" });
2417
+ chunkYYMPHM3I_cjs.AuthManager.setAuthCookie(c, jwt2, { sameSite: "Lax" });
2418
2418
  return c.redirect("/admin");
2419
2419
  }
2420
2420
  const existingUser = await oauthService.findUserByEmail(profile.email);
@@ -2431,13 +2431,13 @@ function createOAuthProvidersPlugin() {
2431
2431
  tokenExpiresAt: tokenExpiresAt ?? void 0,
2432
2432
  profileData: JSON.stringify(profile)
2433
2433
  });
2434
- const jwt2 = await chunkEGUDIX6Q_cjs.AuthManager.generateToken(
2434
+ const jwt2 = await chunkYYMPHM3I_cjs.AuthManager.generateToken(
2435
2435
  existingUser.id,
2436
2436
  existingUser.email,
2437
2437
  existingUser.role,
2438
2438
  c.env.JWT_SECRET
2439
2439
  );
2440
- chunkEGUDIX6Q_cjs.AuthManager.setAuthCookie(c, jwt2, { sameSite: "Lax" });
2440
+ chunkYYMPHM3I_cjs.AuthManager.setAuthCookie(c, jwt2, { sameSite: "Lax" });
2441
2441
  return c.redirect("/admin");
2442
2442
  }
2443
2443
  const newUserId = await oauthService.createUserFromOAuth(profile);
@@ -2450,13 +2450,13 @@ function createOAuthProvidersPlugin() {
2450
2450
  tokenExpiresAt: tokenExpiresAt ?? void 0,
2451
2451
  profileData: JSON.stringify(profile)
2452
2452
  });
2453
- const jwt = await chunkEGUDIX6Q_cjs.AuthManager.generateToken(
2453
+ const jwt = await chunkYYMPHM3I_cjs.AuthManager.generateToken(
2454
2454
  newUserId,
2455
2455
  profile.email.toLowerCase(),
2456
2456
  "viewer",
2457
2457
  c.env.JWT_SECRET
2458
2458
  );
2459
- chunkEGUDIX6Q_cjs.AuthManager.setAuthCookie(c, jwt, { sameSite: "Lax" });
2459
+ chunkYYMPHM3I_cjs.AuthManager.setAuthCookie(c, jwt, { sameSite: "Lax" });
2460
2460
  return c.redirect("/admin");
2461
2461
  } catch (error) {
2462
2462
  console.error("OAuth callback error:", error);
@@ -3896,7 +3896,7 @@ function renderSettingsPage(data) {
3896
3896
  const indexStatusMap = data.indexStatus || {};
3897
3897
  const status = indexStatusMap[collectionId];
3898
3898
  const isNew = collection.is_new === true && !isDismissed && !status;
3899
- const statusBadge = status && isChecked ? `<span class="ml-2 px-2 py-1 text-xs rounded-full ${status.status === "completed" ? "bg-green-100 text-green-800 dark:bg-green-900/30 dark:text-green-300" : status.status === "indexing" ? "bg-blue-100 text-blue-800 dark:bg-blue-900/30 dark:text-blue-300" : status.status === "error" ? "bg-red-100 text-red-800 dark:bg-red-900/30 dark:text-red-300" : "bg-gray-100 text-gray-800 dark:bg-gray-800 dark:text-gray-300"}">${status.status}</span>` : "";
3899
+ const statusBadge2 = status && isChecked ? `<span class="ml-2 px-2 py-1 text-xs rounded-full ${status.status === "completed" ? "bg-green-100 text-green-800 dark:bg-green-900/30 dark:text-green-300" : status.status === "indexing" ? "bg-blue-100 text-blue-800 dark:bg-blue-900/30 dark:text-blue-300" : status.status === "error" ? "bg-red-100 text-red-800 dark:bg-red-900/30 dark:text-red-300" : "bg-gray-100 text-gray-800 dark:bg-gray-800 dark:text-gray-300"}">${status.status}</span>` : "";
3900
3900
  return `<div class="flex items-start gap-3 p-3 rounded-lg border border-zinc-200 dark:border-zinc-700 ${isNew ? "bg-blue-50 dark:bg-blue-900/10 border-blue-200 dark:border-blue-800" : "hover:bg-zinc-50 dark:hover:bg-zinc-800"}">
3901
3901
  <input
3902
3902
  type="checkbox"
@@ -3911,7 +3911,7 @@ function renderSettingsPage(data) {
3911
3911
  <label for="collection_${collectionId}" class="text-sm font-medium text-zinc-950 dark:text-white select-none cursor-pointer flex items-center">
3912
3912
  ${collection.display_name || collection.name || "Unnamed Collection"}
3913
3913
  ${isNew ? '<span class="ml-2 px-2 py-0.5 text-xs rounded-full bg-blue-100 text-blue-800 dark:bg-blue-900/30 dark:text-blue-300">NEW</span>' : ""}
3914
- ${statusBadge}
3914
+ ${statusBadge2}
3915
3915
  </label>
3916
3916
  <p class="text-xs text-zinc-500 dark:text-zinc-400 mt-1">
3917
3917
  ${collection.description || collection.name || "No description"} \u2022 ${collection.item_count || 0} items
@@ -4149,7 +4149,7 @@ function renderSettingsPage(data) {
4149
4149
 
4150
4150
  // src/plugins/core-plugins/ai-search-plugin/routes/admin.ts
4151
4151
  var adminRoutes = new hono.Hono();
4152
- adminRoutes.use("*", chunkEGUDIX6Q_cjs.requireAuth());
4152
+ adminRoutes.use("*", chunkYYMPHM3I_cjs.requireAuth());
4153
4153
  adminRoutes.get("/", async (c) => {
4154
4154
  try {
4155
4155
  const user = c.get("user");
@@ -4550,13 +4550,13 @@ function createMagicLinkAuthPlugin() {
4550
4550
  SET used = 1, used_at = ?
4551
4551
  WHERE id = ?
4552
4552
  `).bind(Date.now(), magicLink.id).run();
4553
- const jwtToken = await chunkEGUDIX6Q_cjs.AuthManager.generateToken(
4553
+ const jwtToken = await chunkYYMPHM3I_cjs.AuthManager.generateToken(
4554
4554
  user.id,
4555
4555
  user.email,
4556
4556
  user.role,
4557
4557
  c.env.JWT_SECRET
4558
4558
  );
4559
- chunkEGUDIX6Q_cjs.AuthManager.setAuthCookie(c, jwtToken);
4559
+ chunkYYMPHM3I_cjs.AuthManager.setAuthCookie(c, jwtToken);
4560
4560
  await db.prepare(`
4561
4561
  UPDATE users SET last_login_at = ? WHERE id = ?
4562
4562
  `).bind(Date.now(), user.id).run();
@@ -5566,7 +5566,7 @@ function renderSecuritySettingsPage(data) {
5566
5566
 
5567
5567
  // src/plugins/core-plugins/security-audit-plugin/routes/admin.ts
5568
5568
  var adminRoutes2 = new hono.Hono();
5569
- adminRoutes2.use("*", chunkEGUDIX6Q_cjs.requireAuth());
5569
+ adminRoutes2.use("*", chunkYYMPHM3I_cjs.requireAuth());
5570
5570
  adminRoutes2.use("*", async (c, next) => {
5571
5571
  const user = c.get("user");
5572
5572
  if (user?.role !== "admin") {
@@ -5836,7 +5836,7 @@ var BruteForceDetector = class {
5836
5836
 
5837
5837
  // src/plugins/core-plugins/security-audit-plugin/routes/api.ts
5838
5838
  var apiRoutes2 = new hono.Hono();
5839
- apiRoutes2.use("*", chunkEGUDIX6Q_cjs.requireAuth());
5839
+ apiRoutes2.use("*", chunkYYMPHM3I_cjs.requireAuth());
5840
5840
  apiRoutes2.use("*", async (c, next) => {
5841
5841
  const user = c.get("user");
5842
5842
  if (user?.role !== "admin") {
@@ -6266,6 +6266,755 @@ function createSecurityAuditPlugin() {
6266
6266
  }
6267
6267
  var securityAuditPlugin = createSecurityAuditPlugin();
6268
6268
 
6269
+ // src/plugins/core-plugins/stripe-plugin/services/subscription-service.ts
6270
+ var SubscriptionService = class {
6271
+ constructor(db) {
6272
+ this.db = db;
6273
+ }
6274
+ /**
6275
+ * Ensure the subscriptions table exists
6276
+ */
6277
+ async ensureTable() {
6278
+ await this.db.prepare(`
6279
+ CREATE TABLE IF NOT EXISTS subscriptions (
6280
+ id TEXT PRIMARY KEY DEFAULT (lower(hex(randomblob(16)))),
6281
+ user_id TEXT NOT NULL,
6282
+ stripe_customer_id TEXT NOT NULL,
6283
+ stripe_subscription_id TEXT NOT NULL UNIQUE,
6284
+ stripe_price_id TEXT NOT NULL,
6285
+ status TEXT NOT NULL DEFAULT 'incomplete',
6286
+ current_period_start INTEGER NOT NULL DEFAULT 0,
6287
+ current_period_end INTEGER NOT NULL DEFAULT 0,
6288
+ cancel_at_period_end INTEGER NOT NULL DEFAULT 0,
6289
+ created_at INTEGER NOT NULL DEFAULT (unixepoch()),
6290
+ updated_at INTEGER NOT NULL DEFAULT (unixepoch())
6291
+ )
6292
+ `).run();
6293
+ await this.db.prepare(`
6294
+ CREATE INDEX IF NOT EXISTS idx_subscriptions_user_id ON subscriptions(user_id)
6295
+ `).run();
6296
+ await this.db.prepare(`
6297
+ CREATE INDEX IF NOT EXISTS idx_subscriptions_stripe_customer_id ON subscriptions(stripe_customer_id)
6298
+ `).run();
6299
+ await this.db.prepare(`
6300
+ CREATE INDEX IF NOT EXISTS idx_subscriptions_stripe_subscription_id ON subscriptions(stripe_subscription_id)
6301
+ `).run();
6302
+ await this.db.prepare(`
6303
+ CREATE INDEX IF NOT EXISTS idx_subscriptions_status ON subscriptions(status)
6304
+ `).run();
6305
+ }
6306
+ /**
6307
+ * Create a new subscription record
6308
+ */
6309
+ async create(data) {
6310
+ const result = await this.db.prepare(`
6311
+ INSERT INTO subscriptions (user_id, stripe_customer_id, stripe_subscription_id, stripe_price_id, status, current_period_start, current_period_end, cancel_at_period_end)
6312
+ VALUES (?, ?, ?, ?, ?, ?, ?, ?)
6313
+ RETURNING *
6314
+ `).bind(
6315
+ data.userId,
6316
+ data.stripeCustomerId,
6317
+ data.stripeSubscriptionId,
6318
+ data.stripePriceId,
6319
+ data.status,
6320
+ data.currentPeriodStart,
6321
+ data.currentPeriodEnd,
6322
+ data.cancelAtPeriodEnd ? 1 : 0
6323
+ ).first();
6324
+ return this.mapRow(result);
6325
+ }
6326
+ /**
6327
+ * Update a subscription by its Stripe subscription ID
6328
+ */
6329
+ async updateByStripeId(stripeSubscriptionId, data) {
6330
+ const sets = [];
6331
+ const values = [];
6332
+ if (data.status !== void 0) {
6333
+ sets.push("status = ?");
6334
+ values.push(data.status);
6335
+ }
6336
+ if (data.stripePriceId !== void 0) {
6337
+ sets.push("stripe_price_id = ?");
6338
+ values.push(data.stripePriceId);
6339
+ }
6340
+ if (data.currentPeriodStart !== void 0) {
6341
+ sets.push("current_period_start = ?");
6342
+ values.push(data.currentPeriodStart);
6343
+ }
6344
+ if (data.currentPeriodEnd !== void 0) {
6345
+ sets.push("current_period_end = ?");
6346
+ values.push(data.currentPeriodEnd);
6347
+ }
6348
+ if (data.cancelAtPeriodEnd !== void 0) {
6349
+ sets.push("cancel_at_period_end = ?");
6350
+ values.push(data.cancelAtPeriodEnd ? 1 : 0);
6351
+ }
6352
+ if (sets.length === 0) return this.getByStripeSubscriptionId(stripeSubscriptionId);
6353
+ sets.push("updated_at = unixepoch()");
6354
+ values.push(stripeSubscriptionId);
6355
+ const result = await this.db.prepare(`
6356
+ UPDATE subscriptions SET ${sets.join(", ")} WHERE stripe_subscription_id = ? RETURNING *
6357
+ `).bind(...values).first();
6358
+ return result ? this.mapRow(result) : null;
6359
+ }
6360
+ /**
6361
+ * Get subscription by Stripe subscription ID
6362
+ */
6363
+ async getByStripeSubscriptionId(stripeSubscriptionId) {
6364
+ const result = await this.db.prepare(
6365
+ "SELECT * FROM subscriptions WHERE stripe_subscription_id = ?"
6366
+ ).bind(stripeSubscriptionId).first();
6367
+ return result ? this.mapRow(result) : null;
6368
+ }
6369
+ /**
6370
+ * Get the active subscription for a user
6371
+ */
6372
+ async getByUserId(userId) {
6373
+ const result = await this.db.prepare(
6374
+ "SELECT * FROM subscriptions WHERE user_id = ? ORDER BY CASE WHEN status = 'active' THEN 0 WHEN status = 'trialing' THEN 1 ELSE 2 END, updated_at DESC LIMIT 1"
6375
+ ).bind(userId).first();
6376
+ return result ? this.mapRow(result) : null;
6377
+ }
6378
+ /**
6379
+ * Get subscription by Stripe customer ID
6380
+ */
6381
+ async getByStripeCustomerId(stripeCustomerId) {
6382
+ const result = await this.db.prepare(
6383
+ "SELECT * FROM subscriptions WHERE stripe_customer_id = ? ORDER BY updated_at DESC LIMIT 1"
6384
+ ).bind(stripeCustomerId).first();
6385
+ return result ? this.mapRow(result) : null;
6386
+ }
6387
+ /**
6388
+ * Find the userId linked to a Stripe customer ID
6389
+ */
6390
+ async getUserIdByStripeCustomer(stripeCustomerId) {
6391
+ const result = await this.db.prepare(
6392
+ "SELECT user_id FROM subscriptions WHERE stripe_customer_id = ? LIMIT 1"
6393
+ ).bind(stripeCustomerId).first();
6394
+ return result?.user_id ?? null;
6395
+ }
6396
+ /**
6397
+ * List subscriptions with filters and pagination
6398
+ */
6399
+ async list(filters = {}) {
6400
+ const where = [];
6401
+ const values = [];
6402
+ if (filters.status) {
6403
+ where.push("status = ?");
6404
+ values.push(filters.status);
6405
+ }
6406
+ if (filters.userId) {
6407
+ where.push("user_id = ?");
6408
+ values.push(filters.userId);
6409
+ }
6410
+ if (filters.stripeCustomerId) {
6411
+ where.push("stripe_customer_id = ?");
6412
+ values.push(filters.stripeCustomerId);
6413
+ }
6414
+ const whereClause = where.length > 0 ? `WHERE ${where.join(" AND ")}` : "";
6415
+ const sortBy = filters.sortBy || "created_at";
6416
+ const sortOrder = filters.sortOrder || "desc";
6417
+ const limit = Math.min(filters.limit || 50, 100);
6418
+ const page = filters.page || 1;
6419
+ const offset = (page - 1) * limit;
6420
+ const countResult = await this.db.prepare(
6421
+ `SELECT COUNT(*) as count FROM subscriptions ${whereClause}`
6422
+ ).bind(...values).first();
6423
+ const results = await this.db.prepare(
6424
+ `SELECT s.*, u.email as user_email FROM subscriptions s LEFT JOIN users u ON s.user_id = u.id ${whereClause} ORDER BY ${sortBy} ${sortOrder} LIMIT ? OFFSET ?`
6425
+ ).bind(...values, limit, offset).all();
6426
+ return {
6427
+ subscriptions: (results.results || []).map((r) => this.mapRow(r)),
6428
+ total: countResult?.count || 0
6429
+ };
6430
+ }
6431
+ /**
6432
+ * Get subscription stats
6433
+ */
6434
+ async getStats() {
6435
+ const result = await this.db.prepare(`
6436
+ SELECT
6437
+ COUNT(*) as total,
6438
+ SUM(CASE WHEN status = 'active' THEN 1 ELSE 0 END) as active,
6439
+ SUM(CASE WHEN status = 'canceled' THEN 1 ELSE 0 END) as canceled,
6440
+ SUM(CASE WHEN status = 'past_due' THEN 1 ELSE 0 END) as past_due,
6441
+ SUM(CASE WHEN status = 'trialing' THEN 1 ELSE 0 END) as trialing
6442
+ FROM subscriptions
6443
+ `).first();
6444
+ return {
6445
+ total: result?.total || 0,
6446
+ active: result?.active || 0,
6447
+ canceled: result?.canceled || 0,
6448
+ pastDue: result?.past_due || 0,
6449
+ trialing: result?.trialing || 0
6450
+ };
6451
+ }
6452
+ /**
6453
+ * Delete a subscription record by Stripe subscription ID
6454
+ */
6455
+ async deleteByStripeId(stripeSubscriptionId) {
6456
+ const result = await this.db.prepare(
6457
+ "DELETE FROM subscriptions WHERE stripe_subscription_id = ?"
6458
+ ).bind(stripeSubscriptionId).run();
6459
+ return (result.meta?.changes || 0) > 0;
6460
+ }
6461
+ mapRow(row) {
6462
+ return {
6463
+ id: row.id,
6464
+ userId: row.user_id,
6465
+ stripeCustomerId: row.stripe_customer_id,
6466
+ stripeSubscriptionId: row.stripe_subscription_id,
6467
+ stripePriceId: row.stripe_price_id,
6468
+ status: row.status,
6469
+ currentPeriodStart: row.current_period_start,
6470
+ currentPeriodEnd: row.current_period_end,
6471
+ cancelAtPeriodEnd: !!row.cancel_at_period_end,
6472
+ createdAt: row.created_at,
6473
+ updatedAt: row.updated_at,
6474
+ // Attach email if joined
6475
+ ...row.user_email ? { userEmail: row.user_email } : {}
6476
+ };
6477
+ }
6478
+ };
6479
+
6480
+ // src/plugins/core-plugins/stripe-plugin/components/subscriptions-page.ts
6481
+ function renderSubscriptionsPage(subscriptions, stats, filters) {
6482
+ return `
6483
+ <div class="space-y-6">
6484
+ <!-- Stats Cards -->
6485
+ <div class="grid grid-cols-1 md:grid-cols-5 gap-4">
6486
+ ${statsCard("Total", stats.total, "text-gray-700")}
6487
+ ${statsCard("Active", stats.active, "text-green-600")}
6488
+ ${statsCard("Trialing", stats.trialing, "text-blue-600")}
6489
+ ${statsCard("Past Due", stats.pastDue, "text-yellow-600")}
6490
+ ${statsCard("Canceled", stats.canceled, "text-red-600")}
6491
+ </div>
6492
+
6493
+ <!-- Filters -->
6494
+ <div class="bg-white rounded-lg shadow p-4">
6495
+ <form method="GET" class="flex items-center gap-4">
6496
+ <label class="text-sm font-medium text-gray-700">Status:</label>
6497
+ <select name="status" class="border rounded px-3 py-1.5 text-sm" onchange="this.form.submit()">
6498
+ <option value="">All</option>
6499
+ ${statusOption("active", filters.status)}
6500
+ ${statusOption("trialing", filters.status)}
6501
+ ${statusOption("past_due", filters.status)}
6502
+ ${statusOption("canceled", filters.status)}
6503
+ ${statusOption("unpaid", filters.status)}
6504
+ ${statusOption("paused", filters.status)}
6505
+ </select>
6506
+ </form>
6507
+ </div>
6508
+
6509
+ <!-- Subscriptions Table -->
6510
+ <div class="bg-white rounded-lg shadow overflow-hidden">
6511
+ <table class="min-w-full divide-y divide-gray-200">
6512
+ <thead class="bg-gray-50">
6513
+ <tr>
6514
+ <th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">User</th>
6515
+ <th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Status</th>
6516
+ <th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Price ID</th>
6517
+ <th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Current Period</th>
6518
+ <th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Cancel at End</th>
6519
+ <th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Stripe</th>
6520
+ </tr>
6521
+ </thead>
6522
+ <tbody class="bg-white divide-y divide-gray-200">
6523
+ ${subscriptions.length === 0 ? '<tr><td colspan="6" class="px-6 py-8 text-center text-gray-500">No subscriptions found</td></tr>' : subscriptions.map(renderRow).join("")}
6524
+ </tbody>
6525
+ </table>
6526
+
6527
+ ${renderPagination2(filters.page, filters.totalPages, filters.status)}
6528
+ </div>
6529
+ </div>
6530
+ `;
6531
+ }
6532
+ function statsCard(label, value, colorClass) {
6533
+ return `
6534
+ <div class="bg-white rounded-lg shadow p-4">
6535
+ <div class="text-sm font-medium text-gray-500">${label}</div>
6536
+ <div class="text-2xl font-bold ${colorClass}">${value}</div>
6537
+ </div>
6538
+ `;
6539
+ }
6540
+ function statusOption(value, current) {
6541
+ const selected = value === current ? "selected" : "";
6542
+ const label = value.replace("_", " ").replace(/\b\w/g, (c) => c.toUpperCase());
6543
+ return `<option value="${value}" ${selected}>${label}</option>`;
6544
+ }
6545
+ function statusBadge(status) {
6546
+ const colors = {
6547
+ active: "bg-green-100 text-green-800",
6548
+ trialing: "bg-blue-100 text-blue-800",
6549
+ past_due: "bg-yellow-100 text-yellow-800",
6550
+ canceled: "bg-red-100 text-red-800",
6551
+ unpaid: "bg-orange-100 text-orange-800",
6552
+ paused: "bg-gray-100 text-gray-800",
6553
+ incomplete: "bg-gray-100 text-gray-500",
6554
+ incomplete_expired: "bg-red-100 text-red-500"
6555
+ };
6556
+ const color = colors[status] || "bg-gray-100 text-gray-800";
6557
+ const label = status.replace("_", " ");
6558
+ return `<span class="inline-flex items-center px-2.5 py-0.5 rounded-full text-xs font-medium ${color}">${label}</span>`;
6559
+ }
6560
+ function formatDate(timestamp) {
6561
+ if (!timestamp) return "-";
6562
+ return new Date(timestamp * 1e3).toLocaleDateString("en-US", {
6563
+ month: "short",
6564
+ day: "numeric",
6565
+ year: "numeric"
6566
+ });
6567
+ }
6568
+ function renderRow(sub) {
6569
+ return `
6570
+ <tr>
6571
+ <td class="px-6 py-4 whitespace-nowrap">
6572
+ <div class="text-sm font-medium text-gray-900">${sub.userEmail || sub.userId}</div>
6573
+ <div class="text-xs text-gray-500">${sub.stripeCustomerId}</div>
6574
+ </td>
6575
+ <td class="px-6 py-4 whitespace-nowrap">${statusBadge(sub.status)}</td>
6576
+ <td class="px-6 py-4 whitespace-nowrap text-sm text-gray-500">${sub.stripePriceId}</td>
6577
+ <td class="px-6 py-4 whitespace-nowrap text-sm text-gray-500">
6578
+ ${formatDate(sub.currentPeriodStart)} - ${formatDate(sub.currentPeriodEnd)}
6579
+ </td>
6580
+ <td class="px-6 py-4 whitespace-nowrap text-sm">
6581
+ ${sub.cancelAtPeriodEnd ? '<span class="text-yellow-600 font-medium">Yes</span>' : '<span class="text-gray-400">No</span>'}
6582
+ </td>
6583
+ <td class="px-6 py-4 whitespace-nowrap text-sm">
6584
+ <a href="https://dashboard.stripe.com/subscriptions/${sub.stripeSubscriptionId}"
6585
+ target="_blank" rel="noopener noreferrer"
6586
+ class="text-indigo-600 hover:text-indigo-800">
6587
+ View in Stripe
6588
+ </a>
6589
+ </td>
6590
+ </tr>
6591
+ `;
6592
+ }
6593
+ function renderPagination2(page, totalPages, status) {
6594
+ if (totalPages <= 1) return "";
6595
+ const params = status ? `&status=${status}` : "";
6596
+ return `
6597
+ <div class="bg-white px-4 py-3 flex items-center justify-between border-t border-gray-200 sm:px-6">
6598
+ <div class="text-sm text-gray-700">
6599
+ Page ${page} of ${totalPages}
6600
+ </div>
6601
+ <div class="flex gap-2">
6602
+ ${page > 1 ? `<a href="?page=${page - 1}${params}" class="px-3 py-1 border rounded text-sm hover:bg-gray-50">Previous</a>` : ""}
6603
+ ${page < totalPages ? `<a href="?page=${page + 1}${params}" class="px-3 py-1 border rounded text-sm hover:bg-gray-50">Next</a>` : ""}
6604
+ </div>
6605
+ </div>
6606
+ `;
6607
+ }
6608
+
6609
+ // src/plugins/core-plugins/stripe-plugin/types.ts
6610
+ var DEFAULT_SETTINGS3 = {
6611
+ stripeSecretKey: "",
6612
+ stripeWebhookSecret: "",
6613
+ stripePriceId: "",
6614
+ successUrl: "/admin/dashboard",
6615
+ cancelUrl: "/admin/dashboard"
6616
+ };
6617
+
6618
+ // src/plugins/core-plugins/stripe-plugin/routes/admin.ts
6619
+ var adminRoutes3 = new hono.Hono();
6620
+ adminRoutes3.use("*", chunkYYMPHM3I_cjs.requireAuth());
6621
+ adminRoutes3.use("*", async (c, next) => {
6622
+ const user = c.get("user");
6623
+ if (user?.role !== "admin") {
6624
+ return c.text("Access denied", 403);
6625
+ }
6626
+ return next();
6627
+ });
6628
+ adminRoutes3.get("/", async (c) => {
6629
+ const db = c.env.DB;
6630
+ const subscriptionService = new SubscriptionService(db);
6631
+ await subscriptionService.ensureTable();
6632
+ const page = parseInt(c.req.query("page") || "1");
6633
+ const limit = 50;
6634
+ const statusFilter = c.req.query("status");
6635
+ const [{ subscriptions, total }, stats] = await Promise.all([
6636
+ subscriptionService.list({ status: statusFilter, page, limit }),
6637
+ subscriptionService.getStats()
6638
+ ]);
6639
+ const totalPages = Math.ceil(total / limit);
6640
+ const html = renderSubscriptionsPage(subscriptions, stats, {
6641
+ status: statusFilter,
6642
+ page,
6643
+ totalPages
6644
+ });
6645
+ return c.html(html);
6646
+ });
6647
+ adminRoutes3.post("/settings", async (c) => {
6648
+ try {
6649
+ const body = await c.req.json();
6650
+ const db = c.env.DB;
6651
+ await db.prepare(`
6652
+ UPDATE plugins
6653
+ SET settings = ?,
6654
+ updated_at = unixepoch()
6655
+ WHERE id = 'stripe'
6656
+ `).bind(JSON.stringify(body)).run();
6657
+ return c.json({ success: true });
6658
+ } catch (error) {
6659
+ console.error("Error saving Stripe settings:", error);
6660
+ return c.json({ success: false, error: "Failed to save settings" }, 500);
6661
+ }
6662
+ });
6663
+
6664
+ // src/plugins/core-plugins/stripe-plugin/services/stripe-api.ts
6665
+ var StripeAPI = class {
6666
+ constructor(secretKey) {
6667
+ this.secretKey = secretKey;
6668
+ }
6669
+ baseUrl = "https://api.stripe.com/v1";
6670
+ /**
6671
+ * Verify a webhook signature
6672
+ * Implements Stripe's v1 signature scheme using Web Crypto API
6673
+ */
6674
+ async verifyWebhookSignature(payload, sigHeader, secret) {
6675
+ const parts = sigHeader.split(",");
6676
+ const timestamp = parts.find((p) => p.startsWith("t="))?.split("=")[1];
6677
+ const signatures = parts.filter((p) => p.startsWith("v1=")).map((p) => p.substring(3));
6678
+ if (!timestamp || signatures.length === 0) return false;
6679
+ const now = Math.floor(Date.now() / 1e3);
6680
+ if (Math.abs(now - parseInt(timestamp)) > 300) return false;
6681
+ const signedPayload = `${timestamp}.${payload}`;
6682
+ const encoder = new TextEncoder();
6683
+ const key = await crypto.subtle.importKey(
6684
+ "raw",
6685
+ encoder.encode(secret),
6686
+ { name: "HMAC", hash: "SHA-256" },
6687
+ false,
6688
+ ["sign"]
6689
+ );
6690
+ const signatureBuffer = await crypto.subtle.sign("HMAC", key, encoder.encode(signedPayload));
6691
+ const expectedSignature = Array.from(new Uint8Array(signatureBuffer)).map((b) => b.toString(16).padStart(2, "0")).join("");
6692
+ return signatures.some((sig) => timingSafeEqual(sig, expectedSignature));
6693
+ }
6694
+ /**
6695
+ * Create a Checkout Session
6696
+ */
6697
+ async createCheckoutSession(params) {
6698
+ const body = new URLSearchParams();
6699
+ body.append("mode", "subscription");
6700
+ body.append("line_items[0][price]", params.priceId);
6701
+ body.append("line_items[0][quantity]", "1");
6702
+ body.append("success_url", params.successUrl);
6703
+ body.append("cancel_url", params.cancelUrl);
6704
+ if (params.customerId) {
6705
+ body.append("customer", params.customerId);
6706
+ } else if (params.customerEmail) {
6707
+ body.append("customer_email", params.customerEmail);
6708
+ }
6709
+ if (params.metadata) {
6710
+ for (const [key, value] of Object.entries(params.metadata)) {
6711
+ body.append(`metadata[${key}]`, value);
6712
+ }
6713
+ }
6714
+ const response = await this.request("POST", "/checkout/sessions", body);
6715
+ return { id: response.id, url: response.url };
6716
+ }
6717
+ /**
6718
+ * Retrieve a Stripe subscription
6719
+ */
6720
+ async getSubscription(subscriptionId) {
6721
+ return this.request("GET", `/subscriptions/${subscriptionId}`);
6722
+ }
6723
+ /**
6724
+ * Create a Stripe customer
6725
+ */
6726
+ async createCustomer(params) {
6727
+ const body = new URLSearchParams();
6728
+ body.append("email", params.email);
6729
+ if (params.metadata) {
6730
+ for (const [key, value] of Object.entries(params.metadata)) {
6731
+ body.append(`metadata[${key}]`, value);
6732
+ }
6733
+ }
6734
+ return this.request("POST", "/customers", body);
6735
+ }
6736
+ /**
6737
+ * Search for a customer by email
6738
+ */
6739
+ async findCustomerByEmail(email) {
6740
+ const params = new URLSearchParams();
6741
+ params.append("query", `email:'${email}'`);
6742
+ params.append("limit", "1");
6743
+ const result = await this.request("GET", `/customers/search?${params.toString()}`);
6744
+ return result.data?.[0] || null;
6745
+ }
6746
+ async request(method, path, body) {
6747
+ const url = path.startsWith("http") ? path : `${this.baseUrl}${path}`;
6748
+ const response = await fetch(url, {
6749
+ method,
6750
+ headers: {
6751
+ "Authorization": `Bearer ${this.secretKey}`,
6752
+ ...body ? { "Content-Type": "application/x-www-form-urlencoded" } : {}
6753
+ },
6754
+ ...body ? { body: body.toString() } : {}
6755
+ });
6756
+ const data = await response.json();
6757
+ if (!response.ok) {
6758
+ throw new Error(`Stripe API error: ${data.error?.message || response.statusText}`);
6759
+ }
6760
+ return data;
6761
+ }
6762
+ };
6763
+ function timingSafeEqual(a, b) {
6764
+ if (a.length !== b.length) return false;
6765
+ let result = 0;
6766
+ for (let i = 0; i < a.length; i++) {
6767
+ result |= a.charCodeAt(i) ^ b.charCodeAt(i);
6768
+ }
6769
+ return result === 0;
6770
+ }
6771
+
6772
+ // src/plugins/core-plugins/stripe-plugin/routes/api.ts
6773
+ var apiRoutes3 = new hono.Hono();
6774
+ async function getSettings3(db) {
6775
+ try {
6776
+ const pluginService = new chunkI6FFGQIT_cjs.PluginService(db);
6777
+ const plugin2 = await pluginService.getPlugin("stripe");
6778
+ if (plugin2?.settings) {
6779
+ const settings = typeof plugin2.settings === "string" ? JSON.parse(plugin2.settings) : plugin2.settings;
6780
+ return { ...DEFAULT_SETTINGS3, ...settings };
6781
+ }
6782
+ } catch {
6783
+ }
6784
+ return DEFAULT_SETTINGS3;
6785
+ }
6786
+ function mapStripeStatus(status) {
6787
+ const map = {
6788
+ active: "active",
6789
+ canceled: "canceled",
6790
+ past_due: "past_due",
6791
+ trialing: "trialing",
6792
+ unpaid: "unpaid",
6793
+ paused: "paused",
6794
+ incomplete: "incomplete",
6795
+ incomplete_expired: "incomplete_expired"
6796
+ };
6797
+ return map[status] || "incomplete";
6798
+ }
6799
+ apiRoutes3.post("/webhook", async (c) => {
6800
+ const db = c.env.DB;
6801
+ const settings = await getSettings3(db);
6802
+ if (!settings.stripeWebhookSecret) {
6803
+ return c.json({ error: "Webhook secret not configured" }, 500);
6804
+ }
6805
+ const rawBody = await c.req.text();
6806
+ const sigHeader = c.req.header("stripe-signature") || "";
6807
+ const stripeApi = new StripeAPI(settings.stripeSecretKey);
6808
+ const isValid = await stripeApi.verifyWebhookSignature(rawBody, sigHeader, settings.stripeWebhookSecret);
6809
+ if (!isValid) {
6810
+ return c.json({ error: "Invalid signature" }, 400);
6811
+ }
6812
+ const event = JSON.parse(rawBody);
6813
+ const subscriptionService = new SubscriptionService(db);
6814
+ await subscriptionService.ensureTable();
6815
+ try {
6816
+ switch (event.type) {
6817
+ case "customer.subscription.created": {
6818
+ const sub = event.data.object;
6819
+ const userId = sub.metadata?.sonicjs_user_id || await subscriptionService.getUserIdByStripeCustomer(sub.customer) || "";
6820
+ await subscriptionService.create({
6821
+ userId,
6822
+ stripeCustomerId: sub.customer,
6823
+ stripeSubscriptionId: sub.id,
6824
+ stripePriceId: sub.items.data[0]?.price.id || "",
6825
+ status: mapStripeStatus(sub.status),
6826
+ currentPeriodStart: sub.current_period_start,
6827
+ currentPeriodEnd: sub.current_period_end,
6828
+ cancelAtPeriodEnd: sub.cancel_at_period_end
6829
+ });
6830
+ console.log(`[Stripe] Subscription created: ${sub.id}`);
6831
+ break;
6832
+ }
6833
+ case "customer.subscription.updated": {
6834
+ const sub = event.data.object;
6835
+ await subscriptionService.updateByStripeId(sub.id, {
6836
+ status: mapStripeStatus(sub.status),
6837
+ stripePriceId: sub.items.data[0]?.price.id || void 0,
6838
+ currentPeriodStart: sub.current_period_start,
6839
+ currentPeriodEnd: sub.current_period_end,
6840
+ cancelAtPeriodEnd: sub.cancel_at_period_end
6841
+ });
6842
+ console.log(`[Stripe] Subscription updated: ${sub.id} -> ${sub.status}`);
6843
+ break;
6844
+ }
6845
+ case "customer.subscription.deleted": {
6846
+ const sub = event.data.object;
6847
+ await subscriptionService.updateByStripeId(sub.id, {
6848
+ status: "canceled"
6849
+ });
6850
+ console.log(`[Stripe] Subscription deleted: ${sub.id}`);
6851
+ break;
6852
+ }
6853
+ case "checkout.session.completed": {
6854
+ const session = event.data.object;
6855
+ const userId = session.metadata?.sonicjs_user_id;
6856
+ if (userId && session.subscription) {
6857
+ const existing = await subscriptionService.getByStripeSubscriptionId(session.subscription);
6858
+ if (existing && !existing.userId) {
6859
+ await subscriptionService.updateByStripeId(session.subscription, {
6860
+ userId
6861
+ });
6862
+ }
6863
+ }
6864
+ console.log(`[Stripe] Checkout completed: ${session.id}`);
6865
+ break;
6866
+ }
6867
+ case "invoice.payment_succeeded": {
6868
+ const invoice = event.data.object;
6869
+ if (invoice.subscription) {
6870
+ await subscriptionService.updateByStripeId(invoice.subscription, {
6871
+ status: "active"
6872
+ });
6873
+ }
6874
+ console.log(`[Stripe] Payment succeeded for invoice: ${invoice.id}`);
6875
+ break;
6876
+ }
6877
+ case "invoice.payment_failed": {
6878
+ const invoice = event.data.object;
6879
+ if (invoice.subscription) {
6880
+ await subscriptionService.updateByStripeId(invoice.subscription, {
6881
+ status: "past_due"
6882
+ });
6883
+ }
6884
+ console.log(`[Stripe] Payment failed for invoice: ${invoice.id}`);
6885
+ break;
6886
+ }
6887
+ default:
6888
+ console.log(`[Stripe] Unhandled event type: ${event.type}`);
6889
+ }
6890
+ } catch (error) {
6891
+ console.error(`[Stripe] Error processing webhook event ${event.type}:`, error);
6892
+ return c.json({ error: "Webhook processing failed" }, 500);
6893
+ }
6894
+ return c.json({ received: true });
6895
+ });
6896
+ apiRoutes3.post("/create-checkout-session", chunkYYMPHM3I_cjs.requireAuth(), async (c) => {
6897
+ const db = c.env.DB;
6898
+ const user = c.get("user");
6899
+ if (!user) return c.json({ error: "Unauthorized" }, 401);
6900
+ const settings = await getSettings3(db);
6901
+ if (!settings.stripeSecretKey) {
6902
+ return c.json({ error: "Stripe not configured" }, 500);
6903
+ }
6904
+ const body = await c.req.json().catch(() => ({}));
6905
+ const priceId = body.priceId || settings.stripePriceId;
6906
+ if (!priceId) {
6907
+ return c.json({ error: "No price ID specified" }, 400);
6908
+ }
6909
+ const stripeApi = new StripeAPI(settings.stripeSecretKey);
6910
+ const subscriptionService = new SubscriptionService(db);
6911
+ await subscriptionService.ensureTable();
6912
+ const existingSub = await subscriptionService.getByUserId(user.userId);
6913
+ let customerId = existingSub?.stripeCustomerId;
6914
+ if (!customerId) {
6915
+ const existing = await stripeApi.findCustomerByEmail(user.email);
6916
+ if (existing) {
6917
+ customerId = existing.id;
6918
+ } else {
6919
+ const customer = await stripeApi.createCustomer({
6920
+ email: user.email,
6921
+ metadata: { sonicjs_user_id: user.userId }
6922
+ });
6923
+ customerId = customer.id;
6924
+ }
6925
+ }
6926
+ const origin = new URL(c.req.url).origin;
6927
+ const session = await stripeApi.createCheckoutSession({
6928
+ priceId,
6929
+ customerId,
6930
+ successUrl: `${origin}${settings.successUrl}?session_id={CHECKOUT_SESSION_ID}`,
6931
+ cancelUrl: `${origin}${settings.cancelUrl}`,
6932
+ metadata: { sonicjs_user_id: user.userId }
6933
+ });
6934
+ return c.json({ sessionId: session.id, url: session.url });
6935
+ });
6936
+ apiRoutes3.get("/subscription", chunkYYMPHM3I_cjs.requireAuth(), async (c) => {
6937
+ const user = c.get("user");
6938
+ if (!user) return c.json({ error: "Unauthorized" }, 401);
6939
+ const db = c.env.DB;
6940
+ const subscriptionService = new SubscriptionService(db);
6941
+ await subscriptionService.ensureTable();
6942
+ const subscription = await subscriptionService.getByUserId(user.userId);
6943
+ if (!subscription) {
6944
+ return c.json({ subscription: null });
6945
+ }
6946
+ return c.json({ subscription });
6947
+ });
6948
+ apiRoutes3.get("/subscriptions", chunkYYMPHM3I_cjs.requireAuth(), async (c) => {
6949
+ const user = c.get("user");
6950
+ if (user?.role !== "admin") return c.json({ error: "Access denied" }, 403);
6951
+ const db = c.env.DB;
6952
+ const subscriptionService = new SubscriptionService(db);
6953
+ await subscriptionService.ensureTable();
6954
+ const filters = {
6955
+ status: c.req.query("status"),
6956
+ page: c.req.query("page") ? parseInt(c.req.query("page")) : 1,
6957
+ limit: c.req.query("limit") ? parseInt(c.req.query("limit")) : 50,
6958
+ sortBy: c.req.query("sortBy") || "created_at",
6959
+ sortOrder: c.req.query("sortOrder") || "desc"
6960
+ };
6961
+ const result = await subscriptionService.list(filters);
6962
+ return c.json(result);
6963
+ });
6964
+ apiRoutes3.get("/stats", chunkYYMPHM3I_cjs.requireAuth(), async (c) => {
6965
+ const user = c.get("user");
6966
+ if (user?.role !== "admin") return c.json({ error: "Access denied" }, 403);
6967
+ const db = c.env.DB;
6968
+ const subscriptionService = new SubscriptionService(db);
6969
+ await subscriptionService.ensureTable();
6970
+ const stats = await subscriptionService.getStats();
6971
+ return c.json(stats);
6972
+ });
6973
+
6974
+ // src/plugins/core-plugins/stripe-plugin/index.ts
6975
+ function createStripePlugin() {
6976
+ const builder = chunk6FHNRRJ3_cjs.PluginBuilder.create({
6977
+ name: "stripe",
6978
+ version: "1.0.0-beta.1",
6979
+ description: "Stripe subscription management with webhook handling, checkout sessions, and subscription gating"
6980
+ });
6981
+ builder.metadata({
6982
+ author: { name: "SonicJS Team" },
6983
+ license: "MIT"
6984
+ });
6985
+ builder.addRoute("/admin/plugins/stripe", adminRoutes3, {
6986
+ description: "Stripe subscriptions admin dashboard",
6987
+ requiresAuth: true,
6988
+ priority: 50
6989
+ });
6990
+ builder.addRoute("/api/stripe", apiRoutes3, {
6991
+ description: "Stripe API endpoints (webhook, checkout, subscription)",
6992
+ requiresAuth: false,
6993
+ // Webhook route handles its own auth via signature
6994
+ priority: 50
6995
+ });
6996
+ builder.addMenuItem("Stripe", "/admin/plugins/stripe", {
6997
+ icon: `<svg class="h-5 w-5" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M3 10h18M7 15h1m4 0h1m-7 4h12a3 3 0 003-3V8a3 3 0 00-3-3H6a3 3 0 00-3 3v8a3 3 0 003 3z"/></svg>`,
6998
+ order: 75
6999
+ });
7000
+ builder.lifecycle({
7001
+ install: async () => {
7002
+ console.log("[Stripe] Plugin installed");
7003
+ },
7004
+ activate: async () => {
7005
+ console.log("[Stripe] Plugin activated");
7006
+ },
7007
+ deactivate: async () => {
7008
+ console.log("[Stripe] Plugin deactivated");
7009
+ },
7010
+ uninstall: async () => {
7011
+ console.log("[Stripe] Plugin uninstalled");
7012
+ }
7013
+ });
7014
+ return builder.build();
7015
+ }
7016
+ var stripePlugin = createStripePlugin();
7017
+
6269
7018
  // src/middleware/plugin-menu.ts
6270
7019
  var MENU_PLUGINS = [
6271
7020
  securityAuditPlugin
@@ -7472,7 +8221,7 @@ function renderCacheDashboard(data) {
7472
8221
  </script>
7473
8222
 
7474
8223
  <!-- Confirmation Dialogs -->
7475
- ${chunkHVTSE2SF_cjs.renderConfirmationDialog({
8224
+ ${chunkDRWSHIFG_cjs.renderConfirmationDialog({
7476
8225
  id: "clear-all-cache-confirm",
7477
8226
  title: "Clear All Cache",
7478
8227
  message: "Are you sure you want to clear all cache entries? This cannot be undone.",
@@ -7483,7 +8232,7 @@ function renderCacheDashboard(data) {
7483
8232
  onConfirm: "performClearAllCaches()"
7484
8233
  })}
7485
8234
 
7486
- ${chunkHVTSE2SF_cjs.renderConfirmationDialog({
8235
+ ${chunkDRWSHIFG_cjs.renderConfirmationDialog({
7487
8236
  id: "clear-namespace-cache-confirm",
7488
8237
  title: "Clear Namespace Cache",
7489
8238
  message: "Clear cache for this namespace?",
@@ -7494,7 +8243,7 @@ function renderCacheDashboard(data) {
7494
8243
  onConfirm: "performClearNamespaceCache()"
7495
8244
  })}
7496
8245
 
7497
- ${chunkHVTSE2SF_cjs.getConfirmationDialogScript()}
8246
+ ${chunkDRWSHIFG_cjs.getConfirmationDialogScript()}
7498
8247
  `;
7499
8248
  const layoutData = {
7500
8249
  title: "Cache System",
@@ -8180,14 +8929,14 @@ var faviconSvg = `<?xml version="1.0" encoding="UTF-8" standalone="no"?>
8180
8929
  // src/app.ts
8181
8930
  function createSonicJSApp(config = {}) {
8182
8931
  const app2 = new hono.Hono();
8183
- const appVersion = config.version || chunkXCP5GCBE_cjs.getCoreVersion();
8932
+ const appVersion = config.version || chunkYULUPQZV_cjs.getCoreVersion();
8184
8933
  const appName = config.name || "SonicJS AI";
8185
8934
  app2.use("*", async (c, next) => {
8186
8935
  c.set("appVersion", appVersion);
8187
8936
  await next();
8188
8937
  });
8189
- app2.use("*", chunkEGUDIX6Q_cjs.metricsMiddleware());
8190
- app2.use("*", chunkEGUDIX6Q_cjs.bootstrapMiddleware(config));
8938
+ app2.use("*", chunkYYMPHM3I_cjs.metricsMiddleware());
8939
+ app2.use("*", chunkYYMPHM3I_cjs.bootstrapMiddleware(config));
8191
8940
  if (config.middleware?.beforeAuth) {
8192
8941
  for (const middleware of config.middleware.beforeAuth) {
8193
8942
  app2.use("*", middleware);
@@ -8196,29 +8945,29 @@ function createSonicJSApp(config = {}) {
8196
8945
  app2.use("*", async (_c, next) => {
8197
8946
  await next();
8198
8947
  });
8199
- app2.use("*", chunkEGUDIX6Q_cjs.securityHeadersMiddleware());
8200
- app2.use("*", chunkEGUDIX6Q_cjs.csrfProtection());
8948
+ app2.use("*", chunkYYMPHM3I_cjs.securityHeadersMiddleware());
8949
+ app2.use("*", chunkYYMPHM3I_cjs.csrfProtection());
8201
8950
  if (config.middleware?.afterAuth) {
8202
8951
  for (const middleware of config.middleware.afterAuth) {
8203
8952
  app2.use("*", middleware);
8204
8953
  }
8205
8954
  }
8206
8955
  app2.use("/admin/*", pluginMenuMiddleware());
8207
- app2.route("/api", chunkHVTSE2SF_cjs.api_default);
8208
- app2.route("/api/media", chunkHVTSE2SF_cjs.api_media_default);
8209
- app2.route("/api/system", chunkHVTSE2SF_cjs.api_system_default);
8210
- app2.route("/admin/api", chunkHVTSE2SF_cjs.admin_api_default);
8211
- app2.route("/admin/dashboard", chunkHVTSE2SF_cjs.router);
8212
- app2.route("/admin/collections", chunkHVTSE2SF_cjs.adminCollectionsRoutes);
8213
- app2.route("/admin/forms", chunkHVTSE2SF_cjs.adminFormsRoutes);
8214
- app2.route("/admin/settings", chunkHVTSE2SF_cjs.adminSettingsRoutes);
8215
- app2.route("/forms", chunkHVTSE2SF_cjs.public_forms_default);
8216
- app2.route("/api/forms", chunkHVTSE2SF_cjs.public_forms_default);
8217
- app2.route("/admin/api-reference", chunkHVTSE2SF_cjs.router2);
8956
+ app2.route("/api", chunkDRWSHIFG_cjs.api_default);
8957
+ app2.route("/api/media", chunkDRWSHIFG_cjs.api_media_default);
8958
+ app2.route("/api/system", chunkDRWSHIFG_cjs.api_system_default);
8959
+ app2.route("/admin/api", chunkDRWSHIFG_cjs.admin_api_default);
8960
+ app2.route("/admin/dashboard", chunkDRWSHIFG_cjs.router);
8961
+ app2.route("/admin/collections", chunkDRWSHIFG_cjs.adminCollectionsRoutes);
8962
+ app2.route("/admin/forms", chunkDRWSHIFG_cjs.adminFormsRoutes);
8963
+ app2.route("/admin/settings", chunkDRWSHIFG_cjs.adminSettingsRoutes);
8964
+ app2.route("/forms", chunkDRWSHIFG_cjs.public_forms_default);
8965
+ app2.route("/api/forms", chunkDRWSHIFG_cjs.public_forms_default);
8966
+ app2.route("/admin/api-reference", chunkDRWSHIFG_cjs.router2);
8218
8967
  app2.route("/admin/database-tools", createDatabaseToolsAdminRoutes());
8219
8968
  app2.route("/admin/seed-data", createSeedDataAdminRoutes());
8220
- app2.route("/admin/content", chunkHVTSE2SF_cjs.admin_content_default);
8221
- app2.route("/admin/media", chunkHVTSE2SF_cjs.adminMediaRoutes);
8969
+ app2.route("/admin/content", chunkDRWSHIFG_cjs.admin_content_default);
8970
+ app2.route("/admin/media", chunkDRWSHIFG_cjs.adminMediaRoutes);
8222
8971
  app2.use("/auth/*", securityAuditMiddleware());
8223
8972
  if (securityAuditPlugin.routes && securityAuditPlugin.routes.length > 0) {
8224
8973
  for (const route of securityAuditPlugin.routes) {
@@ -8236,8 +8985,8 @@ function createSonicJSApp(config = {}) {
8236
8985
  app2.route(route.path, route.handler);
8237
8986
  }
8238
8987
  }
8239
- if (chunkHVTSE2SF_cjs.userProfilesPlugin.routes && chunkHVTSE2SF_cjs.userProfilesPlugin.routes.length > 0) {
8240
- for (const route of chunkHVTSE2SF_cjs.userProfilesPlugin.routes) {
8988
+ if (chunkDRWSHIFG_cjs.userProfilesPlugin.routes && chunkDRWSHIFG_cjs.userProfilesPlugin.routes.length > 0) {
8989
+ for (const route of chunkDRWSHIFG_cjs.userProfilesPlugin.routes) {
8241
8990
  app2.route(route.path, route.handler);
8242
8991
  }
8243
8992
  }
@@ -8246,11 +8995,16 @@ function createSonicJSApp(config = {}) {
8246
8995
  app2.route(route.path, route.handler);
8247
8996
  }
8248
8997
  }
8249
- app2.route("/admin/plugins", chunkHVTSE2SF_cjs.adminPluginRoutes);
8250
- app2.route("/admin/logs", chunkHVTSE2SF_cjs.adminLogsRoutes);
8251
- app2.route("/admin", chunkHVTSE2SF_cjs.userRoutes);
8252
- app2.route("/auth", chunkHVTSE2SF_cjs.auth_default);
8253
- app2.route("/", chunkHVTSE2SF_cjs.test_cleanup_default);
8998
+ app2.route("/admin/plugins", chunkDRWSHIFG_cjs.adminPluginRoutes);
8999
+ app2.route("/admin/logs", chunkDRWSHIFG_cjs.adminLogsRoutes);
9000
+ app2.route("/admin", chunkDRWSHIFG_cjs.userRoutes);
9001
+ app2.route("/auth", chunkDRWSHIFG_cjs.auth_default);
9002
+ app2.route("/", chunkDRWSHIFG_cjs.test_cleanup_default);
9003
+ if (stripePlugin.routes && stripePlugin.routes.length > 0) {
9004
+ for (const route of stripePlugin.routes) {
9005
+ app2.route(route.path, route.handler);
9006
+ }
9007
+ }
8254
9008
  if (emailPlugin.routes && emailPlugin.routes.length > 0) {
8255
9009
  for (const route of emailPlugin.routes) {
8256
9010
  app2.route(route.path, route.handler);
@@ -8334,99 +9088,99 @@ function createDb(d1$1) {
8334
9088
  }
8335
9089
 
8336
9090
  // src/index.ts
8337
- var VERSION = chunkXCP5GCBE_cjs.package_default.version;
9091
+ var VERSION = chunkYULUPQZV_cjs.package_default.version;
8338
9092
 
8339
9093
  Object.defineProperty(exports, "ROUTES_INFO", {
8340
9094
  enumerable: true,
8341
- get: function () { return chunkHVTSE2SF_cjs.ROUTES_INFO; }
9095
+ get: function () { return chunkDRWSHIFG_cjs.ROUTES_INFO; }
8342
9096
  });
8343
9097
  Object.defineProperty(exports, "adminApiRoutes", {
8344
9098
  enumerable: true,
8345
- get: function () { return chunkHVTSE2SF_cjs.admin_api_default; }
9099
+ get: function () { return chunkDRWSHIFG_cjs.admin_api_default; }
8346
9100
  });
8347
9101
  Object.defineProperty(exports, "adminCheckboxRoutes", {
8348
9102
  enumerable: true,
8349
- get: function () { return chunkHVTSE2SF_cjs.adminCheckboxRoutes; }
9103
+ get: function () { return chunkDRWSHIFG_cjs.adminCheckboxRoutes; }
8350
9104
  });
8351
9105
  Object.defineProperty(exports, "adminCodeExamplesRoutes", {
8352
9106
  enumerable: true,
8353
- get: function () { return chunkHVTSE2SF_cjs.admin_code_examples_default; }
9107
+ get: function () { return chunkDRWSHIFG_cjs.admin_code_examples_default; }
8354
9108
  });
8355
9109
  Object.defineProperty(exports, "adminCollectionsRoutes", {
8356
9110
  enumerable: true,
8357
- get: function () { return chunkHVTSE2SF_cjs.adminCollectionsRoutes; }
9111
+ get: function () { return chunkDRWSHIFG_cjs.adminCollectionsRoutes; }
8358
9112
  });
8359
9113
  Object.defineProperty(exports, "adminContentRoutes", {
8360
9114
  enumerable: true,
8361
- get: function () { return chunkHVTSE2SF_cjs.admin_content_default; }
9115
+ get: function () { return chunkDRWSHIFG_cjs.admin_content_default; }
8362
9116
  });
8363
9117
  Object.defineProperty(exports, "adminDashboardRoutes", {
8364
9118
  enumerable: true,
8365
- get: function () { return chunkHVTSE2SF_cjs.router; }
9119
+ get: function () { return chunkDRWSHIFG_cjs.router; }
8366
9120
  });
8367
9121
  Object.defineProperty(exports, "adminDesignRoutes", {
8368
9122
  enumerable: true,
8369
- get: function () { return chunkHVTSE2SF_cjs.adminDesignRoutes; }
9123
+ get: function () { return chunkDRWSHIFG_cjs.adminDesignRoutes; }
8370
9124
  });
8371
9125
  Object.defineProperty(exports, "adminLogsRoutes", {
8372
9126
  enumerable: true,
8373
- get: function () { return chunkHVTSE2SF_cjs.adminLogsRoutes; }
9127
+ get: function () { return chunkDRWSHIFG_cjs.adminLogsRoutes; }
8374
9128
  });
8375
9129
  Object.defineProperty(exports, "adminMediaRoutes", {
8376
9130
  enumerable: true,
8377
- get: function () { return chunkHVTSE2SF_cjs.adminMediaRoutes; }
9131
+ get: function () { return chunkDRWSHIFG_cjs.adminMediaRoutes; }
8378
9132
  });
8379
9133
  Object.defineProperty(exports, "adminPluginRoutes", {
8380
9134
  enumerable: true,
8381
- get: function () { return chunkHVTSE2SF_cjs.adminPluginRoutes; }
9135
+ get: function () { return chunkDRWSHIFG_cjs.adminPluginRoutes; }
8382
9136
  });
8383
9137
  Object.defineProperty(exports, "adminSettingsRoutes", {
8384
9138
  enumerable: true,
8385
- get: function () { return chunkHVTSE2SF_cjs.adminSettingsRoutes; }
9139
+ get: function () { return chunkDRWSHIFG_cjs.adminSettingsRoutes; }
8386
9140
  });
8387
9141
  Object.defineProperty(exports, "adminTestimonialsRoutes", {
8388
9142
  enumerable: true,
8389
- get: function () { return chunkHVTSE2SF_cjs.admin_testimonials_default; }
9143
+ get: function () { return chunkDRWSHIFG_cjs.admin_testimonials_default; }
8390
9144
  });
8391
9145
  Object.defineProperty(exports, "adminUsersRoutes", {
8392
9146
  enumerable: true,
8393
- get: function () { return chunkHVTSE2SF_cjs.userRoutes; }
9147
+ get: function () { return chunkDRWSHIFG_cjs.userRoutes; }
8394
9148
  });
8395
9149
  Object.defineProperty(exports, "apiContentCrudRoutes", {
8396
9150
  enumerable: true,
8397
- get: function () { return chunkHVTSE2SF_cjs.api_content_crud_default; }
9151
+ get: function () { return chunkDRWSHIFG_cjs.api_content_crud_default; }
8398
9152
  });
8399
9153
  Object.defineProperty(exports, "apiMediaRoutes", {
8400
9154
  enumerable: true,
8401
- get: function () { return chunkHVTSE2SF_cjs.api_media_default; }
9155
+ get: function () { return chunkDRWSHIFG_cjs.api_media_default; }
8402
9156
  });
8403
9157
  Object.defineProperty(exports, "apiRoutes", {
8404
9158
  enumerable: true,
8405
- get: function () { return chunkHVTSE2SF_cjs.api_default; }
9159
+ get: function () { return chunkDRWSHIFG_cjs.api_default; }
8406
9160
  });
8407
9161
  Object.defineProperty(exports, "apiSystemRoutes", {
8408
9162
  enumerable: true,
8409
- get: function () { return chunkHVTSE2SF_cjs.api_system_default; }
9163
+ get: function () { return chunkDRWSHIFG_cjs.api_system_default; }
8410
9164
  });
8411
9165
  Object.defineProperty(exports, "authRoutes", {
8412
9166
  enumerable: true,
8413
- get: function () { return chunkHVTSE2SF_cjs.auth_default; }
9167
+ get: function () { return chunkDRWSHIFG_cjs.auth_default; }
8414
9168
  });
8415
9169
  Object.defineProperty(exports, "createUserProfilesPlugin", {
8416
9170
  enumerable: true,
8417
- get: function () { return chunkHVTSE2SF_cjs.createUserProfilesPlugin; }
9171
+ get: function () { return chunkDRWSHIFG_cjs.createUserProfilesPlugin; }
8418
9172
  });
8419
9173
  Object.defineProperty(exports, "defineUserProfile", {
8420
9174
  enumerable: true,
8421
- get: function () { return chunkHVTSE2SF_cjs.defineUserProfile; }
9175
+ get: function () { return chunkDRWSHIFG_cjs.defineUserProfile; }
8422
9176
  });
8423
9177
  Object.defineProperty(exports, "getUserProfileConfig", {
8424
9178
  enumerable: true,
8425
- get: function () { return chunkHVTSE2SF_cjs.getUserProfileConfig; }
9179
+ get: function () { return chunkDRWSHIFG_cjs.getUserProfileConfig; }
8426
9180
  });
8427
9181
  Object.defineProperty(exports, "userProfilesPlugin", {
8428
9182
  enumerable: true,
8429
- get: function () { return chunkHVTSE2SF_cjs.userProfilesPlugin; }
9183
+ get: function () { return chunkDRWSHIFG_cjs.userProfilesPlugin; }
8430
9184
  });
8431
9185
  Object.defineProperty(exports, "Logger", {
8432
9186
  enumerable: true,
@@ -8594,83 +9348,83 @@ Object.defineProperty(exports, "workflowHistory", {
8594
9348
  });
8595
9349
  Object.defineProperty(exports, "AuthManager", {
8596
9350
  enumerable: true,
8597
- get: function () { return chunkEGUDIX6Q_cjs.AuthManager; }
9351
+ get: function () { return chunkYYMPHM3I_cjs.AuthManager; }
8598
9352
  });
8599
9353
  Object.defineProperty(exports, "PermissionManager", {
8600
9354
  enumerable: true,
8601
- get: function () { return chunkEGUDIX6Q_cjs.PermissionManager; }
9355
+ get: function () { return chunkYYMPHM3I_cjs.PermissionManager; }
8602
9356
  });
8603
9357
  Object.defineProperty(exports, "bootstrapMiddleware", {
8604
9358
  enumerable: true,
8605
- get: function () { return chunkEGUDIX6Q_cjs.bootstrapMiddleware; }
9359
+ get: function () { return chunkYYMPHM3I_cjs.bootstrapMiddleware; }
8606
9360
  });
8607
9361
  Object.defineProperty(exports, "cacheHeaders", {
8608
9362
  enumerable: true,
8609
- get: function () { return chunkEGUDIX6Q_cjs.cacheHeaders; }
9363
+ get: function () { return chunkYYMPHM3I_cjs.cacheHeaders; }
8610
9364
  });
8611
9365
  Object.defineProperty(exports, "compressionMiddleware", {
8612
9366
  enumerable: true,
8613
- get: function () { return chunkEGUDIX6Q_cjs.compressionMiddleware; }
9367
+ get: function () { return chunkYYMPHM3I_cjs.compressionMiddleware; }
8614
9368
  });
8615
9369
  Object.defineProperty(exports, "detailedLoggingMiddleware", {
8616
9370
  enumerable: true,
8617
- get: function () { return chunkEGUDIX6Q_cjs.detailedLoggingMiddleware; }
9371
+ get: function () { return chunkYYMPHM3I_cjs.detailedLoggingMiddleware; }
8618
9372
  });
8619
9373
  Object.defineProperty(exports, "getActivePlugins", {
8620
9374
  enumerable: true,
8621
- get: function () { return chunkEGUDIX6Q_cjs.getActivePlugins; }
9375
+ get: function () { return chunkYYMPHM3I_cjs.getActivePlugins; }
8622
9376
  });
8623
9377
  Object.defineProperty(exports, "isPluginActive", {
8624
9378
  enumerable: true,
8625
- get: function () { return chunkEGUDIX6Q_cjs.isPluginActive; }
9379
+ get: function () { return chunkYYMPHM3I_cjs.isPluginActive; }
8626
9380
  });
8627
9381
  Object.defineProperty(exports, "logActivity", {
8628
9382
  enumerable: true,
8629
- get: function () { return chunkEGUDIX6Q_cjs.logActivity; }
9383
+ get: function () { return chunkYYMPHM3I_cjs.logActivity; }
8630
9384
  });
8631
9385
  Object.defineProperty(exports, "loggingMiddleware", {
8632
9386
  enumerable: true,
8633
- get: function () { return chunkEGUDIX6Q_cjs.loggingMiddleware; }
9387
+ get: function () { return chunkYYMPHM3I_cjs.loggingMiddleware; }
8634
9388
  });
8635
9389
  Object.defineProperty(exports, "optionalAuth", {
8636
9390
  enumerable: true,
8637
- get: function () { return chunkEGUDIX6Q_cjs.optionalAuth; }
9391
+ get: function () { return chunkYYMPHM3I_cjs.optionalAuth; }
8638
9392
  });
8639
9393
  Object.defineProperty(exports, "performanceLoggingMiddleware", {
8640
9394
  enumerable: true,
8641
- get: function () { return chunkEGUDIX6Q_cjs.performanceLoggingMiddleware; }
9395
+ get: function () { return chunkYYMPHM3I_cjs.performanceLoggingMiddleware; }
8642
9396
  });
8643
9397
  Object.defineProperty(exports, "requireActivePlugin", {
8644
9398
  enumerable: true,
8645
- get: function () { return chunkEGUDIX6Q_cjs.requireActivePlugin; }
9399
+ get: function () { return chunkYYMPHM3I_cjs.requireActivePlugin; }
8646
9400
  });
8647
9401
  Object.defineProperty(exports, "requireActivePlugins", {
8648
9402
  enumerable: true,
8649
- get: function () { return chunkEGUDIX6Q_cjs.requireActivePlugins; }
9403
+ get: function () { return chunkYYMPHM3I_cjs.requireActivePlugins; }
8650
9404
  });
8651
9405
  Object.defineProperty(exports, "requireAnyPermission", {
8652
9406
  enumerable: true,
8653
- get: function () { return chunkEGUDIX6Q_cjs.requireAnyPermission; }
9407
+ get: function () { return chunkYYMPHM3I_cjs.requireAnyPermission; }
8654
9408
  });
8655
9409
  Object.defineProperty(exports, "requireAuth", {
8656
9410
  enumerable: true,
8657
- get: function () { return chunkEGUDIX6Q_cjs.requireAuth; }
9411
+ get: function () { return chunkYYMPHM3I_cjs.requireAuth; }
8658
9412
  });
8659
9413
  Object.defineProperty(exports, "requirePermission", {
8660
9414
  enumerable: true,
8661
- get: function () { return chunkEGUDIX6Q_cjs.requirePermission; }
9415
+ get: function () { return chunkYYMPHM3I_cjs.requirePermission; }
8662
9416
  });
8663
9417
  Object.defineProperty(exports, "requireRole", {
8664
9418
  enumerable: true,
8665
- get: function () { return chunkEGUDIX6Q_cjs.requireRole; }
9419
+ get: function () { return chunkYYMPHM3I_cjs.requireRole; }
8666
9420
  });
8667
9421
  Object.defineProperty(exports, "securityHeaders", {
8668
9422
  enumerable: true,
8669
- get: function () { return chunkEGUDIX6Q_cjs.securityHeadersMiddleware; }
9423
+ get: function () { return chunkYYMPHM3I_cjs.securityHeadersMiddleware; }
8670
9424
  });
8671
9425
  Object.defineProperty(exports, "securityLoggingMiddleware", {
8672
9426
  enumerable: true,
8673
- get: function () { return chunkEGUDIX6Q_cjs.securityLoggingMiddleware; }
9427
+ get: function () { return chunkYYMPHM3I_cjs.securityLoggingMiddleware; }
8674
9428
  });
8675
9429
  Object.defineProperty(exports, "PluginBootstrapService", {
8676
9430
  enumerable: true,
@@ -8754,7 +9508,7 @@ Object.defineProperty(exports, "validateCollectionConfig", {
8754
9508
  });
8755
9509
  Object.defineProperty(exports, "MigrationService", {
8756
9510
  enumerable: true,
8757
- get: function () { return chunkSER23XI4_cjs.MigrationService; }
9511
+ get: function () { return chunkKZ2MFGET_cjs.MigrationService; }
8758
9512
  });
8759
9513
  Object.defineProperty(exports, "renderFilterBar", {
8760
9514
  enumerable: true,
@@ -8822,31 +9576,31 @@ Object.defineProperty(exports, "PluginHelpers", {
8822
9576
  });
8823
9577
  Object.defineProperty(exports, "QueryFilterBuilder", {
8824
9578
  enumerable: true,
8825
- get: function () { return chunkXCP5GCBE_cjs.QueryFilterBuilder; }
9579
+ get: function () { return chunkYULUPQZV_cjs.QueryFilterBuilder; }
8826
9580
  });
8827
9581
  Object.defineProperty(exports, "SONICJS_VERSION", {
8828
9582
  enumerable: true,
8829
- get: function () { return chunkXCP5GCBE_cjs.SONICJS_VERSION; }
9583
+ get: function () { return chunkYULUPQZV_cjs.SONICJS_VERSION; }
8830
9584
  });
8831
9585
  Object.defineProperty(exports, "TemplateRenderer", {
8832
9586
  enumerable: true,
8833
- get: function () { return chunkXCP5GCBE_cjs.TemplateRenderer; }
9587
+ get: function () { return chunkYULUPQZV_cjs.TemplateRenderer; }
8834
9588
  });
8835
9589
  Object.defineProperty(exports, "buildQuery", {
8836
9590
  enumerable: true,
8837
- get: function () { return chunkXCP5GCBE_cjs.buildQuery; }
9591
+ get: function () { return chunkYULUPQZV_cjs.buildQuery; }
8838
9592
  });
8839
9593
  Object.defineProperty(exports, "getCoreVersion", {
8840
9594
  enumerable: true,
8841
- get: function () { return chunkXCP5GCBE_cjs.getCoreVersion; }
9595
+ get: function () { return chunkYULUPQZV_cjs.getCoreVersion; }
8842
9596
  });
8843
9597
  Object.defineProperty(exports, "renderTemplate", {
8844
9598
  enumerable: true,
8845
- get: function () { return chunkXCP5GCBE_cjs.renderTemplate; }
9599
+ get: function () { return chunkYULUPQZV_cjs.renderTemplate; }
8846
9600
  });
8847
9601
  Object.defineProperty(exports, "templateRenderer", {
8848
9602
  enumerable: true,
8849
- get: function () { return chunkXCP5GCBE_cjs.templateRenderer; }
9603
+ get: function () { return chunkYULUPQZV_cjs.templateRenderer; }
8850
9604
  });
8851
9605
  Object.defineProperty(exports, "metricsTracker", {
8852
9606
  enumerable: true,