@hot-updater/server 0.32.0 → 0.33.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.
- package/dist/db/index.cjs +7 -10
- package/dist/db/index.mjs +7 -10
- package/dist/db/pluginCore.cjs +136 -96
- package/dist/db/pluginCore.mjs +137 -97
- package/dist/db/requestBundleIdentityMap.cjs +29 -0
- package/dist/db/requestBundleIdentityMap.mjs +29 -0
- package/dist/db/types.d.cts +2 -1
- package/dist/db/types.d.mts +2 -1
- package/dist/packages/server/package.cjs +1 -1
- package/dist/packages/server/package.mjs +1 -1
- package/dist/runtime.cjs +10 -12
- package/dist/runtime.mjs +10 -12
- package/package.json +7 -7
- package/src/db/index.spec.ts +36 -0
- package/src/db/index.ts +6 -10
- package/src/db/pluginCore.spec.ts +334 -0
- package/src/db/pluginCore.ts +63 -7
- package/src/db/requestBundleIdentityMap.spec.ts +56 -0
- package/src/db/requestBundleIdentityMap.ts +61 -0
- package/src/db/types.ts +2 -0
- package/src/runtime.spec.ts +39 -0
- package/src/runtime.ts +10 -12
package/dist/db/index.cjs
CHANGED
|
@@ -29,20 +29,17 @@ function createHotUpdater(options) {
|
|
|
29
29
|
resolveFileUrl
|
|
30
30
|
});
|
|
31
31
|
const api = {
|
|
32
|
-
|
|
32
|
+
basePath,
|
|
33
|
+
adapterName: core.adapterName,
|
|
34
|
+
createMigrator: core.createMigrator,
|
|
35
|
+
generateSchema: core.generateSchema,
|
|
33
36
|
handler: require_handler.createHandler(core.api, {
|
|
34
37
|
basePath,
|
|
35
38
|
routes: options.routes
|
|
36
|
-
})
|
|
37
|
-
adapterName: core.adapterName,
|
|
38
|
-
createMigrator: core.createMigrator,
|
|
39
|
-
generateSchema: core.generateSchema
|
|
40
|
-
};
|
|
41
|
-
return {
|
|
42
|
-
...api,
|
|
43
|
-
basePath,
|
|
44
|
-
handler: api.handler
|
|
39
|
+
})
|
|
45
40
|
};
|
|
41
|
+
Object.defineProperties(api, Object.getOwnPropertyDescriptors(core.api));
|
|
42
|
+
return api;
|
|
46
43
|
}
|
|
47
44
|
//#endregion
|
|
48
45
|
exports.createHotUpdater = createHotUpdater;
|
package/dist/db/index.mjs
CHANGED
|
@@ -28,20 +28,17 @@ function createHotUpdater(options) {
|
|
|
28
28
|
resolveFileUrl
|
|
29
29
|
});
|
|
30
30
|
const api = {
|
|
31
|
-
|
|
31
|
+
basePath,
|
|
32
|
+
adapterName: core.adapterName,
|
|
33
|
+
createMigrator: core.createMigrator,
|
|
34
|
+
generateSchema: core.generateSchema,
|
|
32
35
|
handler: createHandler(core.api, {
|
|
33
36
|
basePath,
|
|
34
37
|
routes: options.routes
|
|
35
|
-
})
|
|
36
|
-
adapterName: core.adapterName,
|
|
37
|
-
createMigrator: core.createMigrator,
|
|
38
|
-
generateSchema: core.generateSchema
|
|
39
|
-
};
|
|
40
|
-
return {
|
|
41
|
-
...api,
|
|
42
|
-
basePath,
|
|
43
|
-
handler: api.handler
|
|
38
|
+
})
|
|
44
39
|
};
|
|
40
|
+
Object.defineProperties(api, Object.getOwnPropertyDescriptors(core.api));
|
|
41
|
+
return api;
|
|
45
42
|
}
|
|
46
43
|
//#endregion
|
|
47
44
|
export { createHotUpdater };
|
package/dist/db/pluginCore.cjs
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
require("../_virtual/_rolldown/runtime.cjs");
|
|
2
2
|
const require_schemaEnhancements = require("./schemaEnhancements.cjs");
|
|
3
3
|
const require_updateArtifacts = require("./updateArtifacts.cjs");
|
|
4
|
+
const require_requestBundleIdentityMap = require("./requestBundleIdentityMap.cjs");
|
|
4
5
|
let _hot_updater_plugin_core = require("@hot-updater/plugin-core");
|
|
5
6
|
let _hot_updater_core = require("@hot-updater/core");
|
|
6
7
|
//#region src/db/pluginCore.ts
|
|
@@ -111,109 +112,148 @@ function createPluginDatabaseCore(getPlugin, resolveFileUrl, options) {
|
|
|
111
112
|
enabled: true,
|
|
112
113
|
id: { gte: minBundleId }
|
|
113
114
|
});
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
return bundle.enabled && bundle.platform === args.platform && bundle.channel === channel && bundle.id.localeCompare(minBundleId) >= 0 && !!bundle.targetAppVersion && (0, _hot_updater_plugin_core.semverSatisfies)(bundle.targetAppVersion, args.appVersion);
|
|
146
|
-
}
|
|
147
|
-
});
|
|
148
|
-
},
|
|
149
|
-
async getAppUpdateInfo(args, context) {
|
|
150
|
-
const info = await this.getUpdateInfo(args, context);
|
|
151
|
-
if (!info) return null;
|
|
152
|
-
const { storageUri, ...rest } = info;
|
|
153
|
-
const readStorageText = options?.readStorageText;
|
|
154
|
-
if (info.id === _hot_updater_core.NIL_UUID || !readStorageText) {
|
|
155
|
-
const fileUrl = await resolveFileUrl(storageUri ?? null, context);
|
|
156
|
-
return {
|
|
157
|
-
...rest,
|
|
158
|
-
fileUrl
|
|
159
|
-
};
|
|
115
|
+
const api = {
|
|
116
|
+
async getBundleById(id, context) {
|
|
117
|
+
return getPlugin().getBundleById(id, context);
|
|
118
|
+
},
|
|
119
|
+
async getUpdateInfo(args, context) {
|
|
120
|
+
const directGetUpdateInfo = getPlugin().getUpdateInfo;
|
|
121
|
+
if (directGetUpdateInfo) return context === void 0 ? await directGetUpdateInfo(args) : await directGetUpdateInfo(args, context);
|
|
122
|
+
const channel = args.channel ?? "production";
|
|
123
|
+
const minBundleId = args.minBundleId ?? _hot_updater_core.NIL_UUID;
|
|
124
|
+
const baseWhere = getBaseWhere({
|
|
125
|
+
platform: args.platform,
|
|
126
|
+
channel,
|
|
127
|
+
minBundleId
|
|
128
|
+
});
|
|
129
|
+
if (args._updateStrategy === "fingerprint") return findUpdateInfoByScanning({
|
|
130
|
+
args,
|
|
131
|
+
queryWhere: {
|
|
132
|
+
...baseWhere,
|
|
133
|
+
fingerprintHash: args.fingerprintHash
|
|
134
|
+
},
|
|
135
|
+
context,
|
|
136
|
+
isCandidate: (bundle) => {
|
|
137
|
+
return bundle.enabled && bundle.platform === args.platform && bundle.channel === channel && bundle.id.localeCompare(minBundleId) >= 0 && bundle.fingerprintHash === args.fingerprintHash;
|
|
138
|
+
}
|
|
139
|
+
});
|
|
140
|
+
return findUpdateInfoByScanning({
|
|
141
|
+
args,
|
|
142
|
+
queryWhere: { ...baseWhere },
|
|
143
|
+
context,
|
|
144
|
+
isCandidate: (bundle) => {
|
|
145
|
+
return bundle.enabled && bundle.platform === args.platform && bundle.channel === channel && bundle.id.localeCompare(minBundleId) >= 0 && !!bundle.targetAppVersion && (0, _hot_updater_plugin_core.semverSatisfies)(bundle.targetAppVersion, args.appVersion);
|
|
160
146
|
}
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
147
|
+
});
|
|
148
|
+
},
|
|
149
|
+
async getAppUpdateInfo(args, context) {
|
|
150
|
+
const info = await this.getUpdateInfo(args, context);
|
|
151
|
+
if (!info) return null;
|
|
152
|
+
const { storageUri, ...rest } = info;
|
|
153
|
+
const readStorageText = options?.readStorageText;
|
|
154
|
+
if (info.id === _hot_updater_core.NIL_UUID || !readStorageText) {
|
|
155
|
+
const fileUrl = await resolveFileUrl(storageUri ?? null, context);
|
|
156
|
+
return {
|
|
167
157
|
...rest,
|
|
168
158
|
fileUrl
|
|
169
159
|
};
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
return
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
}
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
160
|
+
}
|
|
161
|
+
const requestBundleSeeds = (0, _hot_updater_plugin_core.getRequestUpdateBundleSeeds)(context);
|
|
162
|
+
const requestBundles = require_requestBundleIdentityMap.createRequestBundleIdentityMap({
|
|
163
|
+
context,
|
|
164
|
+
loadBundleById: (bundleId, requestContext) => getPlugin().getBundleById(bundleId, requestContext),
|
|
165
|
+
seeds: requestBundleSeeds
|
|
166
|
+
});
|
|
167
|
+
const getCurrentBundle = () => {
|
|
168
|
+
if (args.bundleId === _hot_updater_core.NIL_UUID) return null;
|
|
169
|
+
const seededCurrentBundle = requestBundles.peek(args.bundleId);
|
|
170
|
+
if (seededCurrentBundle || requestBundleSeeds.length > 0) return seededCurrentBundle;
|
|
171
|
+
return requestBundles.get(args.bundleId);
|
|
172
|
+
};
|
|
173
|
+
const [fileUrl, targetBundle, currentBundle] = await Promise.all([
|
|
174
|
+
resolveFileUrl(storageUri ?? null, context),
|
|
175
|
+
requestBundles.get(info.id),
|
|
176
|
+
getCurrentBundle()
|
|
177
|
+
]);
|
|
178
|
+
const baseResponse = {
|
|
179
|
+
...rest,
|
|
180
|
+
fileUrl
|
|
181
|
+
};
|
|
182
|
+
const manifestArtifacts = await require_updateArtifacts.resolveManifestArtifacts({
|
|
183
|
+
currentBundle,
|
|
184
|
+
resolveFileUrl,
|
|
185
|
+
readStorageText,
|
|
186
|
+
targetBundle,
|
|
187
|
+
context
|
|
188
|
+
});
|
|
189
|
+
if (!manifestArtifacts) return baseResponse;
|
|
190
|
+
return {
|
|
191
|
+
...baseResponse,
|
|
192
|
+
...manifestArtifacts
|
|
193
|
+
};
|
|
194
|
+
},
|
|
195
|
+
async getChannels(context) {
|
|
196
|
+
return getPlugin().getChannels(context);
|
|
197
|
+
},
|
|
198
|
+
async getBundles(options, context) {
|
|
199
|
+
return getPlugin().getBundles(options, context);
|
|
200
|
+
},
|
|
201
|
+
async insertBundle(bundle, context) {
|
|
202
|
+
require_schemaEnhancements.assertBundlePersistenceConstraints(bundle);
|
|
203
|
+
await runWithMutationPlugin(async (plugin) => {
|
|
204
|
+
await plugin.appendBundle(bundle, context);
|
|
205
|
+
await plugin.commitBundle(context);
|
|
206
|
+
});
|
|
207
|
+
},
|
|
208
|
+
async updateBundleById(bundleId, newBundle, context) {
|
|
209
|
+
await runWithMutationPlugin(async (plugin) => {
|
|
210
|
+
const current = await plugin.getBundleById(bundleId, context);
|
|
211
|
+
if (!current) throw new Error("targetBundleId not found");
|
|
212
|
+
require_schemaEnhancements.assertBundlePersistenceConstraints({
|
|
213
|
+
...current,
|
|
214
|
+
...newBundle
|
|
206
215
|
});
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
216
|
+
await plugin.updateBundle(bundleId, newBundle, context);
|
|
217
|
+
await plugin.commitBundle(context);
|
|
218
|
+
});
|
|
219
|
+
},
|
|
220
|
+
async deleteBundleById(bundleId, context) {
|
|
221
|
+
await runWithMutationPlugin(async (plugin) => {
|
|
222
|
+
const bundle = await plugin.getBundleById(bundleId, context);
|
|
223
|
+
if (!bundle) return;
|
|
224
|
+
await plugin.deleteBundle(bundle, context);
|
|
225
|
+
await plugin.commitBundle(context);
|
|
226
|
+
});
|
|
227
|
+
}
|
|
228
|
+
};
|
|
229
|
+
Object.defineProperty(api, "diagnostics", {
|
|
230
|
+
configurable: true,
|
|
231
|
+
enumerable: true,
|
|
232
|
+
get() {
|
|
233
|
+
const diagnostics = getPlugin().diagnostics;
|
|
234
|
+
if (!diagnostics) {
|
|
235
|
+
Object.defineProperty(this, "diagnostics", {
|
|
236
|
+
configurable: true,
|
|
237
|
+
enumerable: true,
|
|
238
|
+
value: void 0
|
|
214
239
|
});
|
|
240
|
+
return;
|
|
215
241
|
}
|
|
216
|
-
|
|
242
|
+
const wrappedDiagnostics = {};
|
|
243
|
+
if (diagnostics.bundleIndex) wrappedDiagnostics.bundleIndex = {
|
|
244
|
+
check: (context) => getPlugin().diagnostics.bundleIndex.check(context),
|
|
245
|
+
...diagnostics.bundleIndex.repair ? { repair: (context) => getPlugin().diagnostics.bundleIndex.repair(context) } : {}
|
|
246
|
+
};
|
|
247
|
+
Object.defineProperty(this, "diagnostics", {
|
|
248
|
+
configurable: true,
|
|
249
|
+
enumerable: true,
|
|
250
|
+
value: wrappedDiagnostics
|
|
251
|
+
});
|
|
252
|
+
return wrappedDiagnostics;
|
|
253
|
+
}
|
|
254
|
+
});
|
|
255
|
+
return {
|
|
256
|
+
api,
|
|
217
257
|
adapterName: getPlugin().name,
|
|
218
258
|
createMigrator: () => {
|
|
219
259
|
throw new Error("createMigrator is only available for Kysely/Prisma/Drizzle database adapters.");
|
package/dist/db/pluginCore.mjs
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { assertBundlePersistenceConstraints } from "./schemaEnhancements.mjs";
|
|
2
2
|
import { resolveManifestArtifacts } from "./updateArtifacts.mjs";
|
|
3
|
-
import {
|
|
3
|
+
import { createRequestBundleIdentityMap } from "./requestBundleIdentityMap.mjs";
|
|
4
|
+
import { getRequestUpdateBundleSeeds, semverSatisfies } from "@hot-updater/plugin-core";
|
|
4
5
|
import { NIL_UUID, isCohortEligibleForUpdate } from "@hot-updater/core";
|
|
5
6
|
//#region src/db/pluginCore.ts
|
|
6
7
|
const PAGE_SIZE = 100;
|
|
@@ -110,109 +111,148 @@ function createPluginDatabaseCore(getPlugin, resolveFileUrl, options) {
|
|
|
110
111
|
enabled: true,
|
|
111
112
|
id: { gte: minBundleId }
|
|
112
113
|
});
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
return bundle.enabled && bundle.platform === args.platform && bundle.channel === channel && bundle.id.localeCompare(minBundleId) >= 0 && !!bundle.targetAppVersion && semverSatisfies(bundle.targetAppVersion, args.appVersion);
|
|
145
|
-
}
|
|
146
|
-
});
|
|
147
|
-
},
|
|
148
|
-
async getAppUpdateInfo(args, context) {
|
|
149
|
-
const info = await this.getUpdateInfo(args, context);
|
|
150
|
-
if (!info) return null;
|
|
151
|
-
const { storageUri, ...rest } = info;
|
|
152
|
-
const readStorageText = options?.readStorageText;
|
|
153
|
-
if (info.id === NIL_UUID || !readStorageText) {
|
|
154
|
-
const fileUrl = await resolveFileUrl(storageUri ?? null, context);
|
|
155
|
-
return {
|
|
156
|
-
...rest,
|
|
157
|
-
fileUrl
|
|
158
|
-
};
|
|
114
|
+
const api = {
|
|
115
|
+
async getBundleById(id, context) {
|
|
116
|
+
return getPlugin().getBundleById(id, context);
|
|
117
|
+
},
|
|
118
|
+
async getUpdateInfo(args, context) {
|
|
119
|
+
const directGetUpdateInfo = getPlugin().getUpdateInfo;
|
|
120
|
+
if (directGetUpdateInfo) return context === void 0 ? await directGetUpdateInfo(args) : await directGetUpdateInfo(args, context);
|
|
121
|
+
const channel = args.channel ?? "production";
|
|
122
|
+
const minBundleId = args.minBundleId ?? NIL_UUID;
|
|
123
|
+
const baseWhere = getBaseWhere({
|
|
124
|
+
platform: args.platform,
|
|
125
|
+
channel,
|
|
126
|
+
minBundleId
|
|
127
|
+
});
|
|
128
|
+
if (args._updateStrategy === "fingerprint") return findUpdateInfoByScanning({
|
|
129
|
+
args,
|
|
130
|
+
queryWhere: {
|
|
131
|
+
...baseWhere,
|
|
132
|
+
fingerprintHash: args.fingerprintHash
|
|
133
|
+
},
|
|
134
|
+
context,
|
|
135
|
+
isCandidate: (bundle) => {
|
|
136
|
+
return bundle.enabled && bundle.platform === args.platform && bundle.channel === channel && bundle.id.localeCompare(minBundleId) >= 0 && bundle.fingerprintHash === args.fingerprintHash;
|
|
137
|
+
}
|
|
138
|
+
});
|
|
139
|
+
return findUpdateInfoByScanning({
|
|
140
|
+
args,
|
|
141
|
+
queryWhere: { ...baseWhere },
|
|
142
|
+
context,
|
|
143
|
+
isCandidate: (bundle) => {
|
|
144
|
+
return bundle.enabled && bundle.platform === args.platform && bundle.channel === channel && bundle.id.localeCompare(minBundleId) >= 0 && !!bundle.targetAppVersion && semverSatisfies(bundle.targetAppVersion, args.appVersion);
|
|
159
145
|
}
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
146
|
+
});
|
|
147
|
+
},
|
|
148
|
+
async getAppUpdateInfo(args, context) {
|
|
149
|
+
const info = await this.getUpdateInfo(args, context);
|
|
150
|
+
if (!info) return null;
|
|
151
|
+
const { storageUri, ...rest } = info;
|
|
152
|
+
const readStorageText = options?.readStorageText;
|
|
153
|
+
if (info.id === NIL_UUID || !readStorageText) {
|
|
154
|
+
const fileUrl = await resolveFileUrl(storageUri ?? null, context);
|
|
155
|
+
return {
|
|
166
156
|
...rest,
|
|
167
157
|
fileUrl
|
|
168
158
|
};
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
return
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
}
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
159
|
+
}
|
|
160
|
+
const requestBundleSeeds = getRequestUpdateBundleSeeds(context);
|
|
161
|
+
const requestBundles = createRequestBundleIdentityMap({
|
|
162
|
+
context,
|
|
163
|
+
loadBundleById: (bundleId, requestContext) => getPlugin().getBundleById(bundleId, requestContext),
|
|
164
|
+
seeds: requestBundleSeeds
|
|
165
|
+
});
|
|
166
|
+
const getCurrentBundle = () => {
|
|
167
|
+
if (args.bundleId === NIL_UUID) return null;
|
|
168
|
+
const seededCurrentBundle = requestBundles.peek(args.bundleId);
|
|
169
|
+
if (seededCurrentBundle || requestBundleSeeds.length > 0) return seededCurrentBundle;
|
|
170
|
+
return requestBundles.get(args.bundleId);
|
|
171
|
+
};
|
|
172
|
+
const [fileUrl, targetBundle, currentBundle] = await Promise.all([
|
|
173
|
+
resolveFileUrl(storageUri ?? null, context),
|
|
174
|
+
requestBundles.get(info.id),
|
|
175
|
+
getCurrentBundle()
|
|
176
|
+
]);
|
|
177
|
+
const baseResponse = {
|
|
178
|
+
...rest,
|
|
179
|
+
fileUrl
|
|
180
|
+
};
|
|
181
|
+
const manifestArtifacts = await resolveManifestArtifacts({
|
|
182
|
+
currentBundle,
|
|
183
|
+
resolveFileUrl,
|
|
184
|
+
readStorageText,
|
|
185
|
+
targetBundle,
|
|
186
|
+
context
|
|
187
|
+
});
|
|
188
|
+
if (!manifestArtifacts) return baseResponse;
|
|
189
|
+
return {
|
|
190
|
+
...baseResponse,
|
|
191
|
+
...manifestArtifacts
|
|
192
|
+
};
|
|
193
|
+
},
|
|
194
|
+
async getChannels(context) {
|
|
195
|
+
return getPlugin().getChannels(context);
|
|
196
|
+
},
|
|
197
|
+
async getBundles(options, context) {
|
|
198
|
+
return getPlugin().getBundles(options, context);
|
|
199
|
+
},
|
|
200
|
+
async insertBundle(bundle, context) {
|
|
201
|
+
assertBundlePersistenceConstraints(bundle);
|
|
202
|
+
await runWithMutationPlugin(async (plugin) => {
|
|
203
|
+
await plugin.appendBundle(bundle, context);
|
|
204
|
+
await plugin.commitBundle(context);
|
|
205
|
+
});
|
|
206
|
+
},
|
|
207
|
+
async updateBundleById(bundleId, newBundle, context) {
|
|
208
|
+
await runWithMutationPlugin(async (plugin) => {
|
|
209
|
+
const current = await plugin.getBundleById(bundleId, context);
|
|
210
|
+
if (!current) throw new Error("targetBundleId not found");
|
|
211
|
+
assertBundlePersistenceConstraints({
|
|
212
|
+
...current,
|
|
213
|
+
...newBundle
|
|
205
214
|
});
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
215
|
+
await plugin.updateBundle(bundleId, newBundle, context);
|
|
216
|
+
await plugin.commitBundle(context);
|
|
217
|
+
});
|
|
218
|
+
},
|
|
219
|
+
async deleteBundleById(bundleId, context) {
|
|
220
|
+
await runWithMutationPlugin(async (plugin) => {
|
|
221
|
+
const bundle = await plugin.getBundleById(bundleId, context);
|
|
222
|
+
if (!bundle) return;
|
|
223
|
+
await plugin.deleteBundle(bundle, context);
|
|
224
|
+
await plugin.commitBundle(context);
|
|
225
|
+
});
|
|
226
|
+
}
|
|
227
|
+
};
|
|
228
|
+
Object.defineProperty(api, "diagnostics", {
|
|
229
|
+
configurable: true,
|
|
230
|
+
enumerable: true,
|
|
231
|
+
get() {
|
|
232
|
+
const diagnostics = getPlugin().diagnostics;
|
|
233
|
+
if (!diagnostics) {
|
|
234
|
+
Object.defineProperty(this, "diagnostics", {
|
|
235
|
+
configurable: true,
|
|
236
|
+
enumerable: true,
|
|
237
|
+
value: void 0
|
|
213
238
|
});
|
|
239
|
+
return;
|
|
214
240
|
}
|
|
215
|
-
|
|
241
|
+
const wrappedDiagnostics = {};
|
|
242
|
+
if (diagnostics.bundleIndex) wrappedDiagnostics.bundleIndex = {
|
|
243
|
+
check: (context) => getPlugin().diagnostics.bundleIndex.check(context),
|
|
244
|
+
...diagnostics.bundleIndex.repair ? { repair: (context) => getPlugin().diagnostics.bundleIndex.repair(context) } : {}
|
|
245
|
+
};
|
|
246
|
+
Object.defineProperty(this, "diagnostics", {
|
|
247
|
+
configurable: true,
|
|
248
|
+
enumerable: true,
|
|
249
|
+
value: wrappedDiagnostics
|
|
250
|
+
});
|
|
251
|
+
return wrappedDiagnostics;
|
|
252
|
+
}
|
|
253
|
+
});
|
|
254
|
+
return {
|
|
255
|
+
api,
|
|
216
256
|
adapterName: getPlugin().name,
|
|
217
257
|
createMigrator: () => {
|
|
218
258
|
throw new Error("createMigrator is only available for Kysely/Prisma/Drizzle database adapters.");
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
//#region src/db/requestBundleIdentityMap.ts
|
|
2
|
+
const createRequestBundleIdentityMap = ({ context, loadBundleById, seeds }) => {
|
|
3
|
+
const bundles = /* @__PURE__ */ new Map();
|
|
4
|
+
const pendingBundles = /* @__PURE__ */ new Map();
|
|
5
|
+
for (const seed of seeds) if (seed) bundles.set(seed.id, seed);
|
|
6
|
+
const get = async (bundleId) => {
|
|
7
|
+
const cachedBundle = bundles.get(bundleId);
|
|
8
|
+
if (cachedBundle) return cachedBundle;
|
|
9
|
+
const pendingBundle = pendingBundles.get(bundleId);
|
|
10
|
+
if (pendingBundle) return pendingBundle;
|
|
11
|
+
const lookup = loadBundleById(bundleId, context).then((bundle) => {
|
|
12
|
+
pendingBundles.delete(bundleId);
|
|
13
|
+
if (bundle) bundles.set(bundle.id, bundle);
|
|
14
|
+
return bundle;
|
|
15
|
+
}, (error) => {
|
|
16
|
+
pendingBundles.delete(bundleId);
|
|
17
|
+
throw error;
|
|
18
|
+
});
|
|
19
|
+
pendingBundles.set(bundleId, lookup);
|
|
20
|
+
return lookup;
|
|
21
|
+
};
|
|
22
|
+
const peek = (bundleId) => bundles.get(bundleId) ?? null;
|
|
23
|
+
return {
|
|
24
|
+
get,
|
|
25
|
+
peek
|
|
26
|
+
};
|
|
27
|
+
};
|
|
28
|
+
//#endregion
|
|
29
|
+
exports.createRequestBundleIdentityMap = createRequestBundleIdentityMap;
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
//#region src/db/requestBundleIdentityMap.ts
|
|
2
|
+
const createRequestBundleIdentityMap = ({ context, loadBundleById, seeds }) => {
|
|
3
|
+
const bundles = /* @__PURE__ */ new Map();
|
|
4
|
+
const pendingBundles = /* @__PURE__ */ new Map();
|
|
5
|
+
for (const seed of seeds) if (seed) bundles.set(seed.id, seed);
|
|
6
|
+
const get = async (bundleId) => {
|
|
7
|
+
const cachedBundle = bundles.get(bundleId);
|
|
8
|
+
if (cachedBundle) return cachedBundle;
|
|
9
|
+
const pendingBundle = pendingBundles.get(bundleId);
|
|
10
|
+
if (pendingBundle) return pendingBundle;
|
|
11
|
+
const lookup = loadBundleById(bundleId, context).then((bundle) => {
|
|
12
|
+
pendingBundles.delete(bundleId);
|
|
13
|
+
if (bundle) bundles.set(bundle.id, bundle);
|
|
14
|
+
return bundle;
|
|
15
|
+
}, (error) => {
|
|
16
|
+
pendingBundles.delete(bundleId);
|
|
17
|
+
throw error;
|
|
18
|
+
});
|
|
19
|
+
pendingBundles.set(bundleId, lookup);
|
|
20
|
+
return lookup;
|
|
21
|
+
};
|
|
22
|
+
const peek = (bundleId) => bundles.get(bundleId) ?? null;
|
|
23
|
+
return {
|
|
24
|
+
get,
|
|
25
|
+
peek
|
|
26
|
+
};
|
|
27
|
+
};
|
|
28
|
+
//#endregion
|
|
29
|
+
export { createRequestBundleIdentityMap };
|
package/dist/db/types.d.cts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { Provider } from "../node_modules/.pnpm/fumadb@0.2.2_drizzle-orm@0.44.7_@cloudflare_workers-types@4.20260313.1_@electric-sql_pg_c72c8c754becd21f6d6662e8fbd28e7f/node_modules/fumadb/dist/index-CMqePMTF.cjs";
|
|
2
2
|
import { PaginatedResult } from "../types/index.cjs";
|
|
3
3
|
import { AppUpdateAvailableInfo, Bundle, GetBundlesArgs, UpdateInfo } from "@hot-updater/core";
|
|
4
|
-
import { DatabaseBundleQueryOptions, DatabasePlugin, HotUpdaterContext, RuntimeStoragePlugin } from "@hot-updater/plugin-core";
|
|
4
|
+
import { DatabaseBundleQueryOptions, DatabaseDiagnostics, DatabasePlugin, HotUpdaterContext, RuntimeStoragePlugin } from "@hot-updater/plugin-core";
|
|
5
5
|
|
|
6
6
|
//#region src/db/types.d.ts
|
|
7
7
|
type DatabasePluginFactory<TContext = unknown> = () => DatabasePlugin<TContext>;
|
|
@@ -27,6 +27,7 @@ interface DatabaseAPI<TContext = unknown> {
|
|
|
27
27
|
insertBundle(bundle: Bundle, context?: HotUpdaterContext<TContext>): Promise<void>;
|
|
28
28
|
updateBundleById(bundleId: string, newBundle: Partial<Bundle>, context?: HotUpdaterContext<TContext>): Promise<void>;
|
|
29
29
|
deleteBundleById(bundleId: string, context?: HotUpdaterContext<TContext>): Promise<void>;
|
|
30
|
+
diagnostics?: DatabaseDiagnostics<TContext>;
|
|
30
31
|
}
|
|
31
32
|
type StoragePluginFactory<TContext = unknown> = () => RuntimeStoragePlugin<TContext>;
|
|
32
33
|
//#endregion
|
package/dist/db/types.d.mts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { Provider } from "../node_modules/.pnpm/fumadb@0.2.2_drizzle-orm@0.44.7_@cloudflare_workers-types@4.20260313.1_@electric-sql_pg_c72c8c754becd21f6d6662e8fbd28e7f/node_modules/fumadb/dist/index-CMqePMTF.mjs";
|
|
2
2
|
import { PaginatedResult } from "../types/index.mjs";
|
|
3
|
-
import { DatabaseBundleQueryOptions, DatabasePlugin, HotUpdaterContext, RuntimeStoragePlugin } from "@hot-updater/plugin-core";
|
|
3
|
+
import { DatabaseBundleQueryOptions, DatabaseDiagnostics, DatabasePlugin, HotUpdaterContext, RuntimeStoragePlugin } from "@hot-updater/plugin-core";
|
|
4
4
|
import { AppUpdateAvailableInfo, Bundle as Bundle$1, GetBundlesArgs, UpdateInfo } from "@hot-updater/core";
|
|
5
5
|
|
|
6
6
|
//#region src/db/types.d.ts
|
|
@@ -27,6 +27,7 @@ interface DatabaseAPI<TContext = unknown> {
|
|
|
27
27
|
insertBundle(bundle: Bundle$1, context?: HotUpdaterContext<TContext>): Promise<void>;
|
|
28
28
|
updateBundleById(bundleId: string, newBundle: Partial<Bundle$1>, context?: HotUpdaterContext<TContext>): Promise<void>;
|
|
29
29
|
deleteBundleById(bundleId: string, context?: HotUpdaterContext<TContext>): Promise<void>;
|
|
30
|
+
diagnostics?: DatabaseDiagnostics<TContext>;
|
|
30
31
|
}
|
|
31
32
|
type StoragePluginFactory<TContext = unknown> = () => RuntimeStoragePlugin<TContext>;
|
|
32
33
|
//#endregion
|