pocketbase-zod-schema 0.2.5 → 0.3.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/CHANGELOG.md +8 -0
- package/dist/cli/index.cjs +374 -296
- package/dist/cli/index.cjs.map +1 -1
- package/dist/cli/index.d.cts +2 -2
- package/dist/cli/index.d.ts +2 -2
- package/dist/cli/index.js +374 -296
- package/dist/cli/index.js.map +1 -1
- package/dist/cli/migrate.cjs +374 -296
- package/dist/cli/migrate.cjs.map +1 -1
- package/dist/cli/migrate.js +374 -296
- package/dist/cli/migrate.js.map +1 -1
- package/dist/cli/utils/index.d.cts +2 -2
- package/dist/cli/utils/index.d.ts +2 -2
- package/dist/{fields-YjcpBXVp.d.cts → fields-UcOPu1OQ.d.cts} +16 -0
- package/dist/{fields-YjcpBXVp.d.ts → fields-UcOPu1OQ.d.ts} +16 -0
- package/dist/index.cjs +413 -114
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +4 -4
- package/dist/index.d.ts +4 -4
- package/dist/index.js +414 -103
- package/dist/index.js.map +1 -1
- package/dist/migration/analyzer.cjs +12 -2
- package/dist/migration/analyzer.cjs.map +1 -1
- package/dist/migration/analyzer.d.cts +2 -2
- package/dist/migration/analyzer.d.ts +2 -2
- package/dist/migration/analyzer.js +12 -2
- package/dist/migration/analyzer.js.map +1 -1
- package/dist/migration/diff.cjs +76 -1
- package/dist/migration/diff.cjs.map +1 -1
- package/dist/migration/diff.d.cts +2 -2
- package/dist/migration/diff.d.ts +2 -2
- package/dist/migration/diff.js +76 -1
- package/dist/migration/diff.js.map +1 -1
- package/dist/migration/generator.cjs +323 -46
- package/dist/migration/generator.cjs.map +1 -1
- package/dist/migration/generator.d.cts +59 -12
- package/dist/migration/generator.d.ts +59 -12
- package/dist/migration/generator.js +319 -47
- package/dist/migration/generator.js.map +1 -1
- package/dist/migration/index.cjs +399 -49
- package/dist/migration/index.cjs.map +1 -1
- package/dist/migration/index.d.cts +3 -3
- package/dist/migration/index.d.ts +3 -3
- package/dist/migration/index.js +399 -49
- package/dist/migration/index.js.map +1 -1
- package/dist/migration/snapshot.cjs.map +1 -1
- package/dist/migration/snapshot.d.cts +2 -2
- package/dist/migration/snapshot.d.ts +2 -2
- package/dist/migration/snapshot.js.map +1 -1
- package/dist/migration/utils/index.cjs +64 -0
- package/dist/migration/utils/index.cjs.map +1 -1
- package/dist/migration/utils/index.d.cts +39 -202
- package/dist/migration/utils/index.d.ts +39 -202
- package/dist/migration/utils/index.js +63 -1
- package/dist/migration/utils/index.js.map +1 -1
- package/dist/schema.cjs +0 -61
- package/dist/schema.cjs.map +1 -1
- package/dist/schema.d.cts +2 -86
- package/dist/schema.d.ts +2 -86
- package/dist/schema.js +1 -50
- package/dist/schema.js.map +1 -1
- package/dist/type-mapper-DrQmtznD.d.cts +208 -0
- package/dist/type-mapper-n231Fspm.d.ts +208 -0
- package/dist/{types-LFBGHl9Y.d.ts → types-Ds3NQvny.d.ts} +33 -2
- package/dist/{types-mhQXWNi3.d.cts → types-YoBjsa-A.d.cts} +33 -2
- package/package.json +1 -1
package/dist/cli/migrate.js
CHANGED
|
@@ -7,6 +7,7 @@ import * as path5 from 'path';
|
|
|
7
7
|
import { dirname, join } from 'path';
|
|
8
8
|
import { fileURLToPath } from 'url';
|
|
9
9
|
import { z } from 'zod';
|
|
10
|
+
import { randomBytes } from 'crypto';
|
|
10
11
|
import ora from 'ora';
|
|
11
12
|
|
|
12
13
|
({
|
|
@@ -1292,12 +1293,22 @@ function isAuthCollection(fields) {
|
|
|
1292
1293
|
function buildFieldDefinition(fieldName, zodType) {
|
|
1293
1294
|
const fieldMetadata = extractFieldMetadata(zodType.description);
|
|
1294
1295
|
if (fieldMetadata) {
|
|
1295
|
-
|
|
1296
|
+
let required2;
|
|
1297
|
+
if (fieldMetadata.type === "number") {
|
|
1298
|
+
if (fieldMetadata.options?.required !== void 0) {
|
|
1299
|
+
required2 = fieldMetadata.options.required;
|
|
1300
|
+
} else {
|
|
1301
|
+
required2 = false;
|
|
1302
|
+
}
|
|
1303
|
+
} else {
|
|
1304
|
+
required2 = isFieldRequired(zodType);
|
|
1305
|
+
}
|
|
1306
|
+
const { required: _required, ...options2 } = fieldMetadata.options || {};
|
|
1296
1307
|
const fieldDef2 = {
|
|
1297
1308
|
name: fieldName,
|
|
1298
1309
|
type: fieldMetadata.type,
|
|
1299
1310
|
required: required2,
|
|
1300
|
-
options:
|
|
1311
|
+
options: Object.keys(options2).length > 0 ? options2 : void 0
|
|
1301
1312
|
};
|
|
1302
1313
|
if (fieldMetadata.type === "relation") {
|
|
1303
1314
|
const relationMetadata2 = extractRelationMetadata(zodType.description);
|
|
@@ -1467,6 +1478,65 @@ async function buildSchemaDefinition(config) {
|
|
|
1467
1478
|
async function parseSchemaFiles(config) {
|
|
1468
1479
|
return buildSchemaDefinition(config);
|
|
1469
1480
|
}
|
|
1481
|
+
function generateCollectionId() {
|
|
1482
|
+
const chars = "abcdefghijklmnopqrstuvwxyz0123456789";
|
|
1483
|
+
const idLength = 15;
|
|
1484
|
+
const bytes = randomBytes(idLength);
|
|
1485
|
+
let id = "pb_";
|
|
1486
|
+
for (let i = 0; i < idLength; i++) {
|
|
1487
|
+
const index = bytes[i] % chars.length;
|
|
1488
|
+
id += chars[index];
|
|
1489
|
+
}
|
|
1490
|
+
return id;
|
|
1491
|
+
}
|
|
1492
|
+
var CollectionIdRegistry = class {
|
|
1493
|
+
ids;
|
|
1494
|
+
constructor() {
|
|
1495
|
+
this.ids = /* @__PURE__ */ new Set();
|
|
1496
|
+
}
|
|
1497
|
+
/**
|
|
1498
|
+
* Generates a unique collection ID for a given collection name
|
|
1499
|
+
* Special case: Returns constant "_pb_users_auth_" for users collection
|
|
1500
|
+
* Retries up to 10 times if collision occurs (extremely rare)
|
|
1501
|
+
*
|
|
1502
|
+
* @param collectionName - The name of the collection
|
|
1503
|
+
* @returns A unique collection ID
|
|
1504
|
+
* @throws Error if unable to generate unique ID after max attempts
|
|
1505
|
+
*/
|
|
1506
|
+
generate(collectionName) {
|
|
1507
|
+
if (collectionName && collectionName.toLowerCase() === "users") {
|
|
1508
|
+
const usersId = "_pb_users_auth_";
|
|
1509
|
+
this.register(usersId);
|
|
1510
|
+
return usersId;
|
|
1511
|
+
}
|
|
1512
|
+
const maxAttempts = 10;
|
|
1513
|
+
for (let attempt = 0; attempt < maxAttempts; attempt++) {
|
|
1514
|
+
const id = generateCollectionId();
|
|
1515
|
+
if (!this.has(id)) {
|
|
1516
|
+
this.register(id);
|
|
1517
|
+
return id;
|
|
1518
|
+
}
|
|
1519
|
+
}
|
|
1520
|
+
throw new Error("Failed to generate unique collection ID after maximum attempts");
|
|
1521
|
+
}
|
|
1522
|
+
/**
|
|
1523
|
+
* Checks if an ID has already been registered
|
|
1524
|
+
*
|
|
1525
|
+
* @param id - The collection ID to check
|
|
1526
|
+
* @returns True if the ID exists in the registry
|
|
1527
|
+
*/
|
|
1528
|
+
has(id) {
|
|
1529
|
+
return this.ids.has(id);
|
|
1530
|
+
}
|
|
1531
|
+
/**
|
|
1532
|
+
* Registers a collection ID in the registry
|
|
1533
|
+
*
|
|
1534
|
+
* @param id - The collection ID to register
|
|
1535
|
+
*/
|
|
1536
|
+
register(id) {
|
|
1537
|
+
this.ids.add(id);
|
|
1538
|
+
}
|
|
1539
|
+
};
|
|
1470
1540
|
|
|
1471
1541
|
// src/migration/diff.ts
|
|
1472
1542
|
var DEFAULT_CONFIG2 = {
|
|
@@ -1798,6 +1868,18 @@ function aggregateChanges(currentSchema, previousSnapshot, config) {
|
|
|
1798
1868
|
const filteredCollectionsToDelete = collectionsToDelete.filter(
|
|
1799
1869
|
(collection) => !isSystemCollection(collection.name, config)
|
|
1800
1870
|
);
|
|
1871
|
+
const registry = new CollectionIdRegistry();
|
|
1872
|
+
const collectionsWithIds = filteredCollectionsToCreate.map((collection) => {
|
|
1873
|
+
if (collection.id) {
|
|
1874
|
+
registry.register(collection.id);
|
|
1875
|
+
return collection;
|
|
1876
|
+
}
|
|
1877
|
+
const id = registry.generate(collection.name);
|
|
1878
|
+
return {
|
|
1879
|
+
...collection,
|
|
1880
|
+
id
|
|
1881
|
+
};
|
|
1882
|
+
});
|
|
1801
1883
|
const collectionsToModify = [];
|
|
1802
1884
|
const matchedCollections = matchCollectionsByName(currentSchema, previousSnapshot);
|
|
1803
1885
|
for (const [currentCollection, previousCollection] of matchedCollections) {
|
|
@@ -1807,7 +1889,7 @@ function aggregateChanges(currentSchema, previousSnapshot, config) {
|
|
|
1807
1889
|
}
|
|
1808
1890
|
}
|
|
1809
1891
|
return {
|
|
1810
|
-
collectionsToCreate:
|
|
1892
|
+
collectionsToCreate: collectionsWithIds,
|
|
1811
1893
|
collectionsToDelete: filteredCollectionsToDelete,
|
|
1812
1894
|
collectionsToModify
|
|
1813
1895
|
};
|
|
@@ -1890,42 +1972,48 @@ function generateTimestamp(config) {
|
|
|
1890
1972
|
}
|
|
1891
1973
|
return Math.floor(Date.now() / 1e3).toString();
|
|
1892
1974
|
}
|
|
1893
|
-
function
|
|
1894
|
-
const
|
|
1895
|
-
|
|
1896
|
-
|
|
1897
|
-
|
|
1898
|
-
|
|
1899
|
-
|
|
1900
|
-
|
|
1901
|
-
|
|
1902
|
-
|
|
1903
|
-
if (diff.collectionsToDelete.length === 1) {
|
|
1904
|
-
parts.push(`deleted_${diff.collectionsToDelete[0].name}`);
|
|
1905
|
-
} else {
|
|
1906
|
-
parts.push(`deleted_${diff.collectionsToDelete.length}_collections`);
|
|
1907
|
-
}
|
|
1908
|
-
}
|
|
1909
|
-
if (diff.collectionsToModify.length > 0) {
|
|
1910
|
-
if (diff.collectionsToModify.length === 1) {
|
|
1911
|
-
parts.push(`updated_${diff.collectionsToModify[0].collection}`);
|
|
1912
|
-
} else {
|
|
1913
|
-
parts.push(`updated_${diff.collectionsToModify.length}_collections`);
|
|
1914
|
-
}
|
|
1975
|
+
function splitDiffByCollection(diff, baseTimestamp) {
|
|
1976
|
+
const operations = [];
|
|
1977
|
+
let currentTimestamp = parseInt(baseTimestamp, 10);
|
|
1978
|
+
for (const collection of diff.collectionsToCreate) {
|
|
1979
|
+
operations.push({
|
|
1980
|
+
type: "create",
|
|
1981
|
+
collection,
|
|
1982
|
+
timestamp: currentTimestamp.toString()
|
|
1983
|
+
});
|
|
1984
|
+
currentTimestamp += 1;
|
|
1915
1985
|
}
|
|
1916
|
-
|
|
1917
|
-
|
|
1986
|
+
for (const modification of diff.collectionsToModify) {
|
|
1987
|
+
operations.push({
|
|
1988
|
+
type: "modify",
|
|
1989
|
+
collection: modification.collection,
|
|
1990
|
+
modifications: modification,
|
|
1991
|
+
timestamp: currentTimestamp.toString()
|
|
1992
|
+
});
|
|
1993
|
+
currentTimestamp += 1;
|
|
1918
1994
|
}
|
|
1919
|
-
|
|
1920
|
-
|
|
1921
|
-
|
|
1995
|
+
for (const collection of diff.collectionsToDelete) {
|
|
1996
|
+
operations.push({
|
|
1997
|
+
type: "delete",
|
|
1998
|
+
collection: collection.name || collection,
|
|
1999
|
+
// Handle both object and string
|
|
2000
|
+
timestamp: currentTimestamp.toString()
|
|
2001
|
+
});
|
|
2002
|
+
currentTimestamp += 1;
|
|
1922
2003
|
}
|
|
1923
|
-
return
|
|
2004
|
+
return operations;
|
|
1924
2005
|
}
|
|
1925
|
-
function
|
|
1926
|
-
const timestamp =
|
|
1927
|
-
const
|
|
1928
|
-
|
|
2006
|
+
function generateCollectionMigrationFilename(operation) {
|
|
2007
|
+
const timestamp = operation.timestamp;
|
|
2008
|
+
const operationType = operation.type === "modify" ? "updated" : operation.type === "create" ? "created" : "deleted";
|
|
2009
|
+
let collectionName;
|
|
2010
|
+
if (typeof operation.collection === "string") {
|
|
2011
|
+
collectionName = operation.collection;
|
|
2012
|
+
} else {
|
|
2013
|
+
collectionName = operation.collection.name;
|
|
2014
|
+
}
|
|
2015
|
+
const sanitizedName = collectionName.replace(/[^a-zA-Z0-9_]/g, "_").toLowerCase();
|
|
2016
|
+
return `${timestamp}_${operationType}_${sanitizedName}.js`;
|
|
1929
2017
|
}
|
|
1930
2018
|
function createMigrationFileStructure(upCode, downCode, config) {
|
|
1931
2019
|
const mergedConfig = config ? mergeConfig3(config) : DEFAULT_CONFIG3;
|
|
@@ -1997,14 +2085,13 @@ function formatValue(value) {
|
|
|
1997
2085
|
return "null";
|
|
1998
2086
|
}
|
|
1999
2087
|
if (typeof value === "string") {
|
|
2000
|
-
return
|
|
2088
|
+
return JSON.stringify(value);
|
|
2001
2089
|
}
|
|
2002
2090
|
if (typeof value === "number" || typeof value === "boolean") {
|
|
2003
2091
|
return String(value);
|
|
2004
2092
|
}
|
|
2005
2093
|
if (Array.isArray(value)) {
|
|
2006
|
-
|
|
2007
|
-
return `[${items}]`;
|
|
2094
|
+
return JSON.stringify(value).replace(/","/g, '", "');
|
|
2008
2095
|
}
|
|
2009
2096
|
if (typeof value === "object") {
|
|
2010
2097
|
const entries = Object.entries(value).map(([k, v]) => `${k}: ${formatValue(v)}`).join(", ");
|
|
@@ -2012,7 +2099,7 @@ function formatValue(value) {
|
|
|
2012
2099
|
}
|
|
2013
2100
|
return String(value);
|
|
2014
2101
|
}
|
|
2015
|
-
function generateFieldDefinitionObject(field) {
|
|
2102
|
+
function generateFieldDefinitionObject(field, collectionIdMap) {
|
|
2016
2103
|
const parts = [];
|
|
2017
2104
|
parts.push(` name: "${field.name}"`);
|
|
2018
2105
|
parts.push(` type: "${field.type}"`);
|
|
@@ -2020,34 +2107,47 @@ function generateFieldDefinitionObject(field) {
|
|
|
2020
2107
|
if (field.unique !== void 0) {
|
|
2021
2108
|
parts.push(` unique: ${field.unique}`);
|
|
2022
2109
|
}
|
|
2110
|
+
if (field.type === "select") {
|
|
2111
|
+
const maxSelect = field.options?.maxSelect ?? 1;
|
|
2112
|
+
parts.push(` maxSelect: ${maxSelect}`);
|
|
2113
|
+
const values = field.options?.values ?? [];
|
|
2114
|
+
parts.push(` values: ${formatValue(values)}`);
|
|
2115
|
+
}
|
|
2023
2116
|
if (field.options && Object.keys(field.options).length > 0) {
|
|
2024
2117
|
for (const [key, value] of Object.entries(field.options)) {
|
|
2118
|
+
if (field.type === "select" && (key === "maxSelect" || key === "values")) {
|
|
2119
|
+
continue;
|
|
2120
|
+
}
|
|
2025
2121
|
parts.push(` ${key}: ${formatValue(value)}`);
|
|
2026
2122
|
}
|
|
2027
2123
|
}
|
|
2028
2124
|
if (field.relation) {
|
|
2029
2125
|
const isUsersCollection = field.relation.collection.toLowerCase() === "users";
|
|
2030
|
-
|
|
2031
|
-
|
|
2032
|
-
|
|
2033
|
-
|
|
2034
|
-
|
|
2035
|
-
|
|
2036
|
-
|
|
2037
|
-
}
|
|
2038
|
-
if (field.relation.cascadeDelete !== void 0) {
|
|
2039
|
-
parts.push(` cascadeDelete: ${field.relation.cascadeDelete}`);
|
|
2126
|
+
let collectionIdValue;
|
|
2127
|
+
if (isUsersCollection) {
|
|
2128
|
+
collectionIdValue = '"_pb_users_auth_"';
|
|
2129
|
+
} else if (collectionIdMap && collectionIdMap.has(field.relation.collection)) {
|
|
2130
|
+
collectionIdValue = `"${collectionIdMap.get(field.relation.collection)}"`;
|
|
2131
|
+
} else {
|
|
2132
|
+
collectionIdValue = `app.findCollectionByNameOrId("${field.relation.collection}").id`;
|
|
2040
2133
|
}
|
|
2134
|
+
parts.push(` collectionId: ${collectionIdValue}`);
|
|
2135
|
+
const maxSelect = field.relation.maxSelect ?? 1;
|
|
2136
|
+
parts.push(` maxSelect: ${maxSelect}`);
|
|
2137
|
+
const minSelect = field.relation.minSelect ?? null;
|
|
2138
|
+
parts.push(` minSelect: ${minSelect}`);
|
|
2139
|
+
const cascadeDelete = field.relation.cascadeDelete ?? false;
|
|
2140
|
+
parts.push(` cascadeDelete: ${cascadeDelete}`);
|
|
2041
2141
|
}
|
|
2042
2142
|
return ` {
|
|
2043
2143
|
${parts.join(",\n")},
|
|
2044
2144
|
}`;
|
|
2045
2145
|
}
|
|
2046
|
-
function generateFieldsArray(fields) {
|
|
2146
|
+
function generateFieldsArray(fields, collectionIdMap) {
|
|
2047
2147
|
if (fields.length === 0) {
|
|
2048
2148
|
return "[]";
|
|
2049
2149
|
}
|
|
2050
|
-
const fieldObjects = fields.map((field) => generateFieldDefinitionObject(field));
|
|
2150
|
+
const fieldObjects = fields.map((field) => generateFieldDefinitionObject(field, collectionIdMap));
|
|
2051
2151
|
return `[
|
|
2052
2152
|
${fieldObjects.join(",\n")},
|
|
2053
2153
|
]`;
|
|
@@ -2106,7 +2206,7 @@ function generateIndexesArray(indexes) {
|
|
|
2106
2206
|
if (!indexes || indexes.length === 0) {
|
|
2107
2207
|
return "[]";
|
|
2108
2208
|
}
|
|
2109
|
-
const indexStrings = indexes.map((idx) =>
|
|
2209
|
+
const indexStrings = indexes.map((idx) => JSON.stringify(idx));
|
|
2110
2210
|
return `[
|
|
2111
2211
|
${indexStrings.join(",\n ")},
|
|
2112
2212
|
]`;
|
|
@@ -2160,7 +2260,7 @@ function getSystemFields() {
|
|
|
2160
2260
|
}
|
|
2161
2261
|
];
|
|
2162
2262
|
}
|
|
2163
|
-
function generateCollectionCreation(collection, varName = "collection", isLast = false) {
|
|
2263
|
+
function generateCollectionCreation(collection, varName = "collection", isLast = false, collectionIdMap) {
|
|
2164
2264
|
const lines = [];
|
|
2165
2265
|
lines.push(` const ${varName} = new Collection({`);
|
|
2166
2266
|
lines.push(` name: "${collection.name}",`);
|
|
@@ -2174,7 +2274,7 @@ function generateCollectionCreation(collection, varName = "collection", isLast =
|
|
|
2174
2274
|
}
|
|
2175
2275
|
const systemFields = getSystemFields();
|
|
2176
2276
|
const allFields = [...systemFields, ...collection.fields];
|
|
2177
|
-
lines.push(` fields: ${generateFieldsArray(allFields)},`);
|
|
2277
|
+
lines.push(` fields: ${generateFieldsArray(allFields, collectionIdMap)},`);
|
|
2178
2278
|
lines.push(` indexes: ${generateIndexesArray(collection.indexes)},`);
|
|
2179
2279
|
lines.push(` });`);
|
|
2180
2280
|
lines.push(``);
|
|
@@ -2196,42 +2296,59 @@ function getFieldConstructorName(fieldType) {
|
|
|
2196
2296
|
};
|
|
2197
2297
|
return constructorMap[fieldType] || "TextField";
|
|
2198
2298
|
}
|
|
2199
|
-
function generateFieldConstructorOptions(field) {
|
|
2299
|
+
function generateFieldConstructorOptions(field, collectionIdMap) {
|
|
2200
2300
|
const parts = [];
|
|
2201
2301
|
parts.push(` name: "${field.name}"`);
|
|
2202
2302
|
parts.push(` required: ${field.required}`);
|
|
2203
2303
|
if (field.unique !== void 0) {
|
|
2204
2304
|
parts.push(` unique: ${field.unique}`);
|
|
2205
2305
|
}
|
|
2306
|
+
if (field.type === "select") {
|
|
2307
|
+
const maxSelect = field.options?.maxSelect ?? 1;
|
|
2308
|
+
parts.push(` maxSelect: ${maxSelect}`);
|
|
2309
|
+
const values = field.options?.values ?? [];
|
|
2310
|
+
parts.push(` values: ${formatValue(values)}`);
|
|
2311
|
+
}
|
|
2206
2312
|
if (field.options && Object.keys(field.options).length > 0) {
|
|
2207
2313
|
for (const [key, value] of Object.entries(field.options)) {
|
|
2208
|
-
|
|
2314
|
+
if (field.type === "select" && (key === "maxSelect" || key === "values")) {
|
|
2315
|
+
continue;
|
|
2316
|
+
}
|
|
2317
|
+
if (field.type === "number" && key === "noDecimal") {
|
|
2318
|
+
parts.push(` onlyInt: ${formatValue(value)}`);
|
|
2319
|
+
} else {
|
|
2320
|
+
parts.push(` ${key}: ${formatValue(value)}`);
|
|
2321
|
+
}
|
|
2209
2322
|
}
|
|
2210
2323
|
}
|
|
2211
2324
|
if (field.relation && field.type === "relation") {
|
|
2212
2325
|
const isUsersCollection = field.relation.collection.toLowerCase() === "users";
|
|
2213
|
-
|
|
2214
|
-
|
|
2215
|
-
|
|
2216
|
-
|
|
2217
|
-
|
|
2218
|
-
|
|
2219
|
-
|
|
2220
|
-
}
|
|
2221
|
-
if (field.relation.cascadeDelete !== void 0) {
|
|
2222
|
-
parts.push(` cascadeDelete: ${field.relation.cascadeDelete}`);
|
|
2326
|
+
let collectionIdValue;
|
|
2327
|
+
if (isUsersCollection) {
|
|
2328
|
+
collectionIdValue = '"_pb_users_auth_"';
|
|
2329
|
+
} else if (collectionIdMap && collectionIdMap.has(field.relation.collection)) {
|
|
2330
|
+
collectionIdValue = `"${collectionIdMap.get(field.relation.collection)}"`;
|
|
2331
|
+
} else {
|
|
2332
|
+
collectionIdValue = `app.findCollectionByNameOrId("${field.relation.collection}").id`;
|
|
2223
2333
|
}
|
|
2334
|
+
parts.push(` collectionId: ${collectionIdValue}`);
|
|
2335
|
+
const maxSelect = field.relation.maxSelect ?? 1;
|
|
2336
|
+
parts.push(` maxSelect: ${maxSelect}`);
|
|
2337
|
+
const minSelect = field.relation.minSelect ?? null;
|
|
2338
|
+
parts.push(` minSelect: ${minSelect}`);
|
|
2339
|
+
const cascadeDelete = field.relation.cascadeDelete ?? false;
|
|
2340
|
+
parts.push(` cascadeDelete: ${cascadeDelete}`);
|
|
2224
2341
|
}
|
|
2225
2342
|
return parts.join(",\n");
|
|
2226
2343
|
}
|
|
2227
|
-
function generateFieldAddition(collectionName, field, varName, isLast = false) {
|
|
2344
|
+
function generateFieldAddition(collectionName, field, varName, isLast = false, collectionIdMap) {
|
|
2228
2345
|
const lines = [];
|
|
2229
2346
|
const constructorName = getFieldConstructorName(field.type);
|
|
2230
2347
|
const collectionVar = varName || `collection_${collectionName}_${field.name}`;
|
|
2231
2348
|
lines.push(` const ${collectionVar} = app.findCollectionByNameOrId("${collectionName}");`);
|
|
2232
2349
|
lines.push(``);
|
|
2233
2350
|
lines.push(` ${collectionVar}.fields.add(new ${constructorName}({`);
|
|
2234
|
-
lines.push(generateFieldConstructorOptions(field));
|
|
2351
|
+
lines.push(generateFieldConstructorOptions(field, collectionIdMap));
|
|
2235
2352
|
lines.push(` }));`);
|
|
2236
2353
|
lines.push(``);
|
|
2237
2354
|
lines.push(isLast ? ` return app.save(${collectionVar});` : ` app.save(${collectionVar});`);
|
|
@@ -2281,7 +2398,7 @@ function generateIndexAddition(collectionName, index, varName, isLast = false) {
|
|
|
2281
2398
|
const lines = [];
|
|
2282
2399
|
const collectionVar = varName || `collection_${collectionName}_idx`;
|
|
2283
2400
|
lines.push(` const ${collectionVar} = app.findCollectionByNameOrId("${collectionName}");`);
|
|
2284
|
-
lines.push(` ${collectionVar}.indexes.push(
|
|
2401
|
+
lines.push(` ${collectionVar}.indexes.push(${JSON.stringify(index)});`);
|
|
2285
2402
|
lines.push(isLast ? ` return app.save(${collectionVar});` : ` app.save(${collectionVar});`);
|
|
2286
2403
|
return lines.join("\n");
|
|
2287
2404
|
}
|
|
@@ -2290,7 +2407,7 @@ function generateIndexRemoval(collectionName, index, varName, isLast = false) {
|
|
|
2290
2407
|
const collectionVar = varName || `collection_${collectionName}_idx`;
|
|
2291
2408
|
const indexVar = `${collectionVar}_indexToRemove`;
|
|
2292
2409
|
lines.push(` const ${collectionVar} = app.findCollectionByNameOrId("${collectionName}");`);
|
|
2293
|
-
lines.push(` const ${indexVar} = ${collectionVar}.indexes.findIndex(idx => idx ===
|
|
2410
|
+
lines.push(` const ${indexVar} = ${collectionVar}.indexes.findIndex(idx => idx === ${JSON.stringify(index)});`);
|
|
2294
2411
|
lines.push(` if (${indexVar} !== -1) {`);
|
|
2295
2412
|
lines.push(` ${collectionVar}.indexes.splice(${indexVar}, 1);`);
|
|
2296
2413
|
lines.push(` }`);
|
|
@@ -2319,243 +2436,194 @@ function generateCollectionDeletion(collectionName, varName = "collection", isLa
|
|
|
2319
2436
|
lines.push(isLast ? ` return app.delete(${varName});` : ` app.delete(${varName});`);
|
|
2320
2437
|
return lines.join("\n");
|
|
2321
2438
|
}
|
|
2322
|
-
function
|
|
2439
|
+
function generateOperationUpMigration(operation, collectionIdMap) {
|
|
2323
2440
|
const lines = [];
|
|
2324
|
-
|
|
2325
|
-
|
|
2326
|
-
|
|
2327
|
-
lines.push(
|
|
2328
|
-
|
|
2329
|
-
|
|
2330
|
-
|
|
2331
|
-
|
|
2332
|
-
|
|
2333
|
-
|
|
2334
|
-
|
|
2335
|
-
|
|
2336
|
-
|
|
2337
|
-
|
|
2338
|
-
|
|
2339
|
-
if (modification.fieldsToAdd.length > 0) {
|
|
2340
|
-
lines.push(` // Add fields to ${collectionName}`);
|
|
2341
|
-
for (const field of modification.fieldsToAdd) {
|
|
2342
|
-
const varName = `collection_${collectionName}_add_${field.name}`;
|
|
2343
|
-
lines.push(generateFieldAddition(collectionName, field, varName));
|
|
2344
|
-
lines.push(``);
|
|
2345
|
-
}
|
|
2346
|
-
}
|
|
2347
|
-
if (modification.fieldsToModify.length > 0) {
|
|
2348
|
-
lines.push(` // Modify fields in ${collectionName}`);
|
|
2349
|
-
for (const fieldMod of modification.fieldsToModify) {
|
|
2350
|
-
const varName = `collection_${collectionName}_modify_${fieldMod.fieldName}`;
|
|
2351
|
-
lines.push(generateFieldModification(collectionName, fieldMod, varName));
|
|
2352
|
-
lines.push(``);
|
|
2353
|
-
}
|
|
2354
|
-
}
|
|
2355
|
-
if (modification.fieldsToRemove.length > 0) {
|
|
2356
|
-
lines.push(` // Remove fields from ${collectionName}`);
|
|
2357
|
-
for (const field of modification.fieldsToRemove) {
|
|
2358
|
-
const varName = `collection_${collectionName}_remove_${field.name}`;
|
|
2359
|
-
lines.push(generateFieldDeletion(collectionName, field.name, varName));
|
|
2360
|
-
lines.push(``);
|
|
2361
|
-
}
|
|
2362
|
-
}
|
|
2363
|
-
if (modification.indexesToAdd.length > 0) {
|
|
2364
|
-
lines.push(` // Add indexes to ${collectionName}`);
|
|
2365
|
-
for (let i = 0; i < modification.indexesToAdd.length; i++) {
|
|
2366
|
-
const index = modification.indexesToAdd[i];
|
|
2367
|
-
const varName = `collection_${collectionName}_addidx_${i}`;
|
|
2368
|
-
lines.push(generateIndexAddition(collectionName, index, varName));
|
|
2369
|
-
lines.push(``);
|
|
2370
|
-
}
|
|
2371
|
-
}
|
|
2372
|
-
if (modification.indexesToRemove.length > 0) {
|
|
2373
|
-
lines.push(` // Remove indexes from ${collectionName}`);
|
|
2374
|
-
for (let i = 0; i < modification.indexesToRemove.length; i++) {
|
|
2375
|
-
const index = modification.indexesToRemove[i];
|
|
2376
|
-
const varName = `collection_${collectionName}_rmidx_${i}`;
|
|
2377
|
-
lines.push(generateIndexRemoval(collectionName, index, varName));
|
|
2378
|
-
lines.push(``);
|
|
2379
|
-
}
|
|
2380
|
-
}
|
|
2381
|
-
if (modification.permissionsToUpdate && modification.permissionsToUpdate.length > 0) {
|
|
2382
|
-
lines.push(` // Update permissions for ${collectionName}`);
|
|
2383
|
-
for (const permission of modification.permissionsToUpdate) {
|
|
2384
|
-
const varName = `collection_${collectionName}_perm_${permission.ruleType}`;
|
|
2385
|
-
lines.push(generatePermissionUpdate(collectionName, permission.ruleType, permission.newValue, varName));
|
|
2386
|
-
lines.push(``);
|
|
2387
|
-
}
|
|
2388
|
-
} else if (modification.rulesToUpdate.length > 0) {
|
|
2389
|
-
lines.push(` // Update rules for ${collectionName}`);
|
|
2390
|
-
for (const rule of modification.rulesToUpdate) {
|
|
2391
|
-
const varName = `collection_${collectionName}_rule_${rule.ruleType}`;
|
|
2392
|
-
lines.push(generateRuleUpdate(collectionName, rule.ruleType, rule.newValue, varName));
|
|
2393
|
-
lines.push(``);
|
|
2394
|
-
}
|
|
2395
|
-
}
|
|
2441
|
+
if (operation.type === "create") {
|
|
2442
|
+
const collection = operation.collection;
|
|
2443
|
+
const varName = `collection_${collection.name}`;
|
|
2444
|
+
lines.push(generateCollectionCreation(collection, varName, true, collectionIdMap));
|
|
2445
|
+
} else if (operation.type === "modify") {
|
|
2446
|
+
const modification = operation.modifications;
|
|
2447
|
+
const collectionName = typeof operation.collection === "string" ? operation.collection : operation.collection?.name ?? modification.collection;
|
|
2448
|
+
let operationCount = 0;
|
|
2449
|
+
const totalOperations = modification.fieldsToAdd.length + modification.fieldsToModify.length + modification.fieldsToRemove.length + modification.indexesToAdd.length + modification.indexesToRemove.length + modification.rulesToUpdate.length + modification.permissionsToUpdate.length;
|
|
2450
|
+
for (const field of modification.fieldsToAdd) {
|
|
2451
|
+
operationCount++;
|
|
2452
|
+
const varName = `collection_${collectionName}_add_${field.name}`;
|
|
2453
|
+
const isLast = operationCount === totalOperations;
|
|
2454
|
+
lines.push(generateFieldAddition(collectionName, field, varName, isLast, collectionIdMap));
|
|
2455
|
+
if (!isLast) lines.push("");
|
|
2396
2456
|
}
|
|
2397
|
-
|
|
2398
|
-
|
|
2399
|
-
|
|
2400
|
-
|
|
2401
|
-
|
|
2402
|
-
|
|
2403
|
-
lines.push(generateCollectionDeletion(collection.name, varName));
|
|
2404
|
-
lines.push(``);
|
|
2405
|
-
}
|
|
2406
|
-
}
|
|
2407
|
-
if (lines.length === 2) {
|
|
2408
|
-
lines.push(` // No changes detected`);
|
|
2409
|
-
lines.push(``);
|
|
2410
|
-
}
|
|
2411
|
-
let code = lines.join("\n");
|
|
2412
|
-
const savePattern = /^(\s*)app\.save\((\w+)\);$/gm;
|
|
2413
|
-
const deletePattern = /^(\s*)app\.delete\((\w+)\);$/gm;
|
|
2414
|
-
const saveMatches = [...code.matchAll(savePattern)];
|
|
2415
|
-
const deleteMatches = [...code.matchAll(deletePattern)];
|
|
2416
|
-
const allMatches = [
|
|
2417
|
-
...saveMatches.map((m) => ({ match: m, type: "save", index: m.index })),
|
|
2418
|
-
...deleteMatches.map((m) => ({ match: m, type: "delete", index: m.index }))
|
|
2419
|
-
].sort((a, b) => b.index - a.index);
|
|
2420
|
-
if (allMatches.length > 0) {
|
|
2421
|
-
const lastMatch = allMatches[0];
|
|
2422
|
-
if (lastMatch.type === "save") {
|
|
2423
|
-
code = code.substring(0, lastMatch.match.index) + lastMatch.match[1] + "return app.save(" + lastMatch.match[2] + ");" + code.substring(lastMatch.match.index + lastMatch.match[0].length);
|
|
2424
|
-
} else {
|
|
2425
|
-
code = code.substring(0, lastMatch.match.index) + lastMatch.match[1] + "return app.delete(" + lastMatch.match[2] + ");" + code.substring(lastMatch.match.index + lastMatch.match[0].length);
|
|
2457
|
+
for (const fieldMod of modification.fieldsToModify) {
|
|
2458
|
+
operationCount++;
|
|
2459
|
+
const varName = `collection_${collectionName}_modify_${fieldMod.fieldName}`;
|
|
2460
|
+
const isLast = operationCount === totalOperations;
|
|
2461
|
+
lines.push(generateFieldModification(collectionName, fieldMod, varName, isLast));
|
|
2462
|
+
if (!isLast) lines.push("");
|
|
2426
2463
|
}
|
|
2464
|
+
for (const field of modification.fieldsToRemove) {
|
|
2465
|
+
operationCount++;
|
|
2466
|
+
const varName = `collection_${collectionName}_remove_${field.name}`;
|
|
2467
|
+
const isLast = operationCount === totalOperations;
|
|
2468
|
+
lines.push(generateFieldDeletion(collectionName, field.name, varName, isLast));
|
|
2469
|
+
if (!isLast) lines.push("");
|
|
2470
|
+
}
|
|
2471
|
+
for (let i = 0; i < modification.indexesToAdd.length; i++) {
|
|
2472
|
+
operationCount++;
|
|
2473
|
+
const index = modification.indexesToAdd[i];
|
|
2474
|
+
const varName = `collection_${collectionName}_addidx_${i}`;
|
|
2475
|
+
const isLast = operationCount === totalOperations;
|
|
2476
|
+
lines.push(generateIndexAddition(collectionName, index, varName, isLast));
|
|
2477
|
+
if (!isLast) lines.push("");
|
|
2478
|
+
}
|
|
2479
|
+
for (let i = 0; i < modification.indexesToRemove.length; i++) {
|
|
2480
|
+
operationCount++;
|
|
2481
|
+
const index = modification.indexesToRemove[i];
|
|
2482
|
+
const varName = `collection_${collectionName}_rmidx_${i}`;
|
|
2483
|
+
const isLast = operationCount === totalOperations;
|
|
2484
|
+
lines.push(generateIndexRemoval(collectionName, index, varName, isLast));
|
|
2485
|
+
if (!isLast) lines.push("");
|
|
2486
|
+
}
|
|
2487
|
+
if (modification.permissionsToUpdate && modification.permissionsToUpdate.length > 0) {
|
|
2488
|
+
for (const permission of modification.permissionsToUpdate) {
|
|
2489
|
+
operationCount++;
|
|
2490
|
+
const varName = `collection_${collectionName}_perm_${permission.ruleType}`;
|
|
2491
|
+
const isLast = operationCount === totalOperations;
|
|
2492
|
+
lines.push(generatePermissionUpdate(collectionName, permission.ruleType, permission.newValue, varName, isLast));
|
|
2493
|
+
if (!isLast) lines.push("");
|
|
2494
|
+
}
|
|
2495
|
+
} else if (modification.rulesToUpdate.length > 0) {
|
|
2496
|
+
for (const rule of modification.rulesToUpdate) {
|
|
2497
|
+
operationCount++;
|
|
2498
|
+
const varName = `collection_${collectionName}_rule_${rule.ruleType}`;
|
|
2499
|
+
const isLast = operationCount === totalOperations;
|
|
2500
|
+
lines.push(generateRuleUpdate(collectionName, rule.ruleType, rule.newValue, varName, isLast));
|
|
2501
|
+
if (!isLast) lines.push("");
|
|
2502
|
+
}
|
|
2503
|
+
}
|
|
2504
|
+
} else if (operation.type === "delete") {
|
|
2505
|
+
const collectionName = typeof operation.collection === "string" ? operation.collection : operation.collection.name;
|
|
2506
|
+
const varName = `collection_${collectionName}`;
|
|
2507
|
+
lines.push(generateCollectionDeletion(collectionName, varName, true));
|
|
2427
2508
|
}
|
|
2428
|
-
return
|
|
2509
|
+
return lines.join("\n");
|
|
2429
2510
|
}
|
|
2430
|
-
function
|
|
2511
|
+
function generateOperationDownMigration(operation, collectionIdMap) {
|
|
2431
2512
|
const lines = [];
|
|
2432
|
-
|
|
2433
|
-
|
|
2434
|
-
|
|
2435
|
-
lines.push(
|
|
2436
|
-
|
|
2437
|
-
|
|
2438
|
-
|
|
2439
|
-
|
|
2440
|
-
|
|
2513
|
+
if (operation.type === "create") {
|
|
2514
|
+
const collection = operation.collection;
|
|
2515
|
+
const varName = `collection_${collection.name}`;
|
|
2516
|
+
lines.push(generateCollectionDeletion(collection.name, varName, true));
|
|
2517
|
+
} else if (operation.type === "modify") {
|
|
2518
|
+
const modification = operation.modifications;
|
|
2519
|
+
const collectionName = typeof operation.collection === "string" ? operation.collection : operation.collection?.name ?? modification.collection;
|
|
2520
|
+
let operationCount = 0;
|
|
2521
|
+
const totalOperations = modification.fieldsToAdd.length + modification.fieldsToModify.length + modification.fieldsToRemove.length + modification.indexesToAdd.length + modification.indexesToRemove.length + modification.rulesToUpdate.length + modification.permissionsToUpdate.length;
|
|
2522
|
+
if (modification.permissionsToUpdate && modification.permissionsToUpdate.length > 0) {
|
|
2523
|
+
for (const permission of modification.permissionsToUpdate) {
|
|
2524
|
+
operationCount++;
|
|
2525
|
+
const varName = `collection_${collectionName}_revert_perm_${permission.ruleType}`;
|
|
2526
|
+
const isLast = operationCount === totalOperations;
|
|
2527
|
+
lines.push(generatePermissionUpdate(collectionName, permission.ruleType, permission.oldValue, varName, isLast));
|
|
2528
|
+
if (!isLast) lines.push("");
|
|
2529
|
+
}
|
|
2530
|
+
} else if (modification.rulesToUpdate.length > 0) {
|
|
2531
|
+
for (const rule of modification.rulesToUpdate) {
|
|
2532
|
+
operationCount++;
|
|
2533
|
+
const varName = `collection_${collectionName}_revert_rule_${rule.ruleType}`;
|
|
2534
|
+
const isLast = operationCount === totalOperations;
|
|
2535
|
+
lines.push(generateRuleUpdate(collectionName, rule.ruleType, rule.oldValue, varName, isLast));
|
|
2536
|
+
if (!isLast) lines.push("");
|
|
2537
|
+
}
|
|
2538
|
+
}
|
|
2539
|
+
for (let i = 0; i < modification.indexesToRemove.length; i++) {
|
|
2540
|
+
operationCount++;
|
|
2541
|
+
const index = modification.indexesToRemove[i];
|
|
2542
|
+
const varName = `collection_${collectionName}_restore_idx_${i}`;
|
|
2543
|
+
const isLast = operationCount === totalOperations;
|
|
2544
|
+
lines.push(generateIndexAddition(collectionName, index, varName, isLast));
|
|
2545
|
+
if (!isLast) lines.push("");
|
|
2546
|
+
}
|
|
2547
|
+
for (let i = 0; i < modification.indexesToAdd.length; i++) {
|
|
2548
|
+
operationCount++;
|
|
2549
|
+
const index = modification.indexesToAdd[i];
|
|
2550
|
+
const varName = `collection_${collectionName}_revert_idx_${i}`;
|
|
2551
|
+
const isLast = operationCount === totalOperations;
|
|
2552
|
+
lines.push(generateIndexRemoval(collectionName, index, varName, isLast));
|
|
2553
|
+
if (!isLast) lines.push("");
|
|
2441
2554
|
}
|
|
2442
|
-
|
|
2443
|
-
|
|
2444
|
-
|
|
2445
|
-
|
|
2446
|
-
|
|
2447
|
-
if (
|
|
2448
|
-
lines.push(` // Revert permissions for ${collectionName}`);
|
|
2449
|
-
for (const permission of modification.permissionsToUpdate) {
|
|
2450
|
-
const varName = `collection_${collectionName}_revert_perm_${permission.ruleType}`;
|
|
2451
|
-
lines.push(generatePermissionUpdate(collectionName, permission.ruleType, permission.oldValue, varName));
|
|
2452
|
-
lines.push(``);
|
|
2453
|
-
}
|
|
2454
|
-
} else if (modification.rulesToUpdate.length > 0) {
|
|
2455
|
-
lines.push(` // Revert rules for ${collectionName}`);
|
|
2456
|
-
for (const rule of modification.rulesToUpdate) {
|
|
2457
|
-
const varName = `collection_${collectionName}_revert_rule_${rule.ruleType}`;
|
|
2458
|
-
lines.push(generateRuleUpdate(collectionName, rule.ruleType, rule.oldValue, varName));
|
|
2459
|
-
lines.push(``);
|
|
2460
|
-
}
|
|
2461
|
-
}
|
|
2462
|
-
if (modification.indexesToRemove.length > 0) {
|
|
2463
|
-
lines.push(` // Restore indexes to ${collectionName}`);
|
|
2464
|
-
for (let i = 0; i < modification.indexesToRemove.length; i++) {
|
|
2465
|
-
const index = modification.indexesToRemove[i];
|
|
2466
|
-
const varName = `collection_${collectionName}_restore_idx_${i}`;
|
|
2467
|
-
lines.push(generateIndexAddition(collectionName, index, varName));
|
|
2468
|
-
lines.push(``);
|
|
2469
|
-
}
|
|
2470
|
-
}
|
|
2471
|
-
if (modification.indexesToAdd.length > 0) {
|
|
2472
|
-
lines.push(` // Remove indexes from ${collectionName}`);
|
|
2473
|
-
for (let i = 0; i < modification.indexesToAdd.length; i++) {
|
|
2474
|
-
const index = modification.indexesToAdd[i];
|
|
2475
|
-
const varName = `collection_${collectionName}_revert_idx_${i}`;
|
|
2476
|
-
lines.push(generateIndexRemoval(collectionName, index, varName));
|
|
2477
|
-
lines.push(``);
|
|
2478
|
-
}
|
|
2479
|
-
}
|
|
2480
|
-
if (modification.fieldsToRemove.length > 0) {
|
|
2481
|
-
lines.push(` // Restore fields to ${collectionName}`);
|
|
2482
|
-
for (const field of modification.fieldsToRemove) {
|
|
2483
|
-
const varName = `collection_${collectionName}_restore_${field.name}`;
|
|
2484
|
-
lines.push(generateFieldAddition(collectionName, field, varName));
|
|
2485
|
-
lines.push(``);
|
|
2486
|
-
}
|
|
2487
|
-
}
|
|
2488
|
-
if (modification.fieldsToModify.length > 0) {
|
|
2489
|
-
lines.push(` // Revert field modifications in ${collectionName}`);
|
|
2490
|
-
for (const fieldMod of modification.fieldsToModify) {
|
|
2491
|
-
const reverseChanges = fieldMod.changes.map((change) => ({
|
|
2492
|
-
property: change.property,
|
|
2493
|
-
oldValue: change.newValue,
|
|
2494
|
-
newValue: change.oldValue
|
|
2495
|
-
}));
|
|
2496
|
-
const reverseMod = {
|
|
2497
|
-
fieldName: fieldMod.fieldName,
|
|
2498
|
-
currentDefinition: fieldMod.newDefinition,
|
|
2499
|
-
newDefinition: fieldMod.currentDefinition,
|
|
2500
|
-
changes: reverseChanges
|
|
2501
|
-
};
|
|
2502
|
-
const varName = `collection_${collectionName}_revert_${fieldMod.fieldName}`;
|
|
2503
|
-
lines.push(generateFieldModification(collectionName, reverseMod, varName));
|
|
2504
|
-
lines.push(``);
|
|
2505
|
-
}
|
|
2506
|
-
}
|
|
2507
|
-
if (modification.fieldsToAdd.length > 0) {
|
|
2508
|
-
lines.push(` // Remove added fields from ${collectionName}`);
|
|
2509
|
-
for (const field of modification.fieldsToAdd) {
|
|
2510
|
-
const varName = `collection_${collectionName}_revert_add_${field.name}`;
|
|
2511
|
-
lines.push(generateFieldDeletion(collectionName, field.name, varName));
|
|
2512
|
-
lines.push(``);
|
|
2513
|
-
}
|
|
2514
|
-
}
|
|
2555
|
+
for (const field of modification.fieldsToRemove) {
|
|
2556
|
+
operationCount++;
|
|
2557
|
+
const varName = `collection_${collectionName}_restore_${field.name}`;
|
|
2558
|
+
const isLast = operationCount === totalOperations;
|
|
2559
|
+
lines.push(generateFieldAddition(collectionName, field, varName, isLast, collectionIdMap));
|
|
2560
|
+
if (!isLast) lines.push("");
|
|
2515
2561
|
}
|
|
2516
|
-
|
|
2517
|
-
|
|
2518
|
-
|
|
2519
|
-
|
|
2520
|
-
|
|
2521
|
-
|
|
2522
|
-
|
|
2523
|
-
|
|
2524
|
-
|
|
2525
|
-
|
|
2526
|
-
|
|
2527
|
-
|
|
2528
|
-
|
|
2529
|
-
|
|
2530
|
-
|
|
2531
|
-
|
|
2532
|
-
|
|
2533
|
-
|
|
2534
|
-
|
|
2535
|
-
|
|
2536
|
-
|
|
2537
|
-
|
|
2538
|
-
|
|
2539
|
-
|
|
2540
|
-
|
|
2541
|
-
|
|
2542
|
-
|
|
2543
|
-
|
|
2544
|
-
|
|
2562
|
+
for (const fieldMod of modification.fieldsToModify) {
|
|
2563
|
+
operationCount++;
|
|
2564
|
+
const reverseChanges = fieldMod.changes.map((change) => ({
|
|
2565
|
+
property: change.property,
|
|
2566
|
+
oldValue: change.newValue,
|
|
2567
|
+
newValue: change.oldValue
|
|
2568
|
+
}));
|
|
2569
|
+
const reverseMod = {
|
|
2570
|
+
fieldName: fieldMod.fieldName,
|
|
2571
|
+
currentDefinition: fieldMod.newDefinition,
|
|
2572
|
+
newDefinition: fieldMod.currentDefinition,
|
|
2573
|
+
changes: reverseChanges
|
|
2574
|
+
};
|
|
2575
|
+
const varName = `collection_${collectionName}_revert_${fieldMod.fieldName}`;
|
|
2576
|
+
const isLast = operationCount === totalOperations;
|
|
2577
|
+
lines.push(generateFieldModification(collectionName, reverseMod, varName, isLast));
|
|
2578
|
+
if (!isLast) lines.push("");
|
|
2579
|
+
}
|
|
2580
|
+
for (const field of modification.fieldsToAdd) {
|
|
2581
|
+
operationCount++;
|
|
2582
|
+
const varName = `collection_${collectionName}_revert_add_${field.name}`;
|
|
2583
|
+
const isLast = operationCount === totalOperations;
|
|
2584
|
+
lines.push(generateFieldDeletion(collectionName, field.name, varName, isLast));
|
|
2585
|
+
if (!isLast) lines.push("");
|
|
2586
|
+
}
|
|
2587
|
+
} else if (operation.type === "delete") {
|
|
2588
|
+
const collection = operation.collection;
|
|
2589
|
+
if (typeof collection !== "string") {
|
|
2590
|
+
const varName = `collection_${collection.name}`;
|
|
2591
|
+
lines.push(generateCollectionCreation(collection, varName, true, collectionIdMap));
|
|
2545
2592
|
}
|
|
2546
2593
|
}
|
|
2547
|
-
return
|
|
2594
|
+
return lines.join("\n");
|
|
2548
2595
|
}
|
|
2549
2596
|
function generate(diff, config) {
|
|
2550
2597
|
const normalizedConfig = typeof config === "string" ? { migrationDir: config } : config;
|
|
2551
2598
|
try {
|
|
2552
2599
|
const migrationDir = resolveMigrationDir(normalizedConfig);
|
|
2553
|
-
const
|
|
2554
|
-
|
|
2555
|
-
|
|
2556
|
-
|
|
2557
|
-
const
|
|
2558
|
-
|
|
2600
|
+
const hasChanges4 = diff.collectionsToCreate.length > 0 || diff.collectionsToModify.length > 0 || diff.collectionsToDelete.length > 0;
|
|
2601
|
+
if (!hasChanges4) {
|
|
2602
|
+
return [];
|
|
2603
|
+
}
|
|
2604
|
+
const collectionIdMap = /* @__PURE__ */ new Map();
|
|
2605
|
+
for (const collection of diff.collectionsToCreate) {
|
|
2606
|
+
if (collection.id) {
|
|
2607
|
+
collectionIdMap.set(collection.name, collection.id);
|
|
2608
|
+
}
|
|
2609
|
+
}
|
|
2610
|
+
for (const collection of diff.collectionsToDelete) {
|
|
2611
|
+
if (collection.id) {
|
|
2612
|
+
collectionIdMap.set(collection.name, collection.id);
|
|
2613
|
+
}
|
|
2614
|
+
}
|
|
2615
|
+
const baseTimestamp = generateTimestamp(normalizedConfig);
|
|
2616
|
+
const operations = splitDiffByCollection(diff, baseTimestamp);
|
|
2617
|
+
const filePaths = [];
|
|
2618
|
+
for (const operation of operations) {
|
|
2619
|
+
const upCode = generateOperationUpMigration(operation, collectionIdMap);
|
|
2620
|
+
const downCode = generateOperationDownMigration(operation, collectionIdMap);
|
|
2621
|
+
const content = createMigrationFileStructure(upCode, downCode, normalizedConfig);
|
|
2622
|
+
const filename = generateCollectionMigrationFilename(operation);
|
|
2623
|
+
const filePath = writeMigrationFile(migrationDir, filename, content);
|
|
2624
|
+
filePaths.push(filePath);
|
|
2625
|
+
}
|
|
2626
|
+
return filePaths;
|
|
2559
2627
|
} catch (error) {
|
|
2560
2628
|
if (error instanceof MigrationGenerationError || error instanceof FileSystemError) {
|
|
2561
2629
|
throw error;
|
|
@@ -3576,15 +3644,25 @@ async function executeGenerate(options) {
|
|
|
3576
3644
|
process.exit(1);
|
|
3577
3645
|
}
|
|
3578
3646
|
logSection("\u{1F4DD} Generating Migration");
|
|
3579
|
-
const
|
|
3647
|
+
const migrationPaths = await withProgress(
|
|
3580
3648
|
"Creating migration file...",
|
|
3581
3649
|
() => Promise.resolve(generate(diff, migrationsDir))
|
|
3582
3650
|
);
|
|
3583
|
-
|
|
3651
|
+
if (migrationPaths.length === 0) {
|
|
3652
|
+
logWarning("No migration files were generated (no changes detected).");
|
|
3653
|
+
return;
|
|
3654
|
+
}
|
|
3655
|
+
if (migrationPaths.length === 1) {
|
|
3656
|
+
logSuccess(`Migration file created: ${path5.basename(migrationPaths[0])}`);
|
|
3657
|
+
} else {
|
|
3658
|
+
logSuccess(`Created ${migrationPaths.length} migration files`);
|
|
3659
|
+
}
|
|
3584
3660
|
logSection("\u2705 Next Steps");
|
|
3585
3661
|
console.log();
|
|
3586
|
-
console.log(" 1. Review the generated migration file:");
|
|
3587
|
-
|
|
3662
|
+
console.log(" 1. Review the generated migration file(s):");
|
|
3663
|
+
migrationPaths.forEach((migrationPath) => {
|
|
3664
|
+
console.log(` ${migrationPath}`);
|
|
3665
|
+
});
|
|
3588
3666
|
console.log();
|
|
3589
3667
|
console.log(" 2. Apply the migration by running PocketBase:");
|
|
3590
3668
|
console.log(" yarn pb");
|