@hot-updater/server 1.0.0-rc.1 → 1.0.0-rc.2

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 (191) hide show
  1. package/dist/_virtual/_rolldown/runtime.cjs +1 -1
  2. package/dist/adapters/databaseConstraintErrors.cjs +0 -1
  3. package/dist/adapters/databasePluginUtils.cjs +0 -1
  4. package/dist/adapters/drizzle.cjs +10 -3
  5. package/dist/adapters/drizzle.d.cts +0 -1
  6. package/dist/adapters/drizzle.d.mts +0 -1
  7. package/dist/adapters/drizzle.mjs +11 -3
  8. package/dist/adapters/drizzleCrud.cjs +62 -1
  9. package/dist/adapters/drizzleCrud.mjs +61 -2
  10. package/dist/adapters/drizzleLazyDB.cjs +6 -1
  11. package/dist/adapters/drizzleLazyDB.mjs +6 -1
  12. package/dist/adapters/drizzleQuery.cjs +3 -2
  13. package/dist/adapters/drizzleQuery.mjs +3 -1
  14. package/dist/adapters/insightsTransaction.cjs +22 -0
  15. package/dist/adapters/insightsTransaction.mjs +22 -0
  16. package/dist/adapters/kysely.cjs +2 -1
  17. package/dist/adapters/kysely.d.cts +0 -1
  18. package/dist/adapters/kysely.d.mts +0 -1
  19. package/dist/adapters/kysely.mjs +3 -1
  20. package/dist/adapters/kyselyCrud.cjs +54 -3
  21. package/dist/adapters/kyselyCrud.mjs +54 -3
  22. package/dist/adapters/kyselyQuery.cjs +2 -2
  23. package/dist/adapters/kyselyQuery.mjs +2 -1
  24. package/dist/adapters/mongodb.cjs +27 -1
  25. package/dist/adapters/mongodb.d.cts +1 -1
  26. package/dist/adapters/mongodb.d.mts +1 -1
  27. package/dist/adapters/mongodb.mjs +28 -1
  28. package/dist/adapters/mongodbCollections.cjs +2 -0
  29. package/dist/adapters/mongodbCollections.mjs +2 -0
  30. package/dist/adapters/mongodbQuery.cjs +21 -4
  31. package/dist/adapters/mongodbQuery.mjs +21 -5
  32. package/dist/adapters/mongodbReads.cjs +91 -29
  33. package/dist/adapters/mongodbReads.mjs +92 -29
  34. package/dist/adapters/mongodbWrites.cjs +16 -2
  35. package/dist/adapters/mongodbWrites.mjs +18 -3
  36. package/dist/adapters/prisma.cjs +55 -7
  37. package/dist/adapters/prisma.d.cts +0 -1
  38. package/dist/adapters/prisma.d.mts +0 -1
  39. package/dist/adapters/prisma.mjs +56 -7
  40. package/dist/adapters/prismaQuery.cjs +0 -1
  41. package/dist/adapters/prismaRows.cjs +22 -1
  42. package/dist/adapters/prismaRows.mjs +22 -1
  43. package/dist/apiKeys.cjs +6 -2
  44. package/dist/apiKeys.d.cts +0 -1
  45. package/dist/apiKeys.d.mts +0 -1
  46. package/dist/apiKeys.mjs +3 -3
  47. package/dist/createHotUpdaterCore.cjs +24 -9
  48. package/dist/createHotUpdaterCore.d.cts +1 -1
  49. package/dist/createHotUpdaterCore.d.mts +1 -1
  50. package/dist/createHotUpdaterCore.mjs +23 -9
  51. package/dist/db/createBundleDiff.cjs +2 -2
  52. package/dist/db/createBundleDiff.d.cts +1 -5
  53. package/dist/db/createBundleDiff.d.mts +1 -5
  54. package/dist/db/databasePluginCore.cjs +0 -1
  55. package/dist/db/fixedMigrator.cjs +2 -2
  56. package/dist/db/fixedMigrator.mjs +2 -2
  57. package/dist/db/fixedMigratorMongo.cjs +6 -4
  58. package/dist/db/fixedMigratorMongo.mjs +6 -4
  59. package/dist/db/index.d.cts +0 -1
  60. package/dist/db/index.d.mts +0 -1
  61. package/dist/db/releaseCatalog.cjs +0 -1
  62. package/dist/db/releaseCatalog.d.cts +0 -1
  63. package/dist/db/releaseCatalog.d.mts +0 -1
  64. package/dist/db/schema/insightsCollation.cjs +14 -0
  65. package/dist/db/schema/insightsCollation.mjs +14 -0
  66. package/dist/db/schema/sql.cjs +11 -7
  67. package/dist/db/schema/sql.mjs +8 -8
  68. package/dist/db/schemaGenerators.cjs +28 -9
  69. package/dist/db/schemaGenerators.mjs +28 -9
  70. package/dist/db/schemaReadiness.cjs +2 -0
  71. package/dist/db/schemaReadiness.d.cts +1 -0
  72. package/dist/db/schemaReadiness.d.mts +1 -0
  73. package/dist/db/schemaReadiness.mjs +2 -0
  74. package/dist/db/sqlMigrationExecution.cjs +1 -1
  75. package/dist/db/sqlMigrationExecution.mjs +1 -0
  76. package/dist/db/types.cjs +3 -1
  77. package/dist/db/types.d.cts +3 -6
  78. package/dist/db/types.d.mts +3 -6
  79. package/dist/db/types.mjs +2 -2
  80. package/dist/db/updateArtifacts.cjs +0 -1
  81. package/dist/handler.d.cts +1 -2
  82. package/dist/handler.d.mts +1 -2
  83. package/dist/handlerReleaseCatalogRoutes.cjs +0 -1
  84. package/dist/handlerReleaseManagementRoutes.cjs +0 -1
  85. package/dist/handlerTypes.d.cts +0 -1
  86. package/dist/handlerTypes.d.mts +0 -1
  87. package/dist/handlerVersionRoutes.d.cts +1 -0
  88. package/dist/handlerVersionRoutes.d.mts +1 -0
  89. package/dist/index.cjs +1 -1
  90. package/dist/index.d.cts +4 -4
  91. package/dist/index.d.mts +4 -4
  92. package/dist/index.mjs +1 -1
  93. package/dist/insights/domain.d.cts +37 -69
  94. package/dist/insights/domain.d.mts +37 -69
  95. package/dist/insights/errors.cjs +1 -8
  96. package/dist/insights/errors.mjs +2 -8
  97. package/dist/insights/eventInput.cjs +49 -5
  98. package/dist/insights/eventInput.mjs +48 -6
  99. package/dist/insights/provider.cjs +314 -0
  100. package/dist/insights/provider.d.cts +6 -0
  101. package/dist/insights/provider.d.mts +6 -0
  102. package/dist/insights/provider.mjs +314 -0
  103. package/dist/insights/queryInput.cjs +78 -43
  104. package/dist/insights/queryInput.mjs +76 -40
  105. package/dist/insights/routes.cjs +20 -25
  106. package/dist/insights/routes.mjs +22 -27
  107. package/dist/insights/types.d.cts +27 -12
  108. package/dist/insights/types.d.mts +27 -12
  109. package/dist/node.d.cts +0 -1
  110. package/dist/node.d.mts +0 -1
  111. package/dist/package.cjs +1 -1
  112. package/dist/package.mjs +1 -1
  113. package/dist/schema/index.cjs +17 -3
  114. package/dist/schema/index.mjs +4 -4
  115. package/dist/schema/v1_0_0.cjs +72 -30
  116. package/dist/schema/v1_0_0.mjs +72 -31
  117. package/dist/storageAccess.cjs +0 -1
  118. package/dist/types/index.d.cts +0 -1
  119. package/dist/types/index.d.mts +0 -1
  120. package/package.json +7 -7
  121. package/src/adapters/databasePluginTestDatabase.ts +14 -0
  122. package/src/adapters/drizzle.spec.ts +99 -0
  123. package/src/adapters/drizzle.ts +21 -3
  124. package/src/adapters/drizzleCrud.ts +154 -2
  125. package/src/adapters/drizzleLazyDB.ts +17 -3
  126. package/src/adapters/insightsTransaction.ts +32 -0
  127. package/src/adapters/kysely.spec.ts +29 -0
  128. package/src/adapters/kysely.ts +10 -1
  129. package/src/adapters/kyselyCrud.ts +121 -0
  130. package/src/adapters/mongodb.integration.spec.ts +210 -0
  131. package/src/adapters/mongodb.spec.ts +69 -1
  132. package/src/adapters/mongodb.ts +66 -2
  133. package/src/adapters/mongodbCollections.ts +5 -0
  134. package/src/adapters/mongodbQuery.ts +32 -3
  135. package/src/adapters/mongodbReads.ts +69 -0
  136. package/src/adapters/mongodbTestClient.ts +41 -6
  137. package/src/adapters/mongodbTestFilter.ts +4 -1
  138. package/src/adapters/mongodbWrites.ts +27 -0
  139. package/src/adapters/prisma.spec.ts +97 -0
  140. package/src/adapters/prisma.ts +103 -3
  141. package/src/adapters/prismaRows.ts +37 -1
  142. package/src/adapters/prismaTestClient.ts +22 -5
  143. package/src/apiKeys.integration.spec.ts +1 -1
  144. package/src/createHotUpdaterCore.ts +21 -7
  145. package/src/db/databasePluginUpdateCheck.bench.ts +3 -0
  146. package/src/db/fixedMigrator.spec.ts +65 -0
  147. package/src/db/fixedMigratorMongo.spec.ts +56 -9
  148. package/src/db/fixedMigratorMongo.ts +10 -10
  149. package/src/db/index.spec.ts +8 -1
  150. package/src/db/schema/insightsCollation.ts +21 -0
  151. package/src/db/schema/sql.ts +8 -5
  152. package/src/db/schemaGenerators.ts +41 -13
  153. package/src/db/types.spec.ts +8 -0
  154. package/src/db/types.ts +10 -4
  155. package/src/handler-standalone.integration.spec.ts +5 -7
  156. package/src/index.ts +2 -2
  157. package/src/insights/domain.ts +39 -75
  158. package/src/insights/errors.ts +0 -7
  159. package/src/insights/eventInput.ts +60 -3
  160. package/src/insights/insights.integration.spec.ts +254 -17
  161. package/src/insights/provider.spec.ts +385 -0
  162. package/src/insights/provider.ts +591 -0
  163. package/src/insights/queryInput.ts +112 -73
  164. package/src/insights/routes.ts +37 -56
  165. package/src/insights/types.ts +47 -36
  166. package/src/schema/dsl-all-versions.spec.ts +3 -1
  167. package/src/schema/v1_0_0.spec.ts +77 -3
  168. package/src/schema/v1_0_0.ts +94 -30
  169. package/dist/insights/bounded/activeOverview.cjs +0 -87
  170. package/dist/insights/bounded/activeOverview.mjs +0 -85
  171. package/dist/insights/bounded/installationSearch.cjs +0 -42
  172. package/dist/insights/bounded/installationSearch.mjs +0 -42
  173. package/dist/insights/bounded/persistence.cjs +0 -39
  174. package/dist/insights/bounded/persistence.mjs +0 -38
  175. package/dist/insights/bounded/provider.cjs +0 -170
  176. package/dist/insights/bounded/provider.d.cts +0 -7
  177. package/dist/insights/bounded/provider.d.mts +0 -7
  178. package/dist/insights/bounded/provider.mjs +0 -170
  179. package/dist/insights/bounded/scan.cjs +0 -144
  180. package/dist/insights/bounded/scan.mjs +0 -138
  181. package/dist/insights/persistence.d.cts +0 -6
  182. package/dist/insights/persistence.d.mts +0 -6
  183. package/src/insights/bounded/activeOverview.spec.ts +0 -189
  184. package/src/insights/bounded/activeOverview.ts +0 -148
  185. package/src/insights/bounded/installationSearch.spec.ts +0 -130
  186. package/src/insights/bounded/installationSearch.ts +0 -69
  187. package/src/insights/bounded/persistence.ts +0 -43
  188. package/src/insights/bounded/provider.spec.ts +0 -219
  189. package/src/insights/bounded/provider.ts +0 -229
  190. package/src/insights/bounded/scan.ts +0 -235
  191. package/src/insights/persistence.ts +0 -10
@@ -15,7 +15,7 @@ var __copyProps = (to, from, except, desc) => {
15
15
  }
16
16
  return to;
17
17
  };
18
- var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", {
18
+ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(isNodeMode || !mod || !mod.__esModule || !__hasOwnProp.call(mod, "default") ? __defProp(target, "default", {
19
19
  value: mod,
20
20
  enumerable: true
21
21
  }) : target, mod));
@@ -1,4 +1,3 @@
1
- require("../_virtual/_rolldown/runtime.cjs");
2
1
  let _hot_updater_plugin_core_internal = require("@hot-updater/plugin-core/internal");
3
2
  //#region src/adapters/databaseConstraintErrors.ts
4
3
  const readErrorCode = (error) => {
@@ -1,4 +1,3 @@
1
- require("../_virtual/_rolldown/runtime.cjs");
2
1
  let _hot_updater_plugin_core = require("@hot-updater/plugin-core");
3
2
  //#region src/adapters/databasePluginUtils.ts
4
3
  var StoredBundleRowError = class extends Error {
@@ -1,7 +1,7 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
- require("../_virtual/_rolldown/runtime.cjs");
3
2
  const require_registry = require("../db/schema/registry.cjs");
4
3
  const require_schemaGenerators = require("../db/schemaGenerators.cjs");
4
+ const require_insightsTransaction = require("./insightsTransaction.cjs");
5
5
  const require_drizzleCrud = require("./drizzleCrud.cjs");
6
6
  const require_drizzleLazyDB = require("./drizzleLazyDB.cjs");
7
7
  let _hot_updater_plugin_core = require("@hot-updater/plugin-core");
@@ -13,6 +13,10 @@ const createImplementation = (config) => {
13
13
  const transaction = db.transaction?.bind(db);
14
14
  return {
15
15
  ...crud,
16
+ recordInsights: (input) => {
17
+ if (transaction === void 0) throw new Error("Drizzle Insights recording requires transaction support.");
18
+ return require_insightsTransaction.runInsightsTransaction(() => transaction((transactionDatabase) => require_drizzleCrud.recordDrizzleInsights(transactionDatabase, config.provider, input)));
19
+ },
16
20
  deleteChannel: (input) => {
17
21
  if (transaction === void 0) throw new Error("Drizzle channel deletion requires transaction support.");
18
22
  return transaction((transactionDatabase) => require_drizzleCrud.createDrizzleCrud(transactionDatabase, config.provider).deleteChannel(input));
@@ -51,8 +55,11 @@ const drizzleAdapter = (config) => {
51
55
  delete: (input) => getAdapter().models.channels.delete(input)
52
56
  },
53
57
  insights: {
54
- append: (row) => getAdapter().models.insights.append(row),
55
- scan: (input) => getAdapter().models.insights.scan(input)
58
+ record: (input) => getAdapter().models.insights.record(input),
59
+ listEvents: (input) => getAdapter().models.insights.listEvents(input),
60
+ findInstallations: (input) => getAdapter().models.insights.findInstallations(input),
61
+ countInstallations: (input) => getAdapter().models.insights.countInstallations(input),
62
+ countEvents: (input) => getAdapter().models.insights.countEvents(input)
56
63
  },
57
64
  apiKeys: {
58
65
  create: (row) => getAdapter().models.apiKeys.create(row),
@@ -1,5 +1,4 @@
1
1
  import { DatabaseAdapterWithCapabilities, ORMProvider } from "../db/types.cjs";
2
-
3
2
  //#region src/adapters/drizzle.d.ts
4
3
  type DrizzleProvider = Exclude<ORMProvider, "cockroachdb" | "mongodb" | "mssql">;
5
4
  interface DrizzleConfig {
@@ -1,5 +1,4 @@
1
1
  import { DatabaseAdapterWithCapabilities, ORMProvider } from "../db/types.mjs";
2
-
3
2
  //#region src/adapters/drizzle.d.ts
4
3
  type DrizzleProvider = Exclude<ORMProvider, "cockroachdb" | "mongodb" | "mssql">;
5
4
  interface DrizzleConfig {
@@ -1,6 +1,7 @@
1
1
  import { getHotUpdaterSchemaVersion, hotUpdaterSchema } from "../db/schema/registry.mjs";
2
2
  import { generateDrizzleSchema } from "../db/schemaGenerators.mjs";
3
- import { createDrizzleCrud } from "./drizzleCrud.mjs";
3
+ import { runInsightsTransaction } from "./insightsTransaction.mjs";
4
+ import { createDrizzleCrud, recordDrizzleInsights } from "./drizzleCrud.mjs";
4
5
  import { createLazyDB } from "./drizzleLazyDB.mjs";
5
6
  import { createDatabasePlugin } from "@hot-updater/plugin-core";
6
7
  import { createDatabasePluginAdapter } from "@hot-updater/plugin-core/internal";
@@ -11,6 +12,10 @@ const createImplementation = (config) => {
11
12
  const transaction = db.transaction?.bind(db);
12
13
  return {
13
14
  ...crud,
15
+ recordInsights: (input) => {
16
+ if (transaction === void 0) throw new Error("Drizzle Insights recording requires transaction support.");
17
+ return runInsightsTransaction(() => transaction((transactionDatabase) => recordDrizzleInsights(transactionDatabase, config.provider, input)));
18
+ },
14
19
  deleteChannel: (input) => {
15
20
  if (transaction === void 0) throw new Error("Drizzle channel deletion requires transaction support.");
16
21
  return transaction((transactionDatabase) => createDrizzleCrud(transactionDatabase, config.provider).deleteChannel(input));
@@ -49,8 +54,11 @@ const drizzleAdapter = (config) => {
49
54
  delete: (input) => getAdapter().models.channels.delete(input)
50
55
  },
51
56
  insights: {
52
- append: (row) => getAdapter().models.insights.append(row),
53
- scan: (input) => getAdapter().models.insights.scan(input)
57
+ record: (input) => getAdapter().models.insights.record(input),
58
+ listEvents: (input) => getAdapter().models.insights.listEvents(input),
59
+ findInstallations: (input) => getAdapter().models.insights.findInstallations(input),
60
+ countInstallations: (input) => getAdapter().models.insights.countInstallations(input),
61
+ countEvents: (input) => getAdapter().models.insights.countEvents(input)
54
62
  },
55
63
  apiKeys: {
56
64
  create: (row) => getAdapter().models.apiKeys.create(row),
@@ -1,4 +1,3 @@
1
- require("../_virtual/_rolldown/runtime.cjs");
2
1
  const require_databaseConstraintErrors = require("./databaseConstraintErrors.cjs");
3
2
  const require_databasePluginUtils = require("./databasePluginUtils.cjs");
4
3
  const require_drizzleQuery = require("./drizzleQuery.cjs");
@@ -6,6 +5,7 @@ let _hot_updater_plugin_core = require("@hot-updater/plugin-core");
6
5
  let drizzle_orm = require("drizzle-orm");
7
6
  //#region src/adapters/drizzleCrud.ts
8
7
  var MissingDrizzleTableError = class extends Error {
8
+ table;
9
9
  name = "MissingDrizzleTableError";
10
10
  constructor(table) {
11
11
  super(`Drizzle schema is missing table "${table}".`);
@@ -37,9 +37,45 @@ const executeInsert = async (db, provider, table, data, onConflict) => {
37
37
  if (ignored === void 0) throw new DrizzleAdapterInvariantError();
38
38
  await ignored.execute();
39
39
  };
40
+ const recordDrizzleInsights = (db, provider, input) => {
41
+ if (db.resultKind !== "sync") return recordAsyncDrizzleInsights(db, provider, input);
42
+ const events = getDrizzleTable(db, "bundle_events");
43
+ const installations = getDrizzleTable(db, "bundle_installations");
44
+ const eventInsert = db.insert(events).values(input.event).onConflictDoNothing?.().returning?.({ id: getDrizzleColumn(events, "id") });
45
+ const installationInsert = db.insert(installations).values(input.installation).onConflictDoNothing?.();
46
+ const installationUpdate = db.update(installations).set(input.installation).where(newerInstallationWhere(installations, input.installation));
47
+ if (eventInsert?.all === void 0 || installationInsert?.run === void 0 || installationUpdate.run === void 0) throw new DrizzleAdapterInvariantError();
48
+ if (eventInsert.all().length === 0) return;
49
+ installationInsert.run();
50
+ installationUpdate.run();
51
+ };
52
+ const newerInstallationWhere = (installations, installation) => {
53
+ const receivedAt = getDrizzleColumn(installations, "received_at_ms");
54
+ return (0, drizzle_orm.and)((0, drizzle_orm.eq)(getDrizzleColumn(installations, "install_id"), installation.install_id), (0, drizzle_orm.or)((0, drizzle_orm.lt)(receivedAt, installation.received_at_ms), (0, drizzle_orm.and)((0, drizzle_orm.eq)(receivedAt, installation.received_at_ms), (0, drizzle_orm.lt)(getDrizzleColumn(installations, "id"), installation.id))));
55
+ };
56
+ const recordAsyncDrizzleInsights = async (db, provider, { event, installation }) => {
57
+ const events = getDrizzleTable(db, "bundle_events");
58
+ const installations = getDrizzleTable(db, "bundle_installations");
59
+ if (provider === "mysql") {
60
+ if (await db.query.bundle_events.findFirst({ where: (0, drizzle_orm.eq)(getDrizzleColumn(events, "id"), event.id) }) !== void 0) return;
61
+ await db.insert(events).values(event).execute();
62
+ const insertInstallation = db.insert(installations).values(installation).onDuplicateKeyUpdate?.({ set: { install_id: installation.install_id } });
63
+ if (insertInstallation === void 0) throw new DrizzleAdapterInvariantError();
64
+ await insertInstallation.execute();
65
+ } else {
66
+ const returning = (db.insert(events).values(event).onConflictDoNothing?.())?.returning?.({ id: getDrizzleColumn(events, "id") });
67
+ if (returning === void 0) throw new DrizzleAdapterInvariantError();
68
+ const rows = await returning.execute();
69
+ if (!Array.isArray(rows)) throw new DrizzleAdapterInvariantError();
70
+ if (rows.length === 0) return;
71
+ await executeInsert(db, provider, installations, installation, "ignore");
72
+ }
73
+ await db.update(installations).set(installation).where(newerInstallationWhere(installations, installation)).execute();
74
+ };
40
75
  const toOrderBy = (table, input) => {
41
76
  return input.orderBy?.flatMap((clause) => {
42
77
  const column = getDrizzleColumn(table, clause.field);
78
+ if (input.model === "bundle_events" || input.model === "bundle_installations") return [clause.direction === "asc" ? (0, drizzle_orm.asc)(column) : (0, drizzle_orm.desc)(column)];
43
79
  return [(clause.nulls ?? (clause.direction === "asc" ? "last" : "first")) === "first" ? drizzle_orm.sql`${column} is null desc` : drizzle_orm.sql`${column} is null asc`, clause.direction === "asc" ? (0, drizzle_orm.asc)(column) : (0, drizzle_orm.desc)(column)];
44
80
  });
45
81
  };
@@ -47,6 +83,7 @@ const createDrizzleCrud = (db, provider) => {
47
83
  const bundles = getDrizzleTable(db, "bundles");
48
84
  const patches = getDrizzleTable(db, "bundle_patches");
49
85
  const events = getDrizzleTable(db, "bundle_events");
86
+ const installations = getDrizzleTable(db, "bundle_installations");
50
87
  const releases = getDrizzleTable(db, "releases");
51
88
  const releaseCatalogs = getDrizzleTable(db, "release_catalogs");
52
89
  const channels = getDrizzleTable(db, "channels");
@@ -98,6 +135,9 @@ const createDrizzleCrud = (db, provider) => {
98
135
  case "bundle_events":
99
136
  await executeInsert(db, provider, events, input.data, void 0);
100
137
  return input.data;
138
+ case "bundle_installations":
139
+ await executeInsert(db, provider, installations, input.data, input.onConflict);
140
+ return input.data;
101
141
  case "releases":
102
142
  await executeInsert(db, provider, releases, require_databasePluginUtils.toStoredReleaseRow(input.data, provider), void 0);
103
143
  return input.data;
@@ -113,6 +153,15 @@ const createDrizzleCrud = (db, provider) => {
113
153
  }
114
154
  },
115
155
  async update(input) {
156
+ if (input.model === "bundle_installations") {
157
+ const installId = input.where.find((item) => item.field === "install_id" && (item.operator === void 0 || item.operator === "eq") && typeof item.value === "string")?.value;
158
+ if (typeof installId !== "string") throw new DrizzleAdapterInvariantError();
159
+ const where = require_drizzleQuery.buildDrizzleWhere(provider, installations, input.where);
160
+ if (where === void 0) throw new DrizzleAdapterInvariantError();
161
+ await db.update(installations).set(input.update).where(where).execute();
162
+ const row = await db.query.bundle_installations.findFirst({ where: (0, drizzle_orm.eq)(getDrizzleColumn(installations, "install_id"), installId) });
163
+ return row?.id === input.update.id && row.received_at_ms === input.update.received_at_ms ? row : null;
164
+ }
116
165
  const selector = input.where[0];
117
166
  if (selector === void 0 || typeof selector.value !== "string") throw new DrizzleAdapterInvariantError();
118
167
  if (input.model === "api_keys") {
@@ -173,9 +222,11 @@ const createDrizzleCrud = (db, provider) => {
173
222
  async count(input) {
174
223
  if (input.distinct !== void 0) throw new _hot_updater_plugin_core.DatabasePluginInputError("invalid-operation");
175
224
  switch (input.model) {
225
+ case "bundle_events": return db.$count(events, require_drizzleQuery.buildDrizzleWhere(provider, events, input.where));
176
226
  case "bundles": return db.$count(bundles, require_drizzleQuery.buildDrizzleWhere(provider, bundles, input.where));
177
227
  case "bundle_patches": return db.$count(patches, require_drizzleQuery.buildDrizzleWhere(provider, patches, input.where));
178
228
  case "releases": return db.$count(releases, require_drizzleQuery.buildDrizzleWhere(provider, releases, input.where));
229
+ case "bundle_installations": return db.$count(installations, require_drizzleQuery.buildDrizzleWhere(provider, installations, input.where));
179
230
  }
180
231
  },
181
232
  async findOne(input) {
@@ -195,6 +246,7 @@ const createDrizzleCrud = (db, provider) => {
195
246
  const row = await db.query.release_catalogs.findFirst({ where: require_drizzleQuery.buildDrizzleWhere(provider, releaseCatalogs, input.where) });
196
247
  return row === void 0 ? null : require_databasePluginUtils.fromStoredReleaseCatalogRow(row);
197
248
  }
249
+ case "bundle_installations": return await db.query.bundle_installations.findFirst({ where: require_drizzleQuery.buildDrizzleWhere(provider, installations, input.where) }) ?? null;
198
250
  }
199
251
  },
200
252
  async findMany(input) {
@@ -212,6 +264,12 @@ const createDrizzleCrud = (db, provider) => {
212
264
  limit: input.limit,
213
265
  offset: input.offset
214
266
  });
267
+ case "bundle_installations": return db.query.bundle_installations.findMany({
268
+ where: require_drizzleQuery.buildDrizzleWhere(provider, installations, input.where),
269
+ orderBy: toOrderBy(installations, input),
270
+ limit: input.limit,
271
+ offset: input.offset
272
+ });
215
273
  case "api_keys": return db.query.api_keys.findMany({
216
274
  where: require_drizzleQuery.buildDrizzleWhere(provider, apiKeys, input.where),
217
275
  orderBy: toOrderBy(apiKeys, input),
@@ -248,3 +306,6 @@ const createDrizzleCrud = (db, provider) => {
248
306
  };
249
307
  //#endregion
250
308
  exports.createDrizzleCrud = createDrizzleCrud;
309
+ exports.getDrizzleColumn = getDrizzleColumn;
310
+ exports.getDrizzleTable = getDrizzleTable;
311
+ exports.recordDrizzleInsights = recordDrizzleInsights;
@@ -2,9 +2,10 @@ import { isChannelDeleteReferencedError, translateChannelDeleteError } from "./d
2
2
  import { fromStoredBundleRow, fromStoredReleaseCatalogRow, fromStoredReleaseRow, toStoredBundleRow, toStoredBundleUpdate, toStoredReleaseRow, toStoredReleaseUpdate } from "./databasePluginUtils.mjs";
3
3
  import { buildDrizzleWhere } from "./drizzleQuery.mjs";
4
4
  import { DatabasePluginInputError } from "@hot-updater/plugin-core";
5
- import { asc, desc, eq, sql } from "drizzle-orm";
5
+ import { and, asc, desc, eq, lt, or, sql } from "drizzle-orm";
6
6
  //#region src/adapters/drizzleCrud.ts
7
7
  var MissingDrizzleTableError = class extends Error {
8
+ table;
8
9
  name = "MissingDrizzleTableError";
9
10
  constructor(table) {
10
11
  super(`Drizzle schema is missing table "${table}".`);
@@ -36,9 +37,45 @@ const executeInsert = async (db, provider, table, data, onConflict) => {
36
37
  if (ignored === void 0) throw new DrizzleAdapterInvariantError();
37
38
  await ignored.execute();
38
39
  };
40
+ const recordDrizzleInsights = (db, provider, input) => {
41
+ if (db.resultKind !== "sync") return recordAsyncDrizzleInsights(db, provider, input);
42
+ const events = getDrizzleTable(db, "bundle_events");
43
+ const installations = getDrizzleTable(db, "bundle_installations");
44
+ const eventInsert = db.insert(events).values(input.event).onConflictDoNothing?.().returning?.({ id: getDrizzleColumn(events, "id") });
45
+ const installationInsert = db.insert(installations).values(input.installation).onConflictDoNothing?.();
46
+ const installationUpdate = db.update(installations).set(input.installation).where(newerInstallationWhere(installations, input.installation));
47
+ if (eventInsert?.all === void 0 || installationInsert?.run === void 0 || installationUpdate.run === void 0) throw new DrizzleAdapterInvariantError();
48
+ if (eventInsert.all().length === 0) return;
49
+ installationInsert.run();
50
+ installationUpdate.run();
51
+ };
52
+ const newerInstallationWhere = (installations, installation) => {
53
+ const receivedAt = getDrizzleColumn(installations, "received_at_ms");
54
+ return and(eq(getDrizzleColumn(installations, "install_id"), installation.install_id), or(lt(receivedAt, installation.received_at_ms), and(eq(receivedAt, installation.received_at_ms), lt(getDrizzleColumn(installations, "id"), installation.id))));
55
+ };
56
+ const recordAsyncDrizzleInsights = async (db, provider, { event, installation }) => {
57
+ const events = getDrizzleTable(db, "bundle_events");
58
+ const installations = getDrizzleTable(db, "bundle_installations");
59
+ if (provider === "mysql") {
60
+ if (await db.query.bundle_events.findFirst({ where: eq(getDrizzleColumn(events, "id"), event.id) }) !== void 0) return;
61
+ await db.insert(events).values(event).execute();
62
+ const insertInstallation = db.insert(installations).values(installation).onDuplicateKeyUpdate?.({ set: { install_id: installation.install_id } });
63
+ if (insertInstallation === void 0) throw new DrizzleAdapterInvariantError();
64
+ await insertInstallation.execute();
65
+ } else {
66
+ const returning = (db.insert(events).values(event).onConflictDoNothing?.())?.returning?.({ id: getDrizzleColumn(events, "id") });
67
+ if (returning === void 0) throw new DrizzleAdapterInvariantError();
68
+ const rows = await returning.execute();
69
+ if (!Array.isArray(rows)) throw new DrizzleAdapterInvariantError();
70
+ if (rows.length === 0) return;
71
+ await executeInsert(db, provider, installations, installation, "ignore");
72
+ }
73
+ await db.update(installations).set(installation).where(newerInstallationWhere(installations, installation)).execute();
74
+ };
39
75
  const toOrderBy = (table, input) => {
40
76
  return input.orderBy?.flatMap((clause) => {
41
77
  const column = getDrizzleColumn(table, clause.field);
78
+ if (input.model === "bundle_events" || input.model === "bundle_installations") return [clause.direction === "asc" ? asc(column) : desc(column)];
42
79
  return [(clause.nulls ?? (clause.direction === "asc" ? "last" : "first")) === "first" ? sql`${column} is null desc` : sql`${column} is null asc`, clause.direction === "asc" ? asc(column) : desc(column)];
43
80
  });
44
81
  };
@@ -46,6 +83,7 @@ const createDrizzleCrud = (db, provider) => {
46
83
  const bundles = getDrizzleTable(db, "bundles");
47
84
  const patches = getDrizzleTable(db, "bundle_patches");
48
85
  const events = getDrizzleTable(db, "bundle_events");
86
+ const installations = getDrizzleTable(db, "bundle_installations");
49
87
  const releases = getDrizzleTable(db, "releases");
50
88
  const releaseCatalogs = getDrizzleTable(db, "release_catalogs");
51
89
  const channels = getDrizzleTable(db, "channels");
@@ -97,6 +135,9 @@ const createDrizzleCrud = (db, provider) => {
97
135
  case "bundle_events":
98
136
  await executeInsert(db, provider, events, input.data, void 0);
99
137
  return input.data;
138
+ case "bundle_installations":
139
+ await executeInsert(db, provider, installations, input.data, input.onConflict);
140
+ return input.data;
100
141
  case "releases":
101
142
  await executeInsert(db, provider, releases, toStoredReleaseRow(input.data, provider), void 0);
102
143
  return input.data;
@@ -112,6 +153,15 @@ const createDrizzleCrud = (db, provider) => {
112
153
  }
113
154
  },
114
155
  async update(input) {
156
+ if (input.model === "bundle_installations") {
157
+ const installId = input.where.find((item) => item.field === "install_id" && (item.operator === void 0 || item.operator === "eq") && typeof item.value === "string")?.value;
158
+ if (typeof installId !== "string") throw new DrizzleAdapterInvariantError();
159
+ const where = buildDrizzleWhere(provider, installations, input.where);
160
+ if (where === void 0) throw new DrizzleAdapterInvariantError();
161
+ await db.update(installations).set(input.update).where(where).execute();
162
+ const row = await db.query.bundle_installations.findFirst({ where: eq(getDrizzleColumn(installations, "install_id"), installId) });
163
+ return row?.id === input.update.id && row.received_at_ms === input.update.received_at_ms ? row : null;
164
+ }
115
165
  const selector = input.where[0];
116
166
  if (selector === void 0 || typeof selector.value !== "string") throw new DrizzleAdapterInvariantError();
117
167
  if (input.model === "api_keys") {
@@ -172,9 +222,11 @@ const createDrizzleCrud = (db, provider) => {
172
222
  async count(input) {
173
223
  if (input.distinct !== void 0) throw new DatabasePluginInputError("invalid-operation");
174
224
  switch (input.model) {
225
+ case "bundle_events": return db.$count(events, buildDrizzleWhere(provider, events, input.where));
175
226
  case "bundles": return db.$count(bundles, buildDrizzleWhere(provider, bundles, input.where));
176
227
  case "bundle_patches": return db.$count(patches, buildDrizzleWhere(provider, patches, input.where));
177
228
  case "releases": return db.$count(releases, buildDrizzleWhere(provider, releases, input.where));
229
+ case "bundle_installations": return db.$count(installations, buildDrizzleWhere(provider, installations, input.where));
178
230
  }
179
231
  },
180
232
  async findOne(input) {
@@ -194,6 +246,7 @@ const createDrizzleCrud = (db, provider) => {
194
246
  const row = await db.query.release_catalogs.findFirst({ where: buildDrizzleWhere(provider, releaseCatalogs, input.where) });
195
247
  return row === void 0 ? null : fromStoredReleaseCatalogRow(row);
196
248
  }
249
+ case "bundle_installations": return await db.query.bundle_installations.findFirst({ where: buildDrizzleWhere(provider, installations, input.where) }) ?? null;
197
250
  }
198
251
  },
199
252
  async findMany(input) {
@@ -211,6 +264,12 @@ const createDrizzleCrud = (db, provider) => {
211
264
  limit: input.limit,
212
265
  offset: input.offset
213
266
  });
267
+ case "bundle_installations": return db.query.bundle_installations.findMany({
268
+ where: buildDrizzleWhere(provider, installations, input.where),
269
+ orderBy: toOrderBy(installations, input),
270
+ limit: input.limit,
271
+ offset: input.offset
272
+ });
214
273
  case "api_keys": return db.query.api_keys.findMany({
215
274
  where: buildDrizzleWhere(provider, apiKeys, input.where),
216
275
  orderBy: toOrderBy(apiKeys, input),
@@ -246,4 +305,4 @@ const createDrizzleCrud = (db, provider) => {
246
305
  };
247
306
  };
248
307
  //#endregion
249
- export { createDrizzleCrud };
308
+ export { createDrizzleCrud, getDrizzleColumn, getDrizzleTable, recordDrizzleInsights };
@@ -1,5 +1,6 @@
1
1
  //#region src/adapters/drizzleLazyDB.ts
2
2
  var InvalidDrizzleDatabaseError = class extends Error {
3
+ reason;
3
4
  name = "InvalidDrizzleDatabaseError";
4
5
  constructor(reason) {
5
6
  super(`[hot-updater] ${reason}`);
@@ -14,7 +15,7 @@ const isDrizzleDB = (value) => {
14
15
  const metadata = value["_"];
15
16
  if (!isRecord(metadata) || !isRecord(metadata["fullSchema"])) return false;
16
17
  const query = value["query"];
17
- if (!isRecord(query) || !isDrizzleQuery(query["bundle_events"]) || !isDrizzleQuery(query["bundle_patches"]) || !isDrizzleQuery(query["bundles"]) || !isDrizzleQuery(query["channels"]) || !isDrizzleQuery(query["api_keys"]) || !isDrizzleQuery(query["releases"]) || !isDrizzleQuery(query["release_catalogs"])) return false;
18
+ if (!isRecord(query) || !isDrizzleQuery(query["bundle_events"]) || !isDrizzleQuery(query["bundle_installations"]) || !isDrizzleQuery(query["bundle_patches"]) || !isDrizzleQuery(query["bundles"]) || !isDrizzleQuery(query["channels"]) || !isDrizzleQuery(query["api_keys"]) || !isDrizzleQuery(query["releases"]) || !isDrizzleQuery(query["release_catalogs"])) return false;
18
19
  if (value["transaction"] !== void 0 && !hasFunction(value, "transaction")) return false;
19
20
  return hasFunction(value, "$count") && hasFunction(value, "delete") && hasFunction(value, "insert") && hasFunction(value, "update");
20
21
  };
@@ -64,6 +65,10 @@ const createLazyDB = (config) => {
64
65
  findFirst: async (args) => (await getDB()).query.bundle_events.findFirst(args),
65
66
  findMany: async (args) => (await getDB()).query.bundle_events.findMany(args)
66
67
  },
68
+ bundle_installations: {
69
+ findFirst: async (args) => (await getDB()).query.bundle_installations.findFirst(args),
70
+ findMany: async (args) => (await getDB()).query.bundle_installations.findMany(args)
71
+ },
67
72
  bundle_patches: {
68
73
  findFirst: async (args) => (await getDB()).query.bundle_patches.findFirst(args),
69
74
  findMany: async (args) => (await getDB()).query.bundle_patches.findMany(args)
@@ -1,5 +1,6 @@
1
1
  //#region src/adapters/drizzleLazyDB.ts
2
2
  var InvalidDrizzleDatabaseError = class extends Error {
3
+ reason;
3
4
  name = "InvalidDrizzleDatabaseError";
4
5
  constructor(reason) {
5
6
  super(`[hot-updater] ${reason}`);
@@ -14,7 +15,7 @@ const isDrizzleDB = (value) => {
14
15
  const metadata = value["_"];
15
16
  if (!isRecord(metadata) || !isRecord(metadata["fullSchema"])) return false;
16
17
  const query = value["query"];
17
- if (!isRecord(query) || !isDrizzleQuery(query["bundle_events"]) || !isDrizzleQuery(query["bundle_patches"]) || !isDrizzleQuery(query["bundles"]) || !isDrizzleQuery(query["channels"]) || !isDrizzleQuery(query["api_keys"]) || !isDrizzleQuery(query["releases"]) || !isDrizzleQuery(query["release_catalogs"])) return false;
18
+ if (!isRecord(query) || !isDrizzleQuery(query["bundle_events"]) || !isDrizzleQuery(query["bundle_installations"]) || !isDrizzleQuery(query["bundle_patches"]) || !isDrizzleQuery(query["bundles"]) || !isDrizzleQuery(query["channels"]) || !isDrizzleQuery(query["api_keys"]) || !isDrizzleQuery(query["releases"]) || !isDrizzleQuery(query["release_catalogs"])) return false;
18
19
  if (value["transaction"] !== void 0 && !hasFunction(value, "transaction")) return false;
19
20
  return hasFunction(value, "$count") && hasFunction(value, "delete") && hasFunction(value, "insert") && hasFunction(value, "update");
20
21
  };
@@ -64,6 +65,10 @@ const createLazyDB = (config) => {
64
65
  findFirst: async (args) => (await getDB()).query.bundle_events.findFirst(args),
65
66
  findMany: async (args) => (await getDB()).query.bundle_events.findMany(args)
66
67
  },
68
+ bundle_installations: {
69
+ findFirst: async (args) => (await getDB()).query.bundle_installations.findFirst(args),
70
+ findMany: async (args) => (await getDB()).query.bundle_installations.findMany(args)
71
+ },
67
72
  bundle_patches: {
68
73
  findFirst: async (args) => (await getDB()).query.bundle_patches.findFirst(args),
69
74
  findMany: async (args) => (await getDB()).query.bundle_patches.findMany(args)
@@ -1,4 +1,3 @@
1
- require("../_virtual/_rolldown/runtime.cjs");
2
1
  const require_databasePluginUtils = require("./databasePluginUtils.cjs");
3
2
  let drizzle_orm = require("drizzle-orm");
4
3
  //#region src/adapters/drizzleQuery.ts
@@ -6,6 +5,7 @@ var InvalidDatabasePredicateError = class extends Error {
6
5
  name = "InvalidDatabasePredicateError";
7
6
  };
8
7
  var MissingDrizzleColumnError = class extends Error {
8
+ column;
9
9
  name = "MissingDrizzleColumnError";
10
10
  constructor(column) {
11
11
  super(`Drizzle schema is missing column "${column}".`);
@@ -21,7 +21,8 @@ const column = (table, field) => {
21
21
  const stringPredicate = (provider, field, operator, value, insensitive) => {
22
22
  if (provider === "sqlite" && !insensitive) {
23
23
  const literal = require_databasePluginUtils.escapeGlobPattern(value);
24
- return drizzle_orm.sql`${field} glob ${operator === "contains" ? `*${literal}*` : operator === "starts_with" ? `${literal}*` : `*${literal}`}`;
24
+ const pattern = operator === "contains" ? `*${literal}*` : operator === "starts_with" ? `${literal}*` : `*${literal}`;
25
+ return drizzle_orm.sql`${field} glob ${pattern}`;
25
26
  }
26
27
  const literal = require_databasePluginUtils.escapeLikePattern(value);
27
28
  const pattern = operator === "contains" ? `%${literal}%` : operator === "starts_with" ? `${literal}%` : `%${literal}`;
@@ -5,6 +5,7 @@ var InvalidDatabasePredicateError = class extends Error {
5
5
  name = "InvalidDatabasePredicateError";
6
6
  };
7
7
  var MissingDrizzleColumnError = class extends Error {
8
+ column;
8
9
  name = "MissingDrizzleColumnError";
9
10
  constructor(column) {
10
11
  super(`Drizzle schema is missing column "${column}".`);
@@ -20,7 +21,8 @@ const column = (table, field) => {
20
21
  const stringPredicate = (provider, field, operator, value, insensitive) => {
21
22
  if (provider === "sqlite" && !insensitive) {
22
23
  const literal = escapeGlobPattern(value);
23
- return sql`${field} glob ${operator === "contains" ? `*${literal}*` : operator === "starts_with" ? `${literal}*` : `*${literal}`}`;
24
+ const pattern = operator === "contains" ? `*${literal}*` : operator === "starts_with" ? `${literal}*` : `*${literal}`;
25
+ return sql`${field} glob ${pattern}`;
24
26
  }
25
27
  const literal = escapeLikePattern(value);
26
28
  const pattern = operator === "contains" ? `%${literal}%` : operator === "starts_with" ? `${literal}%` : `%${literal}`;
@@ -0,0 +1,22 @@
1
+ //#region src/adapters/insightsTransaction.ts
2
+ const isRetryableConflict = (error) => {
3
+ if (typeof error !== "object" || error === null) return false;
4
+ if ("code" in error && [
5
+ "ER_DUP_ENTRY",
6
+ "ER_LOCK_DEADLOCK",
7
+ "ER_LOCK_WAIT_TIMEOUT",
8
+ "40001",
9
+ "40P01"
10
+ ].includes(String(error.code))) return true;
11
+ return "cause" in error && error.cause !== error && isRetryableConflict(error.cause);
12
+ };
13
+ const runInsightsTransaction = async (operation) => {
14
+ for (let attempt = 0;; attempt += 1) try {
15
+ await operation();
16
+ return;
17
+ } catch (error) {
18
+ if (attempt >= 2 || !isRetryableConflict(error)) throw error;
19
+ }
20
+ };
21
+ //#endregion
22
+ exports.runInsightsTransaction = runInsightsTransaction;
@@ -0,0 +1,22 @@
1
+ //#region src/adapters/insightsTransaction.ts
2
+ const isRetryableConflict = (error) => {
3
+ if (typeof error !== "object" || error === null) return false;
4
+ if ("code" in error && [
5
+ "ER_DUP_ENTRY",
6
+ "ER_LOCK_DEADLOCK",
7
+ "ER_LOCK_WAIT_TIMEOUT",
8
+ "40001",
9
+ "40P01"
10
+ ].includes(String(error.code))) return true;
11
+ return "cause" in error && error.cause !== error && isRetryableConflict(error.cause);
12
+ };
13
+ const runInsightsTransaction = async (operation) => {
14
+ for (let attempt = 0;; attempt += 1) try {
15
+ await operation();
16
+ return;
17
+ } catch (error) {
18
+ if (attempt >= 2 || !isRetryableConflict(error)) throw error;
19
+ }
20
+ };
21
+ //#endregion
22
+ export { runInsightsTransaction };
@@ -1,6 +1,6 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
- require("../_virtual/_rolldown/runtime.cjs");
3
2
  const require_fixedMigrator = require("../db/fixedMigrator.cjs");
3
+ const require_insightsTransaction = require("./insightsTransaction.cjs");
4
4
  const require_kyselyCrud = require("./kyselyCrud.cjs");
5
5
  let _hot_updater_plugin_core = require("@hot-updater/plugin-core");
6
6
  let _hot_updater_plugin_core_internal = require("@hot-updater/plugin-core/internal");
@@ -10,6 +10,7 @@ const createImplementation = (config) => {
10
10
  const relationMode = config.relationMode ?? "foreign-keys";
11
11
  return {
12
12
  ...require_kyselyCrud.createKyselyCrud(db, config.provider, relationMode),
13
+ recordInsights: (input) => require_insightsTransaction.runInsightsTransaction(() => db.transaction().execute((transaction) => require_kyselyCrud.recordKyselyInsights(transaction, config.provider, input))),
13
14
  deleteChannel: (input) => db.transaction().execute((transaction) => require_kyselyCrud.createKyselyCrud(transaction, config.provider, relationMode).deleteChannel(input)),
14
15
  create: (input) => db.transaction().execute((transaction) => require_kyselyCrud.createKyselyCrud(transaction, config.provider, relationMode).create(input)),
15
16
  update: (input) => db.transaction().execute((transaction) => require_kyselyCrud.createKyselyCrud(transaction, config.provider, relationMode).update(input)),
@@ -1,6 +1,5 @@
1
1
  import { DatabaseAdapterWithCapabilities, ORMSQLProvider, RelationMode } from "../db/types.cjs";
2
2
  import { Kysely } from "kysely";
3
-
4
3
  //#region src/adapters/kysely.d.ts
5
4
  type KyselySQLProvider = Exclude<ORMSQLProvider, "mssql">;
6
5
  interface KyselyAdapterConfig<TDatabase extends object = object> {
@@ -1,6 +1,5 @@
1
1
  import { DatabaseAdapterWithCapabilities, ORMSQLProvider, RelationMode } from "../db/types.mjs";
2
2
  import { Kysely } from "kysely";
3
-
4
3
  //#region src/adapters/kysely.d.ts
5
4
  type KyselySQLProvider = Exclude<ORMSQLProvider, "mssql">;
6
5
  interface KyselyAdapterConfig<TDatabase extends object = object> {
@@ -1,5 +1,6 @@
1
1
  import { createKyselyMigrator } from "../db/fixedMigrator.mjs";
2
- import { createKyselyCrud } from "./kyselyCrud.mjs";
2
+ import { runInsightsTransaction } from "./insightsTransaction.mjs";
3
+ import { createKyselyCrud, recordKyselyInsights } from "./kyselyCrud.mjs";
3
4
  import { createDatabasePlugin } from "@hot-updater/plugin-core";
4
5
  import { createDatabasePluginAdapter } from "@hot-updater/plugin-core/internal";
5
6
  //#region src/adapters/kysely.ts
@@ -8,6 +9,7 @@ const createImplementation = (config) => {
8
9
  const relationMode = config.relationMode ?? "foreign-keys";
9
10
  return {
10
11
  ...createKyselyCrud(db, config.provider, relationMode),
12
+ recordInsights: (input) => runInsightsTransaction(() => db.transaction().execute((transaction) => recordKyselyInsights(transaction, config.provider, input))),
11
13
  deleteChannel: (input) => db.transaction().execute((transaction) => createKyselyCrud(transaction, config.provider, relationMode).deleteChannel(input)),
12
14
  create: (input) => db.transaction().execute((transaction) => createKyselyCrud(transaction, config.provider, relationMode).create(input)),
13
15
  update: (input) => db.transaction().execute((transaction) => createKyselyCrud(transaction, config.provider, relationMode).update(input)),