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/index.cjs
CHANGED
|
@@ -3,6 +3,7 @@
|
|
|
3
3
|
var path5 = require('path');
|
|
4
4
|
var fs5 = require('fs');
|
|
5
5
|
var zod = require('zod');
|
|
6
|
+
var crypto = require('crypto');
|
|
6
7
|
var chalk = require('chalk');
|
|
7
8
|
var ora = require('ora');
|
|
8
9
|
|
|
@@ -1315,12 +1316,22 @@ function isAuthCollection(fields) {
|
|
|
1315
1316
|
function buildFieldDefinition(fieldName, zodType) {
|
|
1316
1317
|
const fieldMetadata = extractFieldMetadata(zodType.description);
|
|
1317
1318
|
if (fieldMetadata) {
|
|
1318
|
-
|
|
1319
|
+
let required2;
|
|
1320
|
+
if (fieldMetadata.type === "number") {
|
|
1321
|
+
if (fieldMetadata.options?.required !== void 0) {
|
|
1322
|
+
required2 = fieldMetadata.options.required;
|
|
1323
|
+
} else {
|
|
1324
|
+
required2 = false;
|
|
1325
|
+
}
|
|
1326
|
+
} else {
|
|
1327
|
+
required2 = isFieldRequired(zodType);
|
|
1328
|
+
}
|
|
1329
|
+
const { required: _required, ...options2 } = fieldMetadata.options || {};
|
|
1319
1330
|
const fieldDef2 = {
|
|
1320
1331
|
name: fieldName,
|
|
1321
1332
|
type: fieldMetadata.type,
|
|
1322
1333
|
required: required2,
|
|
1323
|
-
options:
|
|
1334
|
+
options: Object.keys(options2).length > 0 ? options2 : void 0
|
|
1324
1335
|
};
|
|
1325
1336
|
if (fieldMetadata.type === "relation") {
|
|
1326
1337
|
const relationMetadata2 = extractRelationMetadata(zodType.description);
|
|
@@ -1490,6 +1501,65 @@ async function buildSchemaDefinition(config) {
|
|
|
1490
1501
|
async function parseSchemaFiles(config) {
|
|
1491
1502
|
return buildSchemaDefinition(config);
|
|
1492
1503
|
}
|
|
1504
|
+
function generateCollectionId() {
|
|
1505
|
+
const chars = "abcdefghijklmnopqrstuvwxyz0123456789";
|
|
1506
|
+
const idLength = 15;
|
|
1507
|
+
const bytes = crypto.randomBytes(idLength);
|
|
1508
|
+
let id = "pb_";
|
|
1509
|
+
for (let i = 0; i < idLength; i++) {
|
|
1510
|
+
const index = bytes[i] % chars.length;
|
|
1511
|
+
id += chars[index];
|
|
1512
|
+
}
|
|
1513
|
+
return id;
|
|
1514
|
+
}
|
|
1515
|
+
var CollectionIdRegistry = class {
|
|
1516
|
+
ids;
|
|
1517
|
+
constructor() {
|
|
1518
|
+
this.ids = /* @__PURE__ */ new Set();
|
|
1519
|
+
}
|
|
1520
|
+
/**
|
|
1521
|
+
* Generates a unique collection ID for a given collection name
|
|
1522
|
+
* Special case: Returns constant "_pb_users_auth_" for users collection
|
|
1523
|
+
* Retries up to 10 times if collision occurs (extremely rare)
|
|
1524
|
+
*
|
|
1525
|
+
* @param collectionName - The name of the collection
|
|
1526
|
+
* @returns A unique collection ID
|
|
1527
|
+
* @throws Error if unable to generate unique ID after max attempts
|
|
1528
|
+
*/
|
|
1529
|
+
generate(collectionName) {
|
|
1530
|
+
if (collectionName && collectionName.toLowerCase() === "users") {
|
|
1531
|
+
const usersId = "_pb_users_auth_";
|
|
1532
|
+
this.register(usersId);
|
|
1533
|
+
return usersId;
|
|
1534
|
+
}
|
|
1535
|
+
const maxAttempts = 10;
|
|
1536
|
+
for (let attempt = 0; attempt < maxAttempts; attempt++) {
|
|
1537
|
+
const id = generateCollectionId();
|
|
1538
|
+
if (!this.has(id)) {
|
|
1539
|
+
this.register(id);
|
|
1540
|
+
return id;
|
|
1541
|
+
}
|
|
1542
|
+
}
|
|
1543
|
+
throw new Error("Failed to generate unique collection ID after maximum attempts");
|
|
1544
|
+
}
|
|
1545
|
+
/**
|
|
1546
|
+
* Checks if an ID has already been registered
|
|
1547
|
+
*
|
|
1548
|
+
* @param id - The collection ID to check
|
|
1549
|
+
* @returns True if the ID exists in the registry
|
|
1550
|
+
*/
|
|
1551
|
+
has(id) {
|
|
1552
|
+
return this.ids.has(id);
|
|
1553
|
+
}
|
|
1554
|
+
/**
|
|
1555
|
+
* Registers a collection ID in the registry
|
|
1556
|
+
*
|
|
1557
|
+
* @param id - The collection ID to register
|
|
1558
|
+
*/
|
|
1559
|
+
register(id) {
|
|
1560
|
+
this.ids.add(id);
|
|
1561
|
+
}
|
|
1562
|
+
};
|
|
1493
1563
|
|
|
1494
1564
|
// src/migration/diff.ts
|
|
1495
1565
|
var DEFAULT_CONFIG2 = {
|
|
@@ -1821,6 +1891,18 @@ function aggregateChanges(currentSchema, previousSnapshot, config) {
|
|
|
1821
1891
|
const filteredCollectionsToDelete = collectionsToDelete.filter(
|
|
1822
1892
|
(collection) => !isSystemCollection(collection.name, config)
|
|
1823
1893
|
);
|
|
1894
|
+
const registry = new CollectionIdRegistry();
|
|
1895
|
+
const collectionsWithIds = filteredCollectionsToCreate.map((collection) => {
|
|
1896
|
+
if (collection.id) {
|
|
1897
|
+
registry.register(collection.id);
|
|
1898
|
+
return collection;
|
|
1899
|
+
}
|
|
1900
|
+
const id = registry.generate(collection.name);
|
|
1901
|
+
return {
|
|
1902
|
+
...collection,
|
|
1903
|
+
id
|
|
1904
|
+
};
|
|
1905
|
+
});
|
|
1824
1906
|
const collectionsToModify = [];
|
|
1825
1907
|
const matchedCollections = matchCollectionsByName(currentSchema, previousSnapshot);
|
|
1826
1908
|
for (const [currentCollection, previousCollection] of matchedCollections) {
|
|
@@ -1830,7 +1912,7 @@ function aggregateChanges(currentSchema, previousSnapshot, config) {
|
|
|
1830
1912
|
}
|
|
1831
1913
|
}
|
|
1832
1914
|
return {
|
|
1833
|
-
collectionsToCreate:
|
|
1915
|
+
collectionsToCreate: collectionsWithIds,
|
|
1834
1916
|
collectionsToDelete: filteredCollectionsToDelete,
|
|
1835
1917
|
collectionsToModify
|
|
1836
1918
|
};
|
|
@@ -1913,42 +1995,48 @@ function generateTimestamp(config) {
|
|
|
1913
1995
|
}
|
|
1914
1996
|
return Math.floor(Date.now() / 1e3).toString();
|
|
1915
1997
|
}
|
|
1916
|
-
function
|
|
1917
|
-
const
|
|
1918
|
-
|
|
1919
|
-
|
|
1920
|
-
|
|
1921
|
-
|
|
1922
|
-
|
|
1923
|
-
|
|
1924
|
-
|
|
1925
|
-
|
|
1926
|
-
if (diff.collectionsToDelete.length === 1) {
|
|
1927
|
-
parts.push(`deleted_${diff.collectionsToDelete[0].name}`);
|
|
1928
|
-
} else {
|
|
1929
|
-
parts.push(`deleted_${diff.collectionsToDelete.length}_collections`);
|
|
1930
|
-
}
|
|
1931
|
-
}
|
|
1932
|
-
if (diff.collectionsToModify.length > 0) {
|
|
1933
|
-
if (diff.collectionsToModify.length === 1) {
|
|
1934
|
-
parts.push(`updated_${diff.collectionsToModify[0].collection}`);
|
|
1935
|
-
} else {
|
|
1936
|
-
parts.push(`updated_${diff.collectionsToModify.length}_collections`);
|
|
1937
|
-
}
|
|
1998
|
+
function splitDiffByCollection(diff, baseTimestamp) {
|
|
1999
|
+
const operations = [];
|
|
2000
|
+
let currentTimestamp = parseInt(baseTimestamp, 10);
|
|
2001
|
+
for (const collection of diff.collectionsToCreate) {
|
|
2002
|
+
operations.push({
|
|
2003
|
+
type: "create",
|
|
2004
|
+
collection,
|
|
2005
|
+
timestamp: currentTimestamp.toString()
|
|
2006
|
+
});
|
|
2007
|
+
currentTimestamp += 1;
|
|
1938
2008
|
}
|
|
1939
|
-
|
|
1940
|
-
|
|
2009
|
+
for (const modification of diff.collectionsToModify) {
|
|
2010
|
+
operations.push({
|
|
2011
|
+
type: "modify",
|
|
2012
|
+
collection: modification.collection,
|
|
2013
|
+
modifications: modification,
|
|
2014
|
+
timestamp: currentTimestamp.toString()
|
|
2015
|
+
});
|
|
2016
|
+
currentTimestamp += 1;
|
|
1941
2017
|
}
|
|
1942
|
-
|
|
1943
|
-
|
|
1944
|
-
|
|
2018
|
+
for (const collection of diff.collectionsToDelete) {
|
|
2019
|
+
operations.push({
|
|
2020
|
+
type: "delete",
|
|
2021
|
+
collection: collection.name || collection,
|
|
2022
|
+
// Handle both object and string
|
|
2023
|
+
timestamp: currentTimestamp.toString()
|
|
2024
|
+
});
|
|
2025
|
+
currentTimestamp += 1;
|
|
1945
2026
|
}
|
|
1946
|
-
return
|
|
2027
|
+
return operations;
|
|
1947
2028
|
}
|
|
1948
|
-
function
|
|
1949
|
-
const timestamp =
|
|
1950
|
-
const
|
|
1951
|
-
|
|
2029
|
+
function generateCollectionMigrationFilename(operation) {
|
|
2030
|
+
const timestamp = operation.timestamp;
|
|
2031
|
+
const operationType = operation.type === "modify" ? "updated" : operation.type === "create" ? "created" : "deleted";
|
|
2032
|
+
let collectionName;
|
|
2033
|
+
if (typeof operation.collection === "string") {
|
|
2034
|
+
collectionName = operation.collection;
|
|
2035
|
+
} else {
|
|
2036
|
+
collectionName = operation.collection.name;
|
|
2037
|
+
}
|
|
2038
|
+
const sanitizedName = collectionName.replace(/[^a-zA-Z0-9_]/g, "_").toLowerCase();
|
|
2039
|
+
return `${timestamp}_${operationType}_${sanitizedName}.js`;
|
|
1952
2040
|
}
|
|
1953
2041
|
function createMigrationFileStructure(upCode, downCode, config) {
|
|
1954
2042
|
const mergedConfig = config ? mergeConfig3(config) : DEFAULT_CONFIG3;
|
|
@@ -2020,14 +2108,13 @@ function formatValue(value) {
|
|
|
2020
2108
|
return "null";
|
|
2021
2109
|
}
|
|
2022
2110
|
if (typeof value === "string") {
|
|
2023
|
-
return
|
|
2111
|
+
return JSON.stringify(value);
|
|
2024
2112
|
}
|
|
2025
2113
|
if (typeof value === "number" || typeof value === "boolean") {
|
|
2026
2114
|
return String(value);
|
|
2027
2115
|
}
|
|
2028
2116
|
if (Array.isArray(value)) {
|
|
2029
|
-
|
|
2030
|
-
return `[${items}]`;
|
|
2117
|
+
return JSON.stringify(value).replace(/","/g, '", "');
|
|
2031
2118
|
}
|
|
2032
2119
|
if (typeof value === "object") {
|
|
2033
2120
|
const entries = Object.entries(value).map(([k, v]) => `${k}: ${formatValue(v)}`).join(", ");
|
|
@@ -2035,7 +2122,7 @@ function formatValue(value) {
|
|
|
2035
2122
|
}
|
|
2036
2123
|
return String(value);
|
|
2037
2124
|
}
|
|
2038
|
-
function generateFieldDefinitionObject(field) {
|
|
2125
|
+
function generateFieldDefinitionObject(field, collectionIdMap) {
|
|
2039
2126
|
const parts = [];
|
|
2040
2127
|
parts.push(` name: "${field.name}"`);
|
|
2041
2128
|
parts.push(` type: "${field.type}"`);
|
|
@@ -2043,34 +2130,47 @@ function generateFieldDefinitionObject(field) {
|
|
|
2043
2130
|
if (field.unique !== void 0) {
|
|
2044
2131
|
parts.push(` unique: ${field.unique}`);
|
|
2045
2132
|
}
|
|
2133
|
+
if (field.type === "select") {
|
|
2134
|
+
const maxSelect = field.options?.maxSelect ?? 1;
|
|
2135
|
+
parts.push(` maxSelect: ${maxSelect}`);
|
|
2136
|
+
const values = field.options?.values ?? [];
|
|
2137
|
+
parts.push(` values: ${formatValue(values)}`);
|
|
2138
|
+
}
|
|
2046
2139
|
if (field.options && Object.keys(field.options).length > 0) {
|
|
2047
2140
|
for (const [key, value] of Object.entries(field.options)) {
|
|
2141
|
+
if (field.type === "select" && (key === "maxSelect" || key === "values")) {
|
|
2142
|
+
continue;
|
|
2143
|
+
}
|
|
2048
2144
|
parts.push(` ${key}: ${formatValue(value)}`);
|
|
2049
2145
|
}
|
|
2050
2146
|
}
|
|
2051
2147
|
if (field.relation) {
|
|
2052
2148
|
const isUsersCollection = field.relation.collection.toLowerCase() === "users";
|
|
2053
|
-
|
|
2054
|
-
|
|
2055
|
-
|
|
2056
|
-
|
|
2057
|
-
|
|
2058
|
-
|
|
2059
|
-
|
|
2060
|
-
}
|
|
2061
|
-
if (field.relation.cascadeDelete !== void 0) {
|
|
2062
|
-
parts.push(` cascadeDelete: ${field.relation.cascadeDelete}`);
|
|
2149
|
+
let collectionIdValue;
|
|
2150
|
+
if (isUsersCollection) {
|
|
2151
|
+
collectionIdValue = '"_pb_users_auth_"';
|
|
2152
|
+
} else if (collectionIdMap && collectionIdMap.has(field.relation.collection)) {
|
|
2153
|
+
collectionIdValue = `"${collectionIdMap.get(field.relation.collection)}"`;
|
|
2154
|
+
} else {
|
|
2155
|
+
collectionIdValue = `app.findCollectionByNameOrId("${field.relation.collection}").id`;
|
|
2063
2156
|
}
|
|
2157
|
+
parts.push(` collectionId: ${collectionIdValue}`);
|
|
2158
|
+
const maxSelect = field.relation.maxSelect ?? 1;
|
|
2159
|
+
parts.push(` maxSelect: ${maxSelect}`);
|
|
2160
|
+
const minSelect = field.relation.minSelect ?? null;
|
|
2161
|
+
parts.push(` minSelect: ${minSelect}`);
|
|
2162
|
+
const cascadeDelete = field.relation.cascadeDelete ?? false;
|
|
2163
|
+
parts.push(` cascadeDelete: ${cascadeDelete}`);
|
|
2064
2164
|
}
|
|
2065
2165
|
return ` {
|
|
2066
2166
|
${parts.join(",\n")},
|
|
2067
2167
|
}`;
|
|
2068
2168
|
}
|
|
2069
|
-
function generateFieldsArray(fields) {
|
|
2169
|
+
function generateFieldsArray(fields, collectionIdMap) {
|
|
2070
2170
|
if (fields.length === 0) {
|
|
2071
2171
|
return "[]";
|
|
2072
2172
|
}
|
|
2073
|
-
const fieldObjects = fields.map((field) => generateFieldDefinitionObject(field));
|
|
2173
|
+
const fieldObjects = fields.map((field) => generateFieldDefinitionObject(field, collectionIdMap));
|
|
2074
2174
|
return `[
|
|
2075
2175
|
${fieldObjects.join(",\n")},
|
|
2076
2176
|
]`;
|
|
@@ -2129,7 +2229,7 @@ function generateIndexesArray(indexes) {
|
|
|
2129
2229
|
if (!indexes || indexes.length === 0) {
|
|
2130
2230
|
return "[]";
|
|
2131
2231
|
}
|
|
2132
|
-
const indexStrings = indexes.map((idx) =>
|
|
2232
|
+
const indexStrings = indexes.map((idx) => JSON.stringify(idx));
|
|
2133
2233
|
return `[
|
|
2134
2234
|
${indexStrings.join(",\n ")},
|
|
2135
2235
|
]`;
|
|
@@ -2183,7 +2283,7 @@ function getSystemFields() {
|
|
|
2183
2283
|
}
|
|
2184
2284
|
];
|
|
2185
2285
|
}
|
|
2186
|
-
function generateCollectionCreation(collection, varName = "collection", isLast = false) {
|
|
2286
|
+
function generateCollectionCreation(collection, varName = "collection", isLast = false, collectionIdMap) {
|
|
2187
2287
|
const lines = [];
|
|
2188
2288
|
lines.push(` const ${varName} = new Collection({`);
|
|
2189
2289
|
lines.push(` name: "${collection.name}",`);
|
|
@@ -2197,7 +2297,7 @@ function generateCollectionCreation(collection, varName = "collection", isLast =
|
|
|
2197
2297
|
}
|
|
2198
2298
|
const systemFields = getSystemFields();
|
|
2199
2299
|
const allFields = [...systemFields, ...collection.fields];
|
|
2200
|
-
lines.push(` fields: ${generateFieldsArray(allFields)},`);
|
|
2300
|
+
lines.push(` fields: ${generateFieldsArray(allFields, collectionIdMap)},`);
|
|
2201
2301
|
lines.push(` indexes: ${generateIndexesArray(collection.indexes)},`);
|
|
2202
2302
|
lines.push(` });`);
|
|
2203
2303
|
lines.push(``);
|
|
@@ -2219,42 +2319,59 @@ function getFieldConstructorName(fieldType) {
|
|
|
2219
2319
|
};
|
|
2220
2320
|
return constructorMap[fieldType] || "TextField";
|
|
2221
2321
|
}
|
|
2222
|
-
function generateFieldConstructorOptions(field) {
|
|
2322
|
+
function generateFieldConstructorOptions(field, collectionIdMap) {
|
|
2223
2323
|
const parts = [];
|
|
2224
2324
|
parts.push(` name: "${field.name}"`);
|
|
2225
2325
|
parts.push(` required: ${field.required}`);
|
|
2226
2326
|
if (field.unique !== void 0) {
|
|
2227
2327
|
parts.push(` unique: ${field.unique}`);
|
|
2228
2328
|
}
|
|
2329
|
+
if (field.type === "select") {
|
|
2330
|
+
const maxSelect = field.options?.maxSelect ?? 1;
|
|
2331
|
+
parts.push(` maxSelect: ${maxSelect}`);
|
|
2332
|
+
const values = field.options?.values ?? [];
|
|
2333
|
+
parts.push(` values: ${formatValue(values)}`);
|
|
2334
|
+
}
|
|
2229
2335
|
if (field.options && Object.keys(field.options).length > 0) {
|
|
2230
2336
|
for (const [key, value] of Object.entries(field.options)) {
|
|
2231
|
-
|
|
2337
|
+
if (field.type === "select" && (key === "maxSelect" || key === "values")) {
|
|
2338
|
+
continue;
|
|
2339
|
+
}
|
|
2340
|
+
if (field.type === "number" && key === "noDecimal") {
|
|
2341
|
+
parts.push(` onlyInt: ${formatValue(value)}`);
|
|
2342
|
+
} else {
|
|
2343
|
+
parts.push(` ${key}: ${formatValue(value)}`);
|
|
2344
|
+
}
|
|
2232
2345
|
}
|
|
2233
2346
|
}
|
|
2234
2347
|
if (field.relation && field.type === "relation") {
|
|
2235
2348
|
const isUsersCollection = field.relation.collection.toLowerCase() === "users";
|
|
2236
|
-
|
|
2237
|
-
|
|
2238
|
-
|
|
2239
|
-
|
|
2240
|
-
|
|
2241
|
-
|
|
2242
|
-
|
|
2243
|
-
}
|
|
2244
|
-
if (field.relation.cascadeDelete !== void 0) {
|
|
2245
|
-
parts.push(` cascadeDelete: ${field.relation.cascadeDelete}`);
|
|
2349
|
+
let collectionIdValue;
|
|
2350
|
+
if (isUsersCollection) {
|
|
2351
|
+
collectionIdValue = '"_pb_users_auth_"';
|
|
2352
|
+
} else if (collectionIdMap && collectionIdMap.has(field.relation.collection)) {
|
|
2353
|
+
collectionIdValue = `"${collectionIdMap.get(field.relation.collection)}"`;
|
|
2354
|
+
} else {
|
|
2355
|
+
collectionIdValue = `app.findCollectionByNameOrId("${field.relation.collection}").id`;
|
|
2246
2356
|
}
|
|
2357
|
+
parts.push(` collectionId: ${collectionIdValue}`);
|
|
2358
|
+
const maxSelect = field.relation.maxSelect ?? 1;
|
|
2359
|
+
parts.push(` maxSelect: ${maxSelect}`);
|
|
2360
|
+
const minSelect = field.relation.minSelect ?? null;
|
|
2361
|
+
parts.push(` minSelect: ${minSelect}`);
|
|
2362
|
+
const cascadeDelete = field.relation.cascadeDelete ?? false;
|
|
2363
|
+
parts.push(` cascadeDelete: ${cascadeDelete}`);
|
|
2247
2364
|
}
|
|
2248
2365
|
return parts.join(",\n");
|
|
2249
2366
|
}
|
|
2250
|
-
function generateFieldAddition(collectionName, field, varName, isLast = false) {
|
|
2367
|
+
function generateFieldAddition(collectionName, field, varName, isLast = false, collectionIdMap) {
|
|
2251
2368
|
const lines = [];
|
|
2252
2369
|
const constructorName = getFieldConstructorName(field.type);
|
|
2253
2370
|
const collectionVar = varName || `collection_${collectionName}_${field.name}`;
|
|
2254
2371
|
lines.push(` const ${collectionVar} = app.findCollectionByNameOrId("${collectionName}");`);
|
|
2255
2372
|
lines.push(``);
|
|
2256
2373
|
lines.push(` ${collectionVar}.fields.add(new ${constructorName}({`);
|
|
2257
|
-
lines.push(generateFieldConstructorOptions(field));
|
|
2374
|
+
lines.push(generateFieldConstructorOptions(field, collectionIdMap));
|
|
2258
2375
|
lines.push(` }));`);
|
|
2259
2376
|
lines.push(``);
|
|
2260
2377
|
lines.push(isLast ? ` return app.save(${collectionVar});` : ` app.save(${collectionVar});`);
|
|
@@ -2304,7 +2421,7 @@ function generateIndexAddition(collectionName, index, varName, isLast = false) {
|
|
|
2304
2421
|
const lines = [];
|
|
2305
2422
|
const collectionVar = varName || `collection_${collectionName}_idx`;
|
|
2306
2423
|
lines.push(` const ${collectionVar} = app.findCollectionByNameOrId("${collectionName}");`);
|
|
2307
|
-
lines.push(` ${collectionVar}.indexes.push(
|
|
2424
|
+
lines.push(` ${collectionVar}.indexes.push(${JSON.stringify(index)});`);
|
|
2308
2425
|
lines.push(isLast ? ` return app.save(${collectionVar});` : ` app.save(${collectionVar});`);
|
|
2309
2426
|
return lines.join("\n");
|
|
2310
2427
|
}
|
|
@@ -2313,7 +2430,7 @@ function generateIndexRemoval(collectionName, index, varName, isLast = false) {
|
|
|
2313
2430
|
const collectionVar = varName || `collection_${collectionName}_idx`;
|
|
2314
2431
|
const indexVar = `${collectionVar}_indexToRemove`;
|
|
2315
2432
|
lines.push(` const ${collectionVar} = app.findCollectionByNameOrId("${collectionName}");`);
|
|
2316
|
-
lines.push(` const ${indexVar} = ${collectionVar}.indexes.findIndex(idx => idx ===
|
|
2433
|
+
lines.push(` const ${indexVar} = ${collectionVar}.indexes.findIndex(idx => idx === ${JSON.stringify(index)});`);
|
|
2317
2434
|
lines.push(` if (${indexVar} !== -1) {`);
|
|
2318
2435
|
lines.push(` ${collectionVar}.indexes.splice(${indexVar}, 1);`);
|
|
2319
2436
|
lines.push(` }`);
|
|
@@ -2342,243 +2459,194 @@ function generateCollectionDeletion(collectionName, varName = "collection", isLa
|
|
|
2342
2459
|
lines.push(isLast ? ` return app.delete(${varName});` : ` app.delete(${varName});`);
|
|
2343
2460
|
return lines.join("\n");
|
|
2344
2461
|
}
|
|
2345
|
-
function
|
|
2462
|
+
function generateOperationUpMigration(operation, collectionIdMap) {
|
|
2346
2463
|
const lines = [];
|
|
2347
|
-
|
|
2348
|
-
|
|
2349
|
-
|
|
2350
|
-
lines.push(
|
|
2351
|
-
|
|
2352
|
-
|
|
2353
|
-
|
|
2354
|
-
|
|
2355
|
-
|
|
2356
|
-
|
|
2357
|
-
|
|
2358
|
-
|
|
2359
|
-
|
|
2360
|
-
|
|
2361
|
-
|
|
2362
|
-
if (modification.fieldsToAdd.length > 0) {
|
|
2363
|
-
lines.push(` // Add fields to ${collectionName}`);
|
|
2364
|
-
for (const field of modification.fieldsToAdd) {
|
|
2365
|
-
const varName = `collection_${collectionName}_add_${field.name}`;
|
|
2366
|
-
lines.push(generateFieldAddition(collectionName, field, varName));
|
|
2367
|
-
lines.push(``);
|
|
2368
|
-
}
|
|
2369
|
-
}
|
|
2370
|
-
if (modification.fieldsToModify.length > 0) {
|
|
2371
|
-
lines.push(` // Modify fields in ${collectionName}`);
|
|
2372
|
-
for (const fieldMod of modification.fieldsToModify) {
|
|
2373
|
-
const varName = `collection_${collectionName}_modify_${fieldMod.fieldName}`;
|
|
2374
|
-
lines.push(generateFieldModification(collectionName, fieldMod, varName));
|
|
2375
|
-
lines.push(``);
|
|
2376
|
-
}
|
|
2377
|
-
}
|
|
2378
|
-
if (modification.fieldsToRemove.length > 0) {
|
|
2379
|
-
lines.push(` // Remove fields from ${collectionName}`);
|
|
2380
|
-
for (const field of modification.fieldsToRemove) {
|
|
2381
|
-
const varName = `collection_${collectionName}_remove_${field.name}`;
|
|
2382
|
-
lines.push(generateFieldDeletion(collectionName, field.name, varName));
|
|
2383
|
-
lines.push(``);
|
|
2384
|
-
}
|
|
2385
|
-
}
|
|
2386
|
-
if (modification.indexesToAdd.length > 0) {
|
|
2387
|
-
lines.push(` // Add indexes to ${collectionName}`);
|
|
2388
|
-
for (let i = 0; i < modification.indexesToAdd.length; i++) {
|
|
2389
|
-
const index = modification.indexesToAdd[i];
|
|
2390
|
-
const varName = `collection_${collectionName}_addidx_${i}`;
|
|
2391
|
-
lines.push(generateIndexAddition(collectionName, index, varName));
|
|
2392
|
-
lines.push(``);
|
|
2393
|
-
}
|
|
2394
|
-
}
|
|
2395
|
-
if (modification.indexesToRemove.length > 0) {
|
|
2396
|
-
lines.push(` // Remove indexes from ${collectionName}`);
|
|
2397
|
-
for (let i = 0; i < modification.indexesToRemove.length; i++) {
|
|
2398
|
-
const index = modification.indexesToRemove[i];
|
|
2399
|
-
const varName = `collection_${collectionName}_rmidx_${i}`;
|
|
2400
|
-
lines.push(generateIndexRemoval(collectionName, index, varName));
|
|
2401
|
-
lines.push(``);
|
|
2402
|
-
}
|
|
2403
|
-
}
|
|
2404
|
-
if (modification.permissionsToUpdate && modification.permissionsToUpdate.length > 0) {
|
|
2405
|
-
lines.push(` // Update permissions for ${collectionName}`);
|
|
2406
|
-
for (const permission of modification.permissionsToUpdate) {
|
|
2407
|
-
const varName = `collection_${collectionName}_perm_${permission.ruleType}`;
|
|
2408
|
-
lines.push(generatePermissionUpdate(collectionName, permission.ruleType, permission.newValue, varName));
|
|
2409
|
-
lines.push(``);
|
|
2410
|
-
}
|
|
2411
|
-
} else if (modification.rulesToUpdate.length > 0) {
|
|
2412
|
-
lines.push(` // Update rules for ${collectionName}`);
|
|
2413
|
-
for (const rule of modification.rulesToUpdate) {
|
|
2414
|
-
const varName = `collection_${collectionName}_rule_${rule.ruleType}`;
|
|
2415
|
-
lines.push(generateRuleUpdate(collectionName, rule.ruleType, rule.newValue, varName));
|
|
2416
|
-
lines.push(``);
|
|
2417
|
-
}
|
|
2418
|
-
}
|
|
2464
|
+
if (operation.type === "create") {
|
|
2465
|
+
const collection = operation.collection;
|
|
2466
|
+
const varName = `collection_${collection.name}`;
|
|
2467
|
+
lines.push(generateCollectionCreation(collection, varName, true, collectionIdMap));
|
|
2468
|
+
} else if (operation.type === "modify") {
|
|
2469
|
+
const modification = operation.modifications;
|
|
2470
|
+
const collectionName = typeof operation.collection === "string" ? operation.collection : operation.collection?.name ?? modification.collection;
|
|
2471
|
+
let operationCount = 0;
|
|
2472
|
+
const totalOperations = modification.fieldsToAdd.length + modification.fieldsToModify.length + modification.fieldsToRemove.length + modification.indexesToAdd.length + modification.indexesToRemove.length + modification.rulesToUpdate.length + modification.permissionsToUpdate.length;
|
|
2473
|
+
for (const field of modification.fieldsToAdd) {
|
|
2474
|
+
operationCount++;
|
|
2475
|
+
const varName = `collection_${collectionName}_add_${field.name}`;
|
|
2476
|
+
const isLast = operationCount === totalOperations;
|
|
2477
|
+
lines.push(generateFieldAddition(collectionName, field, varName, isLast, collectionIdMap));
|
|
2478
|
+
if (!isLast) lines.push("");
|
|
2419
2479
|
}
|
|
2420
|
-
|
|
2421
|
-
|
|
2422
|
-
|
|
2423
|
-
|
|
2424
|
-
|
|
2425
|
-
|
|
2426
|
-
lines.push(generateCollectionDeletion(collection.name, varName));
|
|
2427
|
-
lines.push(``);
|
|
2428
|
-
}
|
|
2429
|
-
}
|
|
2430
|
-
if (lines.length === 2) {
|
|
2431
|
-
lines.push(` // No changes detected`);
|
|
2432
|
-
lines.push(``);
|
|
2433
|
-
}
|
|
2434
|
-
let code = lines.join("\n");
|
|
2435
|
-
const savePattern = /^(\s*)app\.save\((\w+)\);$/gm;
|
|
2436
|
-
const deletePattern = /^(\s*)app\.delete\((\w+)\);$/gm;
|
|
2437
|
-
const saveMatches = [...code.matchAll(savePattern)];
|
|
2438
|
-
const deleteMatches = [...code.matchAll(deletePattern)];
|
|
2439
|
-
const allMatches = [
|
|
2440
|
-
...saveMatches.map((m) => ({ match: m, type: "save", index: m.index })),
|
|
2441
|
-
...deleteMatches.map((m) => ({ match: m, type: "delete", index: m.index }))
|
|
2442
|
-
].sort((a, b) => b.index - a.index);
|
|
2443
|
-
if (allMatches.length > 0) {
|
|
2444
|
-
const lastMatch = allMatches[0];
|
|
2445
|
-
if (lastMatch.type === "save") {
|
|
2446
|
-
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);
|
|
2447
|
-
} else {
|
|
2448
|
-
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);
|
|
2480
|
+
for (const fieldMod of modification.fieldsToModify) {
|
|
2481
|
+
operationCount++;
|
|
2482
|
+
const varName = `collection_${collectionName}_modify_${fieldMod.fieldName}`;
|
|
2483
|
+
const isLast = operationCount === totalOperations;
|
|
2484
|
+
lines.push(generateFieldModification(collectionName, fieldMod, varName, isLast));
|
|
2485
|
+
if (!isLast) lines.push("");
|
|
2449
2486
|
}
|
|
2487
|
+
for (const field of modification.fieldsToRemove) {
|
|
2488
|
+
operationCount++;
|
|
2489
|
+
const varName = `collection_${collectionName}_remove_${field.name}`;
|
|
2490
|
+
const isLast = operationCount === totalOperations;
|
|
2491
|
+
lines.push(generateFieldDeletion(collectionName, field.name, varName, isLast));
|
|
2492
|
+
if (!isLast) lines.push("");
|
|
2493
|
+
}
|
|
2494
|
+
for (let i = 0; i < modification.indexesToAdd.length; i++) {
|
|
2495
|
+
operationCount++;
|
|
2496
|
+
const index = modification.indexesToAdd[i];
|
|
2497
|
+
const varName = `collection_${collectionName}_addidx_${i}`;
|
|
2498
|
+
const isLast = operationCount === totalOperations;
|
|
2499
|
+
lines.push(generateIndexAddition(collectionName, index, varName, isLast));
|
|
2500
|
+
if (!isLast) lines.push("");
|
|
2501
|
+
}
|
|
2502
|
+
for (let i = 0; i < modification.indexesToRemove.length; i++) {
|
|
2503
|
+
operationCount++;
|
|
2504
|
+
const index = modification.indexesToRemove[i];
|
|
2505
|
+
const varName = `collection_${collectionName}_rmidx_${i}`;
|
|
2506
|
+
const isLast = operationCount === totalOperations;
|
|
2507
|
+
lines.push(generateIndexRemoval(collectionName, index, varName, isLast));
|
|
2508
|
+
if (!isLast) lines.push("");
|
|
2509
|
+
}
|
|
2510
|
+
if (modification.permissionsToUpdate && modification.permissionsToUpdate.length > 0) {
|
|
2511
|
+
for (const permission of modification.permissionsToUpdate) {
|
|
2512
|
+
operationCount++;
|
|
2513
|
+
const varName = `collection_${collectionName}_perm_${permission.ruleType}`;
|
|
2514
|
+
const isLast = operationCount === totalOperations;
|
|
2515
|
+
lines.push(generatePermissionUpdate(collectionName, permission.ruleType, permission.newValue, varName, isLast));
|
|
2516
|
+
if (!isLast) lines.push("");
|
|
2517
|
+
}
|
|
2518
|
+
} else if (modification.rulesToUpdate.length > 0) {
|
|
2519
|
+
for (const rule of modification.rulesToUpdate) {
|
|
2520
|
+
operationCount++;
|
|
2521
|
+
const varName = `collection_${collectionName}_rule_${rule.ruleType}`;
|
|
2522
|
+
const isLast = operationCount === totalOperations;
|
|
2523
|
+
lines.push(generateRuleUpdate(collectionName, rule.ruleType, rule.newValue, varName, isLast));
|
|
2524
|
+
if (!isLast) lines.push("");
|
|
2525
|
+
}
|
|
2526
|
+
}
|
|
2527
|
+
} else if (operation.type === "delete") {
|
|
2528
|
+
const collectionName = typeof operation.collection === "string" ? operation.collection : operation.collection.name;
|
|
2529
|
+
const varName = `collection_${collectionName}`;
|
|
2530
|
+
lines.push(generateCollectionDeletion(collectionName, varName, true));
|
|
2450
2531
|
}
|
|
2451
|
-
return
|
|
2532
|
+
return lines.join("\n");
|
|
2452
2533
|
}
|
|
2453
|
-
function
|
|
2534
|
+
function generateOperationDownMigration(operation, collectionIdMap) {
|
|
2454
2535
|
const lines = [];
|
|
2455
|
-
|
|
2456
|
-
|
|
2457
|
-
|
|
2458
|
-
lines.push(
|
|
2459
|
-
|
|
2460
|
-
|
|
2461
|
-
|
|
2462
|
-
|
|
2463
|
-
|
|
2536
|
+
if (operation.type === "create") {
|
|
2537
|
+
const collection = operation.collection;
|
|
2538
|
+
const varName = `collection_${collection.name}`;
|
|
2539
|
+
lines.push(generateCollectionDeletion(collection.name, varName, true));
|
|
2540
|
+
} else if (operation.type === "modify") {
|
|
2541
|
+
const modification = operation.modifications;
|
|
2542
|
+
const collectionName = typeof operation.collection === "string" ? operation.collection : operation.collection?.name ?? modification.collection;
|
|
2543
|
+
let operationCount = 0;
|
|
2544
|
+
const totalOperations = modification.fieldsToAdd.length + modification.fieldsToModify.length + modification.fieldsToRemove.length + modification.indexesToAdd.length + modification.indexesToRemove.length + modification.rulesToUpdate.length + modification.permissionsToUpdate.length;
|
|
2545
|
+
if (modification.permissionsToUpdate && modification.permissionsToUpdate.length > 0) {
|
|
2546
|
+
for (const permission of modification.permissionsToUpdate) {
|
|
2547
|
+
operationCount++;
|
|
2548
|
+
const varName = `collection_${collectionName}_revert_perm_${permission.ruleType}`;
|
|
2549
|
+
const isLast = operationCount === totalOperations;
|
|
2550
|
+
lines.push(generatePermissionUpdate(collectionName, permission.ruleType, permission.oldValue, varName, isLast));
|
|
2551
|
+
if (!isLast) lines.push("");
|
|
2552
|
+
}
|
|
2553
|
+
} else if (modification.rulesToUpdate.length > 0) {
|
|
2554
|
+
for (const rule of modification.rulesToUpdate) {
|
|
2555
|
+
operationCount++;
|
|
2556
|
+
const varName = `collection_${collectionName}_revert_rule_${rule.ruleType}`;
|
|
2557
|
+
const isLast = operationCount === totalOperations;
|
|
2558
|
+
lines.push(generateRuleUpdate(collectionName, rule.ruleType, rule.oldValue, varName, isLast));
|
|
2559
|
+
if (!isLast) lines.push("");
|
|
2560
|
+
}
|
|
2561
|
+
}
|
|
2562
|
+
for (let i = 0; i < modification.indexesToRemove.length; i++) {
|
|
2563
|
+
operationCount++;
|
|
2564
|
+
const index = modification.indexesToRemove[i];
|
|
2565
|
+
const varName = `collection_${collectionName}_restore_idx_${i}`;
|
|
2566
|
+
const isLast = operationCount === totalOperations;
|
|
2567
|
+
lines.push(generateIndexAddition(collectionName, index, varName, isLast));
|
|
2568
|
+
if (!isLast) lines.push("");
|
|
2569
|
+
}
|
|
2570
|
+
for (let i = 0; i < modification.indexesToAdd.length; i++) {
|
|
2571
|
+
operationCount++;
|
|
2572
|
+
const index = modification.indexesToAdd[i];
|
|
2573
|
+
const varName = `collection_${collectionName}_revert_idx_${i}`;
|
|
2574
|
+
const isLast = operationCount === totalOperations;
|
|
2575
|
+
lines.push(generateIndexRemoval(collectionName, index, varName, isLast));
|
|
2576
|
+
if (!isLast) lines.push("");
|
|
2464
2577
|
}
|
|
2465
|
-
|
|
2466
|
-
|
|
2467
|
-
|
|
2468
|
-
|
|
2469
|
-
|
|
2470
|
-
if (
|
|
2471
|
-
lines.push(` // Revert permissions for ${collectionName}`);
|
|
2472
|
-
for (const permission of modification.permissionsToUpdate) {
|
|
2473
|
-
const varName = `collection_${collectionName}_revert_perm_${permission.ruleType}`;
|
|
2474
|
-
lines.push(generatePermissionUpdate(collectionName, permission.ruleType, permission.oldValue, varName));
|
|
2475
|
-
lines.push(``);
|
|
2476
|
-
}
|
|
2477
|
-
} else if (modification.rulesToUpdate.length > 0) {
|
|
2478
|
-
lines.push(` // Revert rules for ${collectionName}`);
|
|
2479
|
-
for (const rule of modification.rulesToUpdate) {
|
|
2480
|
-
const varName = `collection_${collectionName}_revert_rule_${rule.ruleType}`;
|
|
2481
|
-
lines.push(generateRuleUpdate(collectionName, rule.ruleType, rule.oldValue, varName));
|
|
2482
|
-
lines.push(``);
|
|
2483
|
-
}
|
|
2484
|
-
}
|
|
2485
|
-
if (modification.indexesToRemove.length > 0) {
|
|
2486
|
-
lines.push(` // Restore indexes to ${collectionName}`);
|
|
2487
|
-
for (let i = 0; i < modification.indexesToRemove.length; i++) {
|
|
2488
|
-
const index = modification.indexesToRemove[i];
|
|
2489
|
-
const varName = `collection_${collectionName}_restore_idx_${i}`;
|
|
2490
|
-
lines.push(generateIndexAddition(collectionName, index, varName));
|
|
2491
|
-
lines.push(``);
|
|
2492
|
-
}
|
|
2493
|
-
}
|
|
2494
|
-
if (modification.indexesToAdd.length > 0) {
|
|
2495
|
-
lines.push(` // Remove indexes from ${collectionName}`);
|
|
2496
|
-
for (let i = 0; i < modification.indexesToAdd.length; i++) {
|
|
2497
|
-
const index = modification.indexesToAdd[i];
|
|
2498
|
-
const varName = `collection_${collectionName}_revert_idx_${i}`;
|
|
2499
|
-
lines.push(generateIndexRemoval(collectionName, index, varName));
|
|
2500
|
-
lines.push(``);
|
|
2501
|
-
}
|
|
2502
|
-
}
|
|
2503
|
-
if (modification.fieldsToRemove.length > 0) {
|
|
2504
|
-
lines.push(` // Restore fields to ${collectionName}`);
|
|
2505
|
-
for (const field of modification.fieldsToRemove) {
|
|
2506
|
-
const varName = `collection_${collectionName}_restore_${field.name}`;
|
|
2507
|
-
lines.push(generateFieldAddition(collectionName, field, varName));
|
|
2508
|
-
lines.push(``);
|
|
2509
|
-
}
|
|
2510
|
-
}
|
|
2511
|
-
if (modification.fieldsToModify.length > 0) {
|
|
2512
|
-
lines.push(` // Revert field modifications in ${collectionName}`);
|
|
2513
|
-
for (const fieldMod of modification.fieldsToModify) {
|
|
2514
|
-
const reverseChanges = fieldMod.changes.map((change) => ({
|
|
2515
|
-
property: change.property,
|
|
2516
|
-
oldValue: change.newValue,
|
|
2517
|
-
newValue: change.oldValue
|
|
2518
|
-
}));
|
|
2519
|
-
const reverseMod = {
|
|
2520
|
-
fieldName: fieldMod.fieldName,
|
|
2521
|
-
currentDefinition: fieldMod.newDefinition,
|
|
2522
|
-
newDefinition: fieldMod.currentDefinition,
|
|
2523
|
-
changes: reverseChanges
|
|
2524
|
-
};
|
|
2525
|
-
const varName = `collection_${collectionName}_revert_${fieldMod.fieldName}`;
|
|
2526
|
-
lines.push(generateFieldModification(collectionName, reverseMod, varName));
|
|
2527
|
-
lines.push(``);
|
|
2528
|
-
}
|
|
2529
|
-
}
|
|
2530
|
-
if (modification.fieldsToAdd.length > 0) {
|
|
2531
|
-
lines.push(` // Remove added fields from ${collectionName}`);
|
|
2532
|
-
for (const field of modification.fieldsToAdd) {
|
|
2533
|
-
const varName = `collection_${collectionName}_revert_add_${field.name}`;
|
|
2534
|
-
lines.push(generateFieldDeletion(collectionName, field.name, varName));
|
|
2535
|
-
lines.push(``);
|
|
2536
|
-
}
|
|
2537
|
-
}
|
|
2578
|
+
for (const field of modification.fieldsToRemove) {
|
|
2579
|
+
operationCount++;
|
|
2580
|
+
const varName = `collection_${collectionName}_restore_${field.name}`;
|
|
2581
|
+
const isLast = operationCount === totalOperations;
|
|
2582
|
+
lines.push(generateFieldAddition(collectionName, field, varName, isLast, collectionIdMap));
|
|
2583
|
+
if (!isLast) lines.push("");
|
|
2538
2584
|
}
|
|
2539
|
-
|
|
2540
|
-
|
|
2541
|
-
|
|
2542
|
-
|
|
2543
|
-
|
|
2544
|
-
|
|
2545
|
-
|
|
2546
|
-
|
|
2547
|
-
|
|
2548
|
-
|
|
2549
|
-
|
|
2550
|
-
|
|
2551
|
-
|
|
2552
|
-
|
|
2553
|
-
|
|
2554
|
-
|
|
2555
|
-
|
|
2556
|
-
|
|
2557
|
-
|
|
2558
|
-
|
|
2559
|
-
|
|
2560
|
-
|
|
2561
|
-
|
|
2562
|
-
|
|
2563
|
-
|
|
2564
|
-
|
|
2565
|
-
|
|
2566
|
-
|
|
2567
|
-
|
|
2585
|
+
for (const fieldMod of modification.fieldsToModify) {
|
|
2586
|
+
operationCount++;
|
|
2587
|
+
const reverseChanges = fieldMod.changes.map((change) => ({
|
|
2588
|
+
property: change.property,
|
|
2589
|
+
oldValue: change.newValue,
|
|
2590
|
+
newValue: change.oldValue
|
|
2591
|
+
}));
|
|
2592
|
+
const reverseMod = {
|
|
2593
|
+
fieldName: fieldMod.fieldName,
|
|
2594
|
+
currentDefinition: fieldMod.newDefinition,
|
|
2595
|
+
newDefinition: fieldMod.currentDefinition,
|
|
2596
|
+
changes: reverseChanges
|
|
2597
|
+
};
|
|
2598
|
+
const varName = `collection_${collectionName}_revert_${fieldMod.fieldName}`;
|
|
2599
|
+
const isLast = operationCount === totalOperations;
|
|
2600
|
+
lines.push(generateFieldModification(collectionName, reverseMod, varName, isLast));
|
|
2601
|
+
if (!isLast) lines.push("");
|
|
2602
|
+
}
|
|
2603
|
+
for (const field of modification.fieldsToAdd) {
|
|
2604
|
+
operationCount++;
|
|
2605
|
+
const varName = `collection_${collectionName}_revert_add_${field.name}`;
|
|
2606
|
+
const isLast = operationCount === totalOperations;
|
|
2607
|
+
lines.push(generateFieldDeletion(collectionName, field.name, varName, isLast));
|
|
2608
|
+
if (!isLast) lines.push("");
|
|
2609
|
+
}
|
|
2610
|
+
} else if (operation.type === "delete") {
|
|
2611
|
+
const collection = operation.collection;
|
|
2612
|
+
if (typeof collection !== "string") {
|
|
2613
|
+
const varName = `collection_${collection.name}`;
|
|
2614
|
+
lines.push(generateCollectionCreation(collection, varName, true, collectionIdMap));
|
|
2568
2615
|
}
|
|
2569
2616
|
}
|
|
2570
|
-
return
|
|
2617
|
+
return lines.join("\n");
|
|
2571
2618
|
}
|
|
2572
2619
|
function generate(diff, config) {
|
|
2573
2620
|
const normalizedConfig = typeof config === "string" ? { migrationDir: config } : config;
|
|
2574
2621
|
try {
|
|
2575
2622
|
const migrationDir = resolveMigrationDir(normalizedConfig);
|
|
2576
|
-
const
|
|
2577
|
-
|
|
2578
|
-
|
|
2579
|
-
|
|
2580
|
-
const
|
|
2581
|
-
|
|
2623
|
+
const hasChanges4 = diff.collectionsToCreate.length > 0 || diff.collectionsToModify.length > 0 || diff.collectionsToDelete.length > 0;
|
|
2624
|
+
if (!hasChanges4) {
|
|
2625
|
+
return [];
|
|
2626
|
+
}
|
|
2627
|
+
const collectionIdMap = /* @__PURE__ */ new Map();
|
|
2628
|
+
for (const collection of diff.collectionsToCreate) {
|
|
2629
|
+
if (collection.id) {
|
|
2630
|
+
collectionIdMap.set(collection.name, collection.id);
|
|
2631
|
+
}
|
|
2632
|
+
}
|
|
2633
|
+
for (const collection of diff.collectionsToDelete) {
|
|
2634
|
+
if (collection.id) {
|
|
2635
|
+
collectionIdMap.set(collection.name, collection.id);
|
|
2636
|
+
}
|
|
2637
|
+
}
|
|
2638
|
+
const baseTimestamp = generateTimestamp(normalizedConfig);
|
|
2639
|
+
const operations = splitDiffByCollection(diff, baseTimestamp);
|
|
2640
|
+
const filePaths = [];
|
|
2641
|
+
for (const operation of operations) {
|
|
2642
|
+
const upCode = generateOperationUpMigration(operation, collectionIdMap);
|
|
2643
|
+
const downCode = generateOperationDownMigration(operation, collectionIdMap);
|
|
2644
|
+
const content = createMigrationFileStructure(upCode, downCode, normalizedConfig);
|
|
2645
|
+
const filename = generateCollectionMigrationFilename(operation);
|
|
2646
|
+
const filePath = writeMigrationFile(migrationDir, filename, content);
|
|
2647
|
+
filePaths.push(filePath);
|
|
2648
|
+
}
|
|
2649
|
+
return filePaths;
|
|
2582
2650
|
} catch (error) {
|
|
2583
2651
|
if (error instanceof MigrationGenerationError || error instanceof FileSystemError) {
|
|
2584
2652
|
throw error;
|
|
@@ -3659,15 +3727,25 @@ async function executeGenerate(options) {
|
|
|
3659
3727
|
process.exit(1);
|
|
3660
3728
|
}
|
|
3661
3729
|
logSection("\u{1F4DD} Generating Migration");
|
|
3662
|
-
const
|
|
3730
|
+
const migrationPaths = await withProgress(
|
|
3663
3731
|
"Creating migration file...",
|
|
3664
3732
|
() => Promise.resolve(generate(diff, migrationsDir))
|
|
3665
3733
|
);
|
|
3666
|
-
|
|
3734
|
+
if (migrationPaths.length === 0) {
|
|
3735
|
+
logWarning("No migration files were generated (no changes detected).");
|
|
3736
|
+
return;
|
|
3737
|
+
}
|
|
3738
|
+
if (migrationPaths.length === 1) {
|
|
3739
|
+
logSuccess(`Migration file created: ${path5__namespace.basename(migrationPaths[0])}`);
|
|
3740
|
+
} else {
|
|
3741
|
+
logSuccess(`Created ${migrationPaths.length} migration files`);
|
|
3742
|
+
}
|
|
3667
3743
|
logSection("\u2705 Next Steps");
|
|
3668
3744
|
console.log();
|
|
3669
|
-
console.log(" 1. Review the generated migration file:");
|
|
3670
|
-
|
|
3745
|
+
console.log(" 1. Review the generated migration file(s):");
|
|
3746
|
+
migrationPaths.forEach((migrationPath) => {
|
|
3747
|
+
console.log(` ${migrationPath}`);
|
|
3748
|
+
});
|
|
3671
3749
|
console.log();
|
|
3672
3750
|
console.log(" 2. Apply the migration by running PocketBase:");
|
|
3673
3751
|
console.log(" yarn pb");
|