@hot-updater/server 1.0.0-rc.2 → 1.0.0-rc.21
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/LICENSE +12 -14
- package/dist/adapters/drizzle.cjs +32 -75
- package/dist/adapters/drizzle.d.cts +13 -5
- package/dist/adapters/drizzle.d.mts +13 -5
- package/dist/adapters/drizzle.mjs +32 -77
- package/dist/adapters/drizzleExecutor.cjs +114 -0
- package/dist/adapters/drizzleExecutor.d.cts +9 -0
- package/dist/adapters/drizzleExecutor.d.mts +9 -0
- package/dist/adapters/drizzleExecutor.mjs +112 -0
- package/dist/adapters/kysely.cjs +22 -31
- package/dist/adapters/kysely.d.cts +10 -6
- package/dist/adapters/kysely.d.mts +10 -6
- package/dist/adapters/kysely.mjs +23 -33
- package/dist/adapters/kyselyExecutor.cjs +32 -0
- package/dist/adapters/kyselyExecutor.d.cts +11 -0
- package/dist/adapters/kyselyExecutor.d.mts +11 -0
- package/dist/adapters/kyselyExecutor.mjs +32 -0
- package/dist/adapters/mongodb.cjs +18 -54
- package/dist/adapters/mongodb.d.cts +10 -5
- package/dist/adapters/mongodb.d.mts +10 -5
- package/dist/adapters/mongodb.mjs +19 -56
- package/dist/adapters/mongodbAdapter.cjs +192 -0
- package/dist/adapters/mongodbAdapter.d.cts +9 -0
- package/dist/adapters/mongodbAdapter.d.mts +9 -0
- package/dist/adapters/mongodbAdapter.mjs +191 -0
- package/dist/adapters/prisma.cjs +35 -267
- package/dist/adapters/prisma.d.cts +12 -7
- package/dist/adapters/prisma.d.mts +12 -7
- package/dist/adapters/prisma.mjs +36 -268
- package/dist/adapters/prismaExecutor.cjs +63 -0
- package/dist/adapters/prismaExecutor.mjs +63 -0
- package/dist/adapters/sqlProviders.cjs +14 -0
- package/dist/adapters/sqlProviders.mjs +14 -0
- package/dist/assembly/assemblePlugins.cjs +144 -0
- package/dist/assembly/assemblePlugins.d.cts +5 -0
- package/dist/assembly/assemblePlugins.d.mts +5 -0
- package/dist/assembly/assemblePlugins.mjs +139 -0
- package/dist/assembly/clientPlugins.cjs +88 -0
- package/dist/assembly/clientPlugins.mjs +88 -0
- package/dist/assembly/configError.d.cts +2 -0
- package/dist/assembly/configError.d.mts +2 -0
- package/dist/assembly/configError.mjs +2 -0
- package/dist/core/api.cjs +51 -0
- package/dist/core/api.d.cts +54 -0
- package/dist/core/api.d.mts +54 -0
- package/dist/core/api.mjs +51 -0
- package/dist/core/baseCandidates.cjs +28 -0
- package/dist/core/baseCandidates.mjs +28 -0
- package/dist/core/operations.cjs +351 -0
- package/dist/core/operations.mjs +351 -0
- package/dist/core/reads.cjs +273 -0
- package/dist/core/reads.d.cts +9 -0
- package/dist/core/reads.d.mts +9 -0
- package/dist/core/reads.mjs +267 -0
- package/dist/core/releases.cjs +193 -0
- package/dist/core/releases.mjs +190 -0
- package/dist/core/writes.cjs +96 -0
- package/dist/core/writes.mjs +91 -0
- package/dist/createHotUpdaterCore.cjs +72 -91
- package/dist/createHotUpdaterCore.d.cts +106 -38
- package/dist/createHotUpdaterCore.d.mts +106 -38
- package/dist/createHotUpdaterCore.mjs +74 -89
- package/dist/db/engineDrizzleSchema.cjs +53 -0
- package/dist/db/engineDrizzleSchema.mjs +53 -0
- package/dist/db/enginePrismaSchema.cjs +84 -0
- package/dist/db/enginePrismaSchema.d.cts +5 -0
- package/dist/db/enginePrismaSchema.d.mts +5 -0
- package/dist/db/enginePrismaSchema.mjs +83 -0
- package/dist/db/releaseCatalog.cjs +24 -47
- package/dist/db/releaseCatalog.mjs +20 -44
- package/dist/db/updateArtifacts.cjs +43 -72
- package/dist/db/updateArtifacts.mjs +40 -69
- package/dist/handler.cjs +59 -43
- package/dist/handler.d.cts +3 -5
- package/dist/handler.d.mts +3 -5
- package/dist/handler.mjs +61 -43
- package/dist/handlerAdminRoutes.cjs +374 -0
- package/dist/handlerAdminRoutes.mjs +372 -0
- package/dist/handlerParameters.cjs +6 -11
- package/dist/handlerParameters.mjs +6 -10
- package/dist/handlerReleaseCatalogRoutes.cjs +32 -15
- package/dist/handlerReleaseCatalogRoutes.mjs +32 -15
- package/dist/handlerTypes.d.cts +2 -55
- package/dist/handlerTypes.d.mts +2 -55
- package/dist/handlerVersionRoutes.cjs +20 -4
- package/dist/handlerVersionRoutes.mjs +20 -4
- package/dist/index.cjs +9 -9
- package/dist/index.d.cts +8 -9
- package/dist/index.d.mts +8 -9
- package/dist/index.mjs +3 -4
- package/dist/node.cjs +3 -6
- package/dist/node.d.cts +2 -2
- package/dist/node.d.mts +2 -2
- package/dist/node.mjs +4 -4
- package/dist/package.cjs +1 -1
- package/dist/package.mjs +1 -1
- package/dist/plugins/api-keys/index.cjs +9 -0
- package/dist/plugins/api-keys/index.d.cts +1 -0
- package/dist/plugins/api-keys/index.d.mts +1 -0
- package/dist/plugins/api-keys/index.mjs +2 -0
- package/dist/plugins/definePlugin.d.cts +2 -0
- package/dist/plugins/definePlugin.d.mts +2 -0
- package/dist/plugins/insights/index.cjs +9 -0
- package/dist/plugins/insights/index.d.cts +1 -0
- package/dist/plugins/insights/index.d.mts +1 -0
- package/dist/plugins/insights/index.mjs +2 -0
- package/dist/plugins/official.cjs +30 -0
- package/dist/plugins/official.mjs +29 -0
- package/dist/storageAccess.cjs +13 -10
- package/dist/storageAccess.mjs +13 -10
- package/dist/types/index.d.cts +2 -28
- package/dist/types/index.d.mts +2 -28
- package/package.json +26 -14
- package/dist/_virtual/_rolldown/runtime.cjs +0 -23
- package/dist/adapters/databaseConstraintErrors.cjs +0 -22
- package/dist/adapters/databaseConstraintErrors.mjs +0 -21
- package/dist/adapters/databasePluginUtils.cjs +0 -116
- package/dist/adapters/databasePluginUtils.mjs +0 -106
- package/dist/adapters/drizzleCrud.cjs +0 -311
- package/dist/adapters/drizzleCrud.mjs +0 -308
- package/dist/adapters/drizzleLazyDB.cjs +0 -106
- package/dist/adapters/drizzleLazyDB.mjs +0 -106
- package/dist/adapters/drizzleQuery.cjs +0 -69
- package/dist/adapters/drizzleQuery.mjs +0 -69
- package/dist/adapters/insightsTransaction.cjs +0 -22
- package/dist/adapters/insightsTransaction.mjs +0 -22
- package/dist/adapters/kyselyCrud.cjs +0 -305
- package/dist/adapters/kyselyCrud.mjs +0 -304
- package/dist/adapters/kyselyQuery.cjs +0 -56
- package/dist/adapters/kyselyQuery.mjs +0 -56
- package/dist/adapters/mongodbCollections.cjs +0 -38
- package/dist/adapters/mongodbCollections.mjs +0 -32
- package/dist/adapters/mongodbQuery.cjs +0 -94
- package/dist/adapters/mongodbQuery.mjs +0 -86
- package/dist/adapters/mongodbReads.cjs +0 -210
- package/dist/adapters/mongodbReads.mjs +0 -210
- package/dist/adapters/mongodbWrites.cjs +0 -148
- package/dist/adapters/mongodbWrites.mjs +0 -148
- package/dist/adapters/prismaQuery.cjs +0 -57
- package/dist/adapters/prismaQuery.mjs +0 -56
- package/dist/adapters/prismaRows.cjs +0 -219
- package/dist/adapters/prismaRows.mjs +0 -209
- package/dist/apiKeys.cjs +0 -143
- package/dist/apiKeys.d.cts +0 -49
- package/dist/apiKeys.d.mts +0 -49
- package/dist/apiKeys.mjs +0 -133
- package/dist/db/createBundleDiff.cjs +0 -144
- package/dist/db/createBundleDiff.d.cts +0 -16
- package/dist/db/createBundleDiff.d.mts +0 -16
- package/dist/db/createBundleDiff.mjs +0 -141
- package/dist/db/databasePluginCore.cjs +0 -137
- package/dist/db/databasePluginCore.mjs +0 -137
- package/dist/db/fixedMigrator.cjs +0 -79
- package/dist/db/fixedMigrator.mjs +0 -78
- package/dist/db/fixedMigratorMongo.cjs +0 -321
- package/dist/db/fixedMigratorMongo.mjs +0 -321
- package/dist/db/fixedMigratorShared.cjs +0 -23
- package/dist/db/fixedMigratorShared.mjs +0 -18
- package/dist/db/index.cjs +0 -27
- package/dist/db/index.d.cts +0 -12
- package/dist/db/index.d.mts +0 -12
- package/dist/db/index.mjs +0 -22
- package/dist/db/mongoMigrationExecution.cjs +0 -11
- package/dist/db/mongoMigrationExecution.mjs +0 -11
- package/dist/db/releaseCatalog.d.cts +0 -16
- package/dist/db/releaseCatalog.d.mts +0 -16
- package/dist/db/schema/insightsCollation.cjs +0 -14
- package/dist/db/schema/insightsCollation.mjs +0 -14
- package/dist/db/schema/mongodb.cjs +0 -25
- package/dist/db/schema/mongodb.mjs +0 -25
- package/dist/db/schema/registry.cjs +0 -21
- package/dist/db/schema/registry.mjs +0 -17
- package/dist/db/schema/sql.cjs +0 -105
- package/dist/db/schema/sql.mjs +0 -97
- package/dist/db/schema/sqlOperations.cjs +0 -27
- package/dist/db/schema/sqlOperations.mjs +0 -26
- package/dist/db/schemaGenerators.cjs +0 -275
- package/dist/db/schemaGenerators.mjs +0 -273
- package/dist/db/schemaReadiness.cjs +0 -26
- package/dist/db/schemaReadiness.d.cts +0 -9
- package/dist/db/schemaReadiness.d.mts +0 -9
- package/dist/db/schemaReadiness.mjs +0 -25
- package/dist/db/sqlMigrationExecution.cjs +0 -67
- package/dist/db/sqlMigrationExecution.mjs +0 -67
- package/dist/db/types.cjs +0 -22
- package/dist/db/types.d.cts +0 -118
- package/dist/db/types.d.mts +0 -118
- package/dist/db/types.mjs +0 -19
- package/dist/handlerBundleRoutes.cjs +0 -155
- package/dist/handlerBundleRoutes.mjs +0 -155
- package/dist/handlerReleaseManagementRoutes.cjs +0 -124
- package/dist/handlerReleaseManagementRoutes.mjs +0 -124
- package/dist/insights/domain.d.cts +0 -89
- package/dist/insights/domain.d.mts +0 -89
- package/dist/insights/errors.cjs +0 -15
- package/dist/insights/errors.mjs +0 -14
- package/dist/insights/eventInput.cjs +0 -155
- package/dist/insights/eventInput.mjs +0 -153
- package/dist/insights/provider.cjs +0 -314
- package/dist/insights/provider.d.cts +0 -6
- package/dist/insights/provider.d.mts +0 -6
- package/dist/insights/provider.mjs +0 -314
- package/dist/insights/queryInput.cjs +0 -93
- package/dist/insights/queryInput.mjs +0 -91
- package/dist/insights/routes.cjs +0 -58
- package/dist/insights/routes.mjs +0 -56
- package/dist/insights/types.d.cts +0 -32
- package/dist/insights/types.d.mts +0 -32
- package/dist/schema/dsl.cjs +0 -103
- package/dist/schema/dsl.mjs +0 -87
- package/dist/schema/index.cjs +0 -20
- package/dist/schema/index.mjs +0 -7
- package/dist/schema/settings.cjs +0 -9
- package/dist/schema/settings.mjs +0 -9
- package/dist/schema/types.cjs +0 -8
- package/dist/schema/types.mjs +0 -6
- package/dist/schema/v1_0_0.cjs +0 -406
- package/dist/schema/v1_0_0.mjs +0 -398
- package/src/adapters/databaseConstraintErrors.ts +0 -25
- package/src/adapters/databasePluginTestDatabase.ts +0 -120
- package/src/adapters/databasePluginUtils.spec.ts +0 -29
- package/src/adapters/databasePluginUtils.ts +0 -214
- package/src/adapters/drizzle.spec.ts +0 -336
- package/src/adapters/drizzle.ts +0 -162
- package/src/adapters/drizzleCrud.ts +0 -571
- package/src/adapters/drizzleLazyDB.ts +0 -271
- package/src/adapters/drizzleQuery.ts +0 -164
- package/src/adapters/insightsTransaction.ts +0 -32
- package/src/adapters/kysely.spec.ts +0 -174
- package/src/adapters/kysely.ts +0 -110
- package/src/adapters/kyselyCrud.ts +0 -709
- package/src/adapters/kyselyQuery.ts +0 -128
- package/src/adapters/mongodb.integration.spec.ts +0 -210
- package/src/adapters/mongodb.spec.ts +0 -209
- package/src/adapters/mongodb.ts +0 -138
- package/src/adapters/mongodbCollections.ts +0 -67
- package/src/adapters/mongodbQuery.ts +0 -255
- package/src/adapters/mongodbReads.ts +0 -380
- package/src/adapters/mongodbRows.spec.ts +0 -64
- package/src/adapters/mongodbRows.ts +0 -118
- package/src/adapters/mongodbTestClient.ts +0 -377
- package/src/adapters/mongodbTestFilter.ts +0 -169
- package/src/adapters/mongodbWrites.ts +0 -287
- package/src/adapters/prisma.spec.ts +0 -293
- package/src/adapters/prisma.ts +0 -565
- package/src/adapters/prismaQuery.ts +0 -129
- package/src/adapters/prismaRows.spec.ts +0 -98
- package/src/adapters/prismaRows.ts +0 -337
- package/src/adapters/prismaTestClient.ts +0 -413
- package/src/apiKeys.integration.spec.ts +0 -192
- package/src/apiKeys.spec.ts +0 -162
- package/src/apiKeys.ts +0 -220
- package/src/calculatePagination.ts +0 -34
- package/src/createHotUpdaterCore.ts +0 -246
- package/src/db/bundleRows.spec.ts +0 -164
- package/src/db/bundleRows.ts +0 -10
- package/src/db/createBundleDiff.spec.ts +0 -450
- package/src/db/createBundleDiff.ts +0 -364
- package/src/db/databasePluginCore.spec.ts +0 -62
- package/src/db/databasePluginCore.testFixtures.ts +0 -76
- package/src/db/databasePluginCore.ts +0 -185
- package/src/db/databasePluginUpdateCheck.bench.ts +0 -110
- package/src/db/fixedMigrator.spec.ts +0 -296
- package/src/db/fixedMigrator.ts +0 -147
- package/src/db/fixedMigratorMongo.spec.ts +0 -239
- package/src/db/fixedMigratorMongo.ts +0 -425
- package/src/db/fixedMigratorShared.ts +0 -36
- package/src/db/hotUpdaterSchema.ts +0 -5
- package/src/db/index.spec.ts +0 -1269
- package/src/db/index.ts +0 -47
- package/src/db/mongoMigrationExecution.ts +0 -23
- package/src/db/node-sqlite.d.ts +0 -25
- package/src/db/releaseCatalog.ts +0 -148
- package/src/db/schema/definitions.ts +0 -1
- package/src/db/schema/insightsCollation.ts +0 -21
- package/src/db/schema/mongodb.ts +0 -40
- package/src/db/schema/registry.ts +0 -55
- package/src/db/schema/sql.ts +0 -244
- package/src/db/schema/sqlOperations.ts +0 -63
- package/src/db/schema/types.ts +0 -1
- package/src/db/schemaGenerators.ts +0 -494
- package/src/db/schemaReadiness.ts +0 -34
- package/src/db/sqlMigrationExecution.spec.ts +0 -65
- package/src/db/sqlMigrationExecution.ts +0 -108
- package/src/db/types.spec.ts +0 -63
- package/src/db/types.ts +0 -228
- package/src/db/updateArtifacts.spec.ts +0 -359
- package/src/db/updateArtifacts.ts +0 -541
- package/src/handler-standalone.integration.spec.ts +0 -528
- package/src/handler.spec.ts +0 -190
- package/src/handler.testFixtures.ts +0 -30
- package/src/handler.ts +0 -245
- package/src/handlerAuth.integration.spec.ts +0 -33
- package/src/handlerBundleRoutes.ts +0 -259
- package/src/handlerErrors.ts +0 -7
- package/src/handlerManagement.spec.ts +0 -262
- package/src/handlerParameters.ts +0 -105
- package/src/handlerReleaseCatalogRoutes.ts +0 -154
- package/src/handlerReleaseManagementRoutes.ts +0 -213
- package/src/handlerTypes.ts +0 -96
- package/src/handlerVersionRoutes.ts +0 -12
- package/src/index.ts +0 -30
- package/src/insights/domain.ts +0 -103
- package/src/insights/errors.ts +0 -11
- package/src/insights/eventInput.ts +0 -225
- package/src/insights/insights.integration.spec.ts +0 -381
- package/src/insights/provider.spec.ts +0 -385
- package/src/insights/provider.ts +0 -591
- package/src/insights/queryInput.ts +0 -141
- package/src/insights/routes.ts +0 -104
- package/src/insights/types.ts +0 -55
- package/src/internalRouter.ts +0 -104
- package/src/node.spec.ts +0 -119
- package/src/node.ts +0 -111
- package/src/releaseCatalogRoutes.integration.spec.ts +0 -238
- package/src/runtime.spec.ts +0 -194
- package/src/runtime.testFixtures.ts +0 -71
- package/src/schema/dsl-all-versions.spec.ts +0 -37
- package/src/schema/dsl.ts +0 -187
- package/src/schema/index.ts +0 -10
- package/src/schema/settings.ts +0 -15
- package/src/schema/types.ts +0 -79
- package/src/schema/v1_0_0.spec.ts +0 -220
- package/src/schema/v1_0_0.ts +0 -529
- package/src/storageAccess.spec.ts +0 -152
- package/src/storageAccess.ts +0 -141
- package/src/types/index.ts +0 -34
- package/src/version.ts +0 -3
package/src/adapters/prisma.ts
DELETED
|
@@ -1,565 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
createDatabasePlugin,
|
|
3
|
-
DatabasePluginInputError,
|
|
4
|
-
type InsightsRecordInput,
|
|
5
|
-
type InsightsModel,
|
|
6
|
-
} from "@hot-updater/plugin-core";
|
|
7
|
-
import {
|
|
8
|
-
createDatabasePluginAdapter,
|
|
9
|
-
type DatabaseImplementationResult,
|
|
10
|
-
type DatabasePluginImplementation,
|
|
11
|
-
type FindManyDatabaseImplementationInput,
|
|
12
|
-
type TransactionDatabasePluginImplementation,
|
|
13
|
-
} from "@hot-updater/plugin-core/internal";
|
|
14
|
-
|
|
15
|
-
import {
|
|
16
|
-
getHotUpdaterSchemaVersion,
|
|
17
|
-
hotUpdaterSchema,
|
|
18
|
-
} from "../db/schema/registry";
|
|
19
|
-
import { generatePrismaSchema } from "../db/schemaGenerators";
|
|
20
|
-
import type {
|
|
21
|
-
DatabaseAdapterWithCapabilities,
|
|
22
|
-
ORMProvider,
|
|
23
|
-
ORMSQLProvider,
|
|
24
|
-
SchemaGenerator,
|
|
25
|
-
} from "../db/types";
|
|
26
|
-
import {
|
|
27
|
-
isChannelDeleteReferencedError,
|
|
28
|
-
translateChannelDeleteError,
|
|
29
|
-
} from "./databaseConstraintErrors";
|
|
30
|
-
import { hasNullOrderOverrides, sortRowsByOrder } from "./databasePluginUtils";
|
|
31
|
-
import { createPrismaOrderBy, createPrismaWhere } from "./prismaQuery";
|
|
32
|
-
import {
|
|
33
|
-
getPrismaDelegate,
|
|
34
|
-
parsePrismaBundleEventRow,
|
|
35
|
-
parsePrismaInsightsInstallationRow,
|
|
36
|
-
parsePrismaBundleRow,
|
|
37
|
-
parsePrismaChannelRow,
|
|
38
|
-
parsePrismaApiKeyRow,
|
|
39
|
-
parsePrismaPatchRow,
|
|
40
|
-
parsePrismaReleaseCatalogRow,
|
|
41
|
-
parsePrismaReleaseRow,
|
|
42
|
-
parsePrismaRows,
|
|
43
|
-
PrismaAdapterError,
|
|
44
|
-
} from "./prismaRows";
|
|
45
|
-
|
|
46
|
-
type PrismaRelationMode = "prisma" | "foreign-keys";
|
|
47
|
-
|
|
48
|
-
type PrismaTransactionOptions = {
|
|
49
|
-
readonly isolationLevel: "Serializable";
|
|
50
|
-
};
|
|
51
|
-
|
|
52
|
-
type PrismaTransactionClient = object & {
|
|
53
|
-
readonly $transaction: <TResult>(
|
|
54
|
-
callback: (client: object) => Promise<TResult>,
|
|
55
|
-
options?: PrismaTransactionOptions,
|
|
56
|
-
) => Promise<TResult>;
|
|
57
|
-
};
|
|
58
|
-
|
|
59
|
-
export interface PrismaConfig {
|
|
60
|
-
readonly prisma: object;
|
|
61
|
-
readonly provider: ORMSQLProvider;
|
|
62
|
-
readonly relationMode?: PrismaRelationMode;
|
|
63
|
-
readonly db?: unknown;
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
const hasCallbackTransaction = (
|
|
67
|
-
client: object,
|
|
68
|
-
): client is PrismaTransactionClient =>
|
|
69
|
-
"$transaction" in client && typeof client.$transaction === "function";
|
|
70
|
-
|
|
71
|
-
const runPrismaTransaction = <TResult>(
|
|
72
|
-
client: PrismaTransactionClient,
|
|
73
|
-
isolationLevel: "default" | "serializable",
|
|
74
|
-
callback: (client: object) => Promise<TResult>,
|
|
75
|
-
retryUniqueConflict = false,
|
|
76
|
-
): Promise<TResult> => {
|
|
77
|
-
const execute = () =>
|
|
78
|
-
isolationLevel === "serializable"
|
|
79
|
-
? client.$transaction(callback, { isolationLevel: "Serializable" })
|
|
80
|
-
: client.$transaction(callback);
|
|
81
|
-
if (isolationLevel === "default") return execute();
|
|
82
|
-
|
|
83
|
-
return (async () => {
|
|
84
|
-
for (let attempt = 0; ; attempt += 1) {
|
|
85
|
-
try {
|
|
86
|
-
return await execute();
|
|
87
|
-
} catch (error) {
|
|
88
|
-
if (
|
|
89
|
-
attempt >= 2 ||
|
|
90
|
-
typeof error !== "object" ||
|
|
91
|
-
error === null ||
|
|
92
|
-
!("code" in error) ||
|
|
93
|
-
(error.code !== "P2034" &&
|
|
94
|
-
!(retryUniqueConflict && error.code === "P2002"))
|
|
95
|
-
) {
|
|
96
|
-
throw error;
|
|
97
|
-
}
|
|
98
|
-
}
|
|
99
|
-
}
|
|
100
|
-
})();
|
|
101
|
-
};
|
|
102
|
-
|
|
103
|
-
const assertPrismaProvider = (provider: ORMProvider): void => {
|
|
104
|
-
if (provider === "mongodb") {
|
|
105
|
-
throw new PrismaAdapterError(
|
|
106
|
-
"Prisma adapter does not support MongoDB; use mongodbAdapter instead",
|
|
107
|
-
);
|
|
108
|
-
}
|
|
109
|
-
};
|
|
110
|
-
|
|
111
|
-
const findMany = async (
|
|
112
|
-
client: object,
|
|
113
|
-
input: FindManyDatabaseImplementationInput,
|
|
114
|
-
provider: ORMSQLProvider,
|
|
115
|
-
): Promise<readonly DatabaseImplementationResult[]> => {
|
|
116
|
-
if (input.distinctOn !== undefined) {
|
|
117
|
-
throw new DatabasePluginInputError("invalid-operation");
|
|
118
|
-
}
|
|
119
|
-
const rawOrderBy = input.orderBy;
|
|
120
|
-
const orderBy = createPrismaOrderBy(rawOrderBy);
|
|
121
|
-
const shouldSortInMemory =
|
|
122
|
-
rawOrderBy !== undefined && hasNullOrderOverrides(rawOrderBy);
|
|
123
|
-
const rows = shouldSortInMemory
|
|
124
|
-
? sortRowsByOrder(
|
|
125
|
-
(await getPrismaDelegate(client, input.model).findMany({
|
|
126
|
-
where: createPrismaWhere(input.where, provider),
|
|
127
|
-
})) as Record<string, unknown>[],
|
|
128
|
-
rawOrderBy,
|
|
129
|
-
).slice(input.offset, input.offset + input.limit)
|
|
130
|
-
: await getPrismaDelegate(client, input.model).findMany({
|
|
131
|
-
where: createPrismaWhere(input.where, provider),
|
|
132
|
-
...(orderBy ? { orderBy } : {}),
|
|
133
|
-
skip: input.offset,
|
|
134
|
-
take: input.limit,
|
|
135
|
-
});
|
|
136
|
-
switch (input.model) {
|
|
137
|
-
case "bundles":
|
|
138
|
-
return parsePrismaRows(rows, parsePrismaBundleRow);
|
|
139
|
-
case "bundle_patches":
|
|
140
|
-
return parsePrismaRows(rows, parsePrismaPatchRow);
|
|
141
|
-
case "bundle_events":
|
|
142
|
-
return parsePrismaRows(rows, parsePrismaBundleEventRow);
|
|
143
|
-
case "bundle_installations":
|
|
144
|
-
return parsePrismaRows(rows, parsePrismaInsightsInstallationRow);
|
|
145
|
-
case "channels":
|
|
146
|
-
return parsePrismaRows(rows, parsePrismaChannelRow);
|
|
147
|
-
case "api_keys":
|
|
148
|
-
return parsePrismaRows(rows, parsePrismaApiKeyRow);
|
|
149
|
-
case "releases":
|
|
150
|
-
return parsePrismaRows(rows, parsePrismaReleaseRow);
|
|
151
|
-
case "release_catalogs":
|
|
152
|
-
return parsePrismaRows(rows, parsePrismaReleaseCatalogRow);
|
|
153
|
-
}
|
|
154
|
-
};
|
|
155
|
-
|
|
156
|
-
const assertPatchReferences = async (
|
|
157
|
-
client: object,
|
|
158
|
-
bundleId: string,
|
|
159
|
-
baseBundleId: string,
|
|
160
|
-
): Promise<void> => {
|
|
161
|
-
const ids = Array.from(new Set([bundleId, baseBundleId]));
|
|
162
|
-
const count = await getPrismaDelegate(client, "bundles").count({
|
|
163
|
-
where: { id: { in: ids } },
|
|
164
|
-
});
|
|
165
|
-
if (count !== ids.length) {
|
|
166
|
-
throw new PrismaAdapterError("patch references a missing bundle");
|
|
167
|
-
}
|
|
168
|
-
};
|
|
169
|
-
|
|
170
|
-
const createCrudImplementation = (
|
|
171
|
-
client: object,
|
|
172
|
-
provider: ORMSQLProvider,
|
|
173
|
-
relationMode: PrismaRelationMode,
|
|
174
|
-
): TransactionDatabasePluginImplementation &
|
|
175
|
-
Pick<DatabasePluginImplementation, "deleteChannel" | "insertChannel"> => ({
|
|
176
|
-
deleteChannel: async ({ id }) => {
|
|
177
|
-
const channels = getPrismaDelegate(client, "channels");
|
|
178
|
-
const existing = await channels.findFirst({ where: { id } });
|
|
179
|
-
if (existing === null) return { deleted: false, reason: "not_found" };
|
|
180
|
-
const referencedReleases = await getPrismaDelegate(
|
|
181
|
-
client,
|
|
182
|
-
"releases",
|
|
183
|
-
).count({ where: { channel_id: id } });
|
|
184
|
-
if (referencedReleases > 0) {
|
|
185
|
-
return { deleted: false, reason: "not_empty" };
|
|
186
|
-
}
|
|
187
|
-
try {
|
|
188
|
-
await channels.deleteMany({ where: { id } });
|
|
189
|
-
} catch (error) {
|
|
190
|
-
if (isChannelDeleteReferencedError(error)) {
|
|
191
|
-
return { deleted: false, reason: "not_empty" };
|
|
192
|
-
}
|
|
193
|
-
throw error;
|
|
194
|
-
}
|
|
195
|
-
return { deleted: true };
|
|
196
|
-
},
|
|
197
|
-
insertChannel: async (input) => {
|
|
198
|
-
const delegate = getPrismaDelegate(client, "channels");
|
|
199
|
-
const existing = await delegate.findFirst({
|
|
200
|
-
where: { name: input.row.name },
|
|
201
|
-
});
|
|
202
|
-
if (existing !== null) {
|
|
203
|
-
return { row: parsePrismaChannelRow(existing), inserted: false };
|
|
204
|
-
}
|
|
205
|
-
const row = parsePrismaChannelRow(
|
|
206
|
-
await delegate.upsert({
|
|
207
|
-
where: { name: input.row.name },
|
|
208
|
-
create: input.row,
|
|
209
|
-
update: {},
|
|
210
|
-
}),
|
|
211
|
-
);
|
|
212
|
-
return { row, inserted: row.id === input.row.id };
|
|
213
|
-
},
|
|
214
|
-
create: async (input) => {
|
|
215
|
-
if (input.model === "bundle_patches") {
|
|
216
|
-
await assertPatchReferences(
|
|
217
|
-
client,
|
|
218
|
-
input.data.bundle_id,
|
|
219
|
-
input.data.base_bundle_id,
|
|
220
|
-
);
|
|
221
|
-
}
|
|
222
|
-
const delegate = getPrismaDelegate(client, input.model);
|
|
223
|
-
let row: unknown;
|
|
224
|
-
if (input.onConflict === "ignore") {
|
|
225
|
-
const where =
|
|
226
|
-
input.model === "channels"
|
|
227
|
-
? { name: input.data.name }
|
|
228
|
-
: input.model === "api_keys"
|
|
229
|
-
? { hash: input.data.hash }
|
|
230
|
-
: { install_id: input.data.install_id };
|
|
231
|
-
row = await delegate.upsert({
|
|
232
|
-
where,
|
|
233
|
-
create: input.data,
|
|
234
|
-
update: {},
|
|
235
|
-
});
|
|
236
|
-
} else {
|
|
237
|
-
row = await delegate.create({ data: input.data });
|
|
238
|
-
}
|
|
239
|
-
switch (input.model) {
|
|
240
|
-
case "bundles":
|
|
241
|
-
return parsePrismaBundleRow(row);
|
|
242
|
-
case "bundle_patches":
|
|
243
|
-
return parsePrismaPatchRow(row);
|
|
244
|
-
case "bundle_events":
|
|
245
|
-
return parsePrismaBundleEventRow(row);
|
|
246
|
-
case "bundle_installations":
|
|
247
|
-
return parsePrismaInsightsInstallationRow(row);
|
|
248
|
-
case "channels":
|
|
249
|
-
return parsePrismaChannelRow(row);
|
|
250
|
-
case "api_keys":
|
|
251
|
-
return parsePrismaApiKeyRow(row);
|
|
252
|
-
case "releases":
|
|
253
|
-
return parsePrismaReleaseRow(row);
|
|
254
|
-
case "release_catalogs":
|
|
255
|
-
return parsePrismaReleaseCatalogRow(row);
|
|
256
|
-
}
|
|
257
|
-
},
|
|
258
|
-
update: async (input) => {
|
|
259
|
-
if (input.model === "bundle_installations") {
|
|
260
|
-
const installId = input.where.find(
|
|
261
|
-
(item) =>
|
|
262
|
-
item.field === "install_id" &&
|
|
263
|
-
(item.operator === undefined || item.operator === "eq") &&
|
|
264
|
-
typeof item.value === "string",
|
|
265
|
-
)?.value;
|
|
266
|
-
if (typeof installId !== "string") {
|
|
267
|
-
throw new PrismaAdapterError(
|
|
268
|
-
"bundle_installations update requires install_id",
|
|
269
|
-
);
|
|
270
|
-
}
|
|
271
|
-
const delegate = getPrismaDelegate(client, "bundle_installations");
|
|
272
|
-
if (delegate.updateMany === undefined) {
|
|
273
|
-
throw new PrismaAdapterError(
|
|
274
|
-
'model delegate "bundle_installations" requires updateMany',
|
|
275
|
-
);
|
|
276
|
-
}
|
|
277
|
-
const result = await delegate.updateMany({
|
|
278
|
-
where: createPrismaWhere(input.where, provider),
|
|
279
|
-
data: input.update,
|
|
280
|
-
});
|
|
281
|
-
if (result.count === 0) return null;
|
|
282
|
-
const stored = await delegate.findFirst({
|
|
283
|
-
where: { install_id: installId },
|
|
284
|
-
});
|
|
285
|
-
return stored === null
|
|
286
|
-
? null
|
|
287
|
-
: parsePrismaInsightsInstallationRow(stored);
|
|
288
|
-
}
|
|
289
|
-
const id = input.where[0]?.value;
|
|
290
|
-
if (typeof id !== "string") {
|
|
291
|
-
throw new PrismaAdapterError(
|
|
292
|
-
`${input.model} update requires a string id`,
|
|
293
|
-
);
|
|
294
|
-
}
|
|
295
|
-
if (input.model === "api_keys") {
|
|
296
|
-
const delegate = getPrismaDelegate(client, "api_keys");
|
|
297
|
-
const current = await delegate.findFirst({ where: { id } });
|
|
298
|
-
if (current === null) return null;
|
|
299
|
-
await delegate.update({ where: { id }, data: input.update });
|
|
300
|
-
const stored = await delegate.findFirst({ where: { id } });
|
|
301
|
-
return stored === null ? null : parsePrismaApiKeyRow(stored);
|
|
302
|
-
}
|
|
303
|
-
if (input.model === "releases") {
|
|
304
|
-
const delegate = getPrismaDelegate(client, "releases");
|
|
305
|
-
const current = await delegate.findFirst({ where: { id } });
|
|
306
|
-
if (current === null) return null;
|
|
307
|
-
await delegate.update({ where: { id }, data: input.update });
|
|
308
|
-
const stored = await delegate.findFirst({ where: { id } });
|
|
309
|
-
return stored === null ? null : parsePrismaReleaseRow(stored);
|
|
310
|
-
}
|
|
311
|
-
if (input.model === "release_catalogs") {
|
|
312
|
-
const delegate = getPrismaDelegate(client, "release_catalogs");
|
|
313
|
-
const current = await delegate.findFirst({ where: { scope_key: id } });
|
|
314
|
-
if (current === null) return null;
|
|
315
|
-
await delegate.update({ where: { scope_key: id }, data: input.update });
|
|
316
|
-
const stored = await delegate.findFirst({ where: { scope_key: id } });
|
|
317
|
-
return stored === null ? null : parsePrismaReleaseCatalogRow(stored);
|
|
318
|
-
}
|
|
319
|
-
const delegate = getPrismaDelegate(client, "bundles");
|
|
320
|
-
if (delegate.updateMany === undefined) {
|
|
321
|
-
throw new PrismaAdapterError(
|
|
322
|
-
'model delegate "bundles" requires updateMany',
|
|
323
|
-
);
|
|
324
|
-
}
|
|
325
|
-
const current = await delegate.findFirst({ where: { id } });
|
|
326
|
-
if (current === null) return null;
|
|
327
|
-
await delegate.updateMany({
|
|
328
|
-
where: { id },
|
|
329
|
-
data: input.update,
|
|
330
|
-
});
|
|
331
|
-
const stored = await delegate.findFirst({ where: { id } });
|
|
332
|
-
if (stored === null) return null;
|
|
333
|
-
return parsePrismaBundleRow(stored);
|
|
334
|
-
},
|
|
335
|
-
delete: async (input) => {
|
|
336
|
-
if (input.model === "bundles" && relationMode === "prisma") {
|
|
337
|
-
const rows = await getPrismaDelegate(client, "bundles").findMany({
|
|
338
|
-
where: createPrismaWhere(input.where, provider),
|
|
339
|
-
});
|
|
340
|
-
const ids = parsePrismaRows(rows, parsePrismaBundleRow).map(
|
|
341
|
-
({ id }) => id,
|
|
342
|
-
);
|
|
343
|
-
if (ids.length === 0) return;
|
|
344
|
-
await getPrismaDelegate(client, "bundle_patches").deleteMany({
|
|
345
|
-
where: {
|
|
346
|
-
OR: [{ bundle_id: { in: ids } }, { base_bundle_id: { in: ids } }],
|
|
347
|
-
},
|
|
348
|
-
});
|
|
349
|
-
}
|
|
350
|
-
try {
|
|
351
|
-
await getPrismaDelegate(client, input.model).deleteMany({
|
|
352
|
-
where: createPrismaWhere(input.where, provider),
|
|
353
|
-
});
|
|
354
|
-
} catch (error) {
|
|
355
|
-
if (input.model === "channels") {
|
|
356
|
-
translateChannelDeleteError(error);
|
|
357
|
-
}
|
|
358
|
-
throw error;
|
|
359
|
-
}
|
|
360
|
-
},
|
|
361
|
-
count: async (input) => {
|
|
362
|
-
if (input.distinct !== undefined) {
|
|
363
|
-
throw new DatabasePluginInputError("invalid-operation");
|
|
364
|
-
}
|
|
365
|
-
return getPrismaDelegate(client, input.model).count({
|
|
366
|
-
where: createPrismaWhere(input.where, provider),
|
|
367
|
-
});
|
|
368
|
-
},
|
|
369
|
-
findOne: async (input) => {
|
|
370
|
-
const row = await getPrismaDelegate(client, input.model).findFirst({
|
|
371
|
-
where: createPrismaWhere(input.where, provider),
|
|
372
|
-
});
|
|
373
|
-
if (row === null) return null;
|
|
374
|
-
switch (input.model) {
|
|
375
|
-
case "bundles":
|
|
376
|
-
return parsePrismaBundleRow(row);
|
|
377
|
-
case "bundle_patches":
|
|
378
|
-
return parsePrismaPatchRow(row);
|
|
379
|
-
case "channels":
|
|
380
|
-
return parsePrismaChannelRow(row);
|
|
381
|
-
case "api_keys":
|
|
382
|
-
return parsePrismaApiKeyRow(row);
|
|
383
|
-
case "releases":
|
|
384
|
-
return parsePrismaReleaseRow(row);
|
|
385
|
-
case "release_catalogs":
|
|
386
|
-
return parsePrismaReleaseCatalogRow(row);
|
|
387
|
-
case "bundle_installations":
|
|
388
|
-
return parsePrismaInsightsInstallationRow(row);
|
|
389
|
-
}
|
|
390
|
-
},
|
|
391
|
-
findMany: (input) => findMany(client, input, provider),
|
|
392
|
-
});
|
|
393
|
-
|
|
394
|
-
const createPrismaImplementation = (
|
|
395
|
-
client: object,
|
|
396
|
-
relationMode: PrismaRelationMode,
|
|
397
|
-
provider: ORMSQLProvider,
|
|
398
|
-
): DatabasePluginImplementation => {
|
|
399
|
-
const crud = createCrudImplementation(client, provider, relationMode);
|
|
400
|
-
const implementation: DatabasePluginImplementation = {
|
|
401
|
-
...crud,
|
|
402
|
-
recordInsights: (input: InsightsRecordInput) => {
|
|
403
|
-
if (!hasCallbackTransaction(client)) {
|
|
404
|
-
throw new PrismaAdapterError(
|
|
405
|
-
"Insights recording requires callback transactions",
|
|
406
|
-
);
|
|
407
|
-
}
|
|
408
|
-
return runPrismaTransaction(
|
|
409
|
-
client,
|
|
410
|
-
"serializable",
|
|
411
|
-
async (transactionClient) => {
|
|
412
|
-
const events = getPrismaDelegate(transactionClient, "bundle_events");
|
|
413
|
-
if (
|
|
414
|
-
(await events.findFirst({ where: { id: input.event.id } })) !== null
|
|
415
|
-
)
|
|
416
|
-
return;
|
|
417
|
-
await events.create({ data: input.event });
|
|
418
|
-
const installations = getPrismaDelegate(
|
|
419
|
-
transactionClient,
|
|
420
|
-
"bundle_installations",
|
|
421
|
-
);
|
|
422
|
-
const existing = await installations.findFirst({
|
|
423
|
-
where: { install_id: input.installation.install_id },
|
|
424
|
-
});
|
|
425
|
-
if (existing === null) {
|
|
426
|
-
await installations.create({ data: input.installation });
|
|
427
|
-
return;
|
|
428
|
-
}
|
|
429
|
-
const current = parsePrismaInsightsInstallationRow(existing);
|
|
430
|
-
if (
|
|
431
|
-
current.received_at_ms > input.installation.received_at_ms ||
|
|
432
|
-
(current.received_at_ms === input.installation.received_at_ms &&
|
|
433
|
-
current.id >= input.installation.id)
|
|
434
|
-
)
|
|
435
|
-
return;
|
|
436
|
-
await installations.update({
|
|
437
|
-
where: { install_id: input.installation.install_id },
|
|
438
|
-
data: input.installation,
|
|
439
|
-
});
|
|
440
|
-
},
|
|
441
|
-
true,
|
|
442
|
-
);
|
|
443
|
-
},
|
|
444
|
-
deleteChannel: (input) => {
|
|
445
|
-
if (!hasCallbackTransaction(client)) {
|
|
446
|
-
throw new PrismaAdapterError(
|
|
447
|
-
"channel deletion requires callback transactions",
|
|
448
|
-
);
|
|
449
|
-
}
|
|
450
|
-
return runPrismaTransaction(client, "serializable", (transactionClient) =>
|
|
451
|
-
createCrudImplementation(
|
|
452
|
-
transactionClient,
|
|
453
|
-
provider,
|
|
454
|
-
relationMode,
|
|
455
|
-
).deleteChannel(input),
|
|
456
|
-
);
|
|
457
|
-
},
|
|
458
|
-
delete: (input) => {
|
|
459
|
-
if (input.model !== "bundles" || relationMode === "foreign-keys") {
|
|
460
|
-
return crud.delete(input);
|
|
461
|
-
}
|
|
462
|
-
if (!hasCallbackTransaction(client)) {
|
|
463
|
-
throw new PrismaAdapterError(
|
|
464
|
-
'relation mode "prisma" requires callback transactions',
|
|
465
|
-
);
|
|
466
|
-
}
|
|
467
|
-
return runPrismaTransaction(client, "serializable", (transactionClient) =>
|
|
468
|
-
createCrudImplementation(
|
|
469
|
-
transactionClient,
|
|
470
|
-
provider,
|
|
471
|
-
relationMode,
|
|
472
|
-
).delete(input),
|
|
473
|
-
);
|
|
474
|
-
},
|
|
475
|
-
};
|
|
476
|
-
if (relationMode === "prisma" && !hasCallbackTransaction(client)) {
|
|
477
|
-
throw new PrismaAdapterError(
|
|
478
|
-
'relation mode "prisma" requires callback transactions',
|
|
479
|
-
);
|
|
480
|
-
}
|
|
481
|
-
if (!hasCallbackTransaction(client)) return implementation;
|
|
482
|
-
if (relationMode === "prisma") {
|
|
483
|
-
implementation.create = (input) =>
|
|
484
|
-
runPrismaTransaction(client, "serializable", (transactionClient) =>
|
|
485
|
-
createCrudImplementation(
|
|
486
|
-
transactionClient,
|
|
487
|
-
provider,
|
|
488
|
-
relationMode,
|
|
489
|
-
).create(input),
|
|
490
|
-
);
|
|
491
|
-
}
|
|
492
|
-
implementation.update = (input) =>
|
|
493
|
-
runPrismaTransaction(
|
|
494
|
-
client,
|
|
495
|
-
relationMode === "prisma" ? "serializable" : "default",
|
|
496
|
-
(transactionClient) =>
|
|
497
|
-
createCrudImplementation(
|
|
498
|
-
transactionClient,
|
|
499
|
-
provider,
|
|
500
|
-
relationMode,
|
|
501
|
-
).update(input),
|
|
502
|
-
);
|
|
503
|
-
return {
|
|
504
|
-
...implementation,
|
|
505
|
-
transaction: (callback) =>
|
|
506
|
-
runPrismaTransaction(
|
|
507
|
-
client,
|
|
508
|
-
"serializable",
|
|
509
|
-
async (transactionClient) => {
|
|
510
|
-
return callback(
|
|
511
|
-
createCrudImplementation(transactionClient, provider, relationMode),
|
|
512
|
-
);
|
|
513
|
-
},
|
|
514
|
-
),
|
|
515
|
-
};
|
|
516
|
-
};
|
|
517
|
-
|
|
518
|
-
export const prismaAdapter = (
|
|
519
|
-
config: PrismaConfig,
|
|
520
|
-
): DatabaseAdapterWithCapabilities => {
|
|
521
|
-
assertPrismaProvider(config.provider);
|
|
522
|
-
const adapter = createDatabasePluginAdapter(
|
|
523
|
-
"prisma",
|
|
524
|
-
createPrismaImplementation(
|
|
525
|
-
config.prisma,
|
|
526
|
-
config.relationMode ?? "foreign-keys",
|
|
527
|
-
config.provider,
|
|
528
|
-
),
|
|
529
|
-
);
|
|
530
|
-
const unsupportedMssqlInsights = async (): Promise<never> => {
|
|
531
|
-
throw new PrismaAdapterError(
|
|
532
|
-
"SQL Server Insights is unsupported: string keys pad trailing spaces and do not provide the required exact UTF-8 identity ordering",
|
|
533
|
-
);
|
|
534
|
-
};
|
|
535
|
-
const insights: InsightsModel =
|
|
536
|
-
config.provider === "mssql"
|
|
537
|
-
? {
|
|
538
|
-
record: unsupportedMssqlInsights,
|
|
539
|
-
listEvents: unsupportedMssqlInsights,
|
|
540
|
-
findInstallations: unsupportedMssqlInsights,
|
|
541
|
-
countInstallations: unsupportedMssqlInsights,
|
|
542
|
-
countEvents: unsupportedMssqlInsights,
|
|
543
|
-
}
|
|
544
|
-
: adapter.models.insights;
|
|
545
|
-
return Object.assign(
|
|
546
|
-
createDatabasePlugin({
|
|
547
|
-
name: "prisma",
|
|
548
|
-
models: { ...adapter.models, insights },
|
|
549
|
-
commit: adapter.commit,
|
|
550
|
-
}),
|
|
551
|
-
{
|
|
552
|
-
adapterName: "prisma",
|
|
553
|
-
provider: config.provider,
|
|
554
|
-
generateSchema: ((version) => ({
|
|
555
|
-
code: generatePrismaSchema(
|
|
556
|
-
config.provider,
|
|
557
|
-
version === "latest"
|
|
558
|
-
? hotUpdaterSchema
|
|
559
|
-
: getHotUpdaterSchemaVersion(version),
|
|
560
|
-
),
|
|
561
|
-
path: "./prisma/schema/hot_updater.prisma",
|
|
562
|
-
})) satisfies SchemaGenerator,
|
|
563
|
-
},
|
|
564
|
-
);
|
|
565
|
-
};
|
|
@@ -1,129 +0,0 @@
|
|
|
1
|
-
import { DatabasePluginInputError } from "@hot-updater/plugin-core";
|
|
2
|
-
import type {
|
|
3
|
-
DatabaseModel,
|
|
4
|
-
DatabaseOrderBy,
|
|
5
|
-
DatabaseSortBy,
|
|
6
|
-
DatabaseWhere,
|
|
7
|
-
} from "@hot-updater/plugin-core/internal";
|
|
8
|
-
|
|
9
|
-
import type { ORMProvider } from "../db/types";
|
|
10
|
-
|
|
11
|
-
export type PrismaQuery = Readonly<Record<string, unknown>>;
|
|
12
|
-
type AnyDatabaseWhere = {
|
|
13
|
-
readonly [TModel in DatabaseModel]: DatabaseWhere<TModel>;
|
|
14
|
-
}[DatabaseModel];
|
|
15
|
-
type AnyDatabaseSortBy = {
|
|
16
|
-
readonly [TModel in DatabaseModel]: DatabaseSortBy<TModel>;
|
|
17
|
-
}[DatabaseModel];
|
|
18
|
-
type AnyDatabaseOrderBy = {
|
|
19
|
-
readonly [TModel in DatabaseModel]: DatabaseOrderBy<TModel>;
|
|
20
|
-
}[DatabaseModel];
|
|
21
|
-
|
|
22
|
-
const stringFilter = (
|
|
23
|
-
operator: "contains" | "ends_with" | "starts_with",
|
|
24
|
-
value: string,
|
|
25
|
-
mode: "default" | undefined,
|
|
26
|
-
): PrismaQuery => {
|
|
27
|
-
const key =
|
|
28
|
-
operator === "starts_with"
|
|
29
|
-
? "startsWith"
|
|
30
|
-
: operator === "ends_with"
|
|
31
|
-
? "endsWith"
|
|
32
|
-
: "contains";
|
|
33
|
-
return {
|
|
34
|
-
[key]: value,
|
|
35
|
-
...(mode ? { mode } : {}),
|
|
36
|
-
};
|
|
37
|
-
};
|
|
38
|
-
|
|
39
|
-
const SQL_PATTERN_METACHARACTERS = /[%_\\]/u;
|
|
40
|
-
const MONGODB_PATTERN_METACHARACTERS = /[.*+?^${}()|[\]\\]/u;
|
|
41
|
-
|
|
42
|
-
const prismaMode = (
|
|
43
|
-
mode: "insensitive" | "sensitive" | undefined,
|
|
44
|
-
provider: ORMProvider,
|
|
45
|
-
): "default" | undefined => {
|
|
46
|
-
if (
|
|
47
|
-
mode === "insensitive" ||
|
|
48
|
-
(mode === "sensitive" && provider !== "postgresql")
|
|
49
|
-
) {
|
|
50
|
-
throw new DatabasePluginInputError("invalid-operation");
|
|
51
|
-
}
|
|
52
|
-
return mode === "sensitive" ? "default" : undefined;
|
|
53
|
-
};
|
|
54
|
-
|
|
55
|
-
const assertLiteralPattern = (value: string, provider: ORMProvider): void => {
|
|
56
|
-
const pattern =
|
|
57
|
-
provider === "mongodb"
|
|
58
|
-
? MONGODB_PATTERN_METACHARACTERS
|
|
59
|
-
: SQL_PATTERN_METACHARACTERS;
|
|
60
|
-
if (pattern.test(value)) {
|
|
61
|
-
throw new DatabasePluginInputError("invalid-operation");
|
|
62
|
-
}
|
|
63
|
-
};
|
|
64
|
-
|
|
65
|
-
const predicate = (
|
|
66
|
-
where: AnyDatabaseWhere,
|
|
67
|
-
provider: ORMProvider,
|
|
68
|
-
): PrismaQuery => {
|
|
69
|
-
const mode = prismaMode("mode" in where ? where.mode : undefined, provider);
|
|
70
|
-
switch (where.operator) {
|
|
71
|
-
case undefined:
|
|
72
|
-
case "eq":
|
|
73
|
-
return {
|
|
74
|
-
[where.field]: mode ? { equals: where.value, mode } : where.value,
|
|
75
|
-
};
|
|
76
|
-
case "ne":
|
|
77
|
-
return {
|
|
78
|
-
[where.field]: {
|
|
79
|
-
not: where.value,
|
|
80
|
-
...(mode ? { mode } : {}),
|
|
81
|
-
},
|
|
82
|
-
};
|
|
83
|
-
case "gt":
|
|
84
|
-
case "gte":
|
|
85
|
-
case "lt":
|
|
86
|
-
case "lte":
|
|
87
|
-
return { [where.field]: { [where.operator]: where.value } };
|
|
88
|
-
case "in":
|
|
89
|
-
return { [where.field]: { in: where.value } };
|
|
90
|
-
case "not_in":
|
|
91
|
-
return { [where.field]: { notIn: where.value } };
|
|
92
|
-
case "contains":
|
|
93
|
-
case "starts_with":
|
|
94
|
-
case "ends_with": {
|
|
95
|
-
assertLiteralPattern(where.value, provider);
|
|
96
|
-
return {
|
|
97
|
-
[where.field]: stringFilter(where.operator, where.value, mode),
|
|
98
|
-
};
|
|
99
|
-
}
|
|
100
|
-
}
|
|
101
|
-
};
|
|
102
|
-
|
|
103
|
-
export const createPrismaWhere = (
|
|
104
|
-
where: readonly AnyDatabaseWhere[] | undefined,
|
|
105
|
-
provider: ORMProvider,
|
|
106
|
-
): PrismaQuery => {
|
|
107
|
-
const items = where ?? [];
|
|
108
|
-
const first = items[0];
|
|
109
|
-
if (first === undefined) return {};
|
|
110
|
-
|
|
111
|
-
let result = predicate(first, provider);
|
|
112
|
-
for (const item of items.slice(1)) {
|
|
113
|
-
result = {
|
|
114
|
-
[item.connector === "OR" ? "OR" : "AND"]: [
|
|
115
|
-
result,
|
|
116
|
-
predicate(item, provider),
|
|
117
|
-
],
|
|
118
|
-
};
|
|
119
|
-
}
|
|
120
|
-
return result;
|
|
121
|
-
};
|
|
122
|
-
|
|
123
|
-
export const createPrismaOrderBy = (
|
|
124
|
-
orderBy: AnyDatabaseOrderBy | readonly AnyDatabaseSortBy[] | undefined,
|
|
125
|
-
): PrismaQuery | PrismaQuery[] | undefined => {
|
|
126
|
-
if (orderBy === undefined) return undefined;
|
|
127
|
-
const clauses = Array.isArray(orderBy) ? orderBy : [orderBy];
|
|
128
|
-
return clauses.map((clause) => ({ [clause.field]: clause.direction }));
|
|
129
|
-
};
|