pocketbase-zod-schema 0.1.3 → 0.1.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (46) hide show
  1. package/CHANGELOG.md +7 -0
  2. package/dist/cli/index.cjs +406 -102
  3. package/dist/cli/index.cjs.map +1 -1
  4. package/dist/cli/index.js +404 -100
  5. package/dist/cli/index.js.map +1 -1
  6. package/dist/cli/migrate.cjs +409 -105
  7. package/dist/cli/migrate.cjs.map +1 -1
  8. package/dist/cli/migrate.js +404 -100
  9. package/dist/cli/migrate.js.map +1 -1
  10. package/dist/index.cjs +515 -159
  11. package/dist/index.cjs.map +1 -1
  12. package/dist/index.d.cts +3 -3
  13. package/dist/index.d.ts +3 -3
  14. package/dist/index.js +511 -158
  15. package/dist/index.js.map +1 -1
  16. package/dist/migration/diff.cjs +21 -3
  17. package/dist/migration/diff.cjs.map +1 -1
  18. package/dist/migration/diff.js +21 -3
  19. package/dist/migration/diff.js.map +1 -1
  20. package/dist/migration/index.cjs +457 -123
  21. package/dist/migration/index.cjs.map +1 -1
  22. package/dist/migration/index.d.cts +1 -1
  23. package/dist/migration/index.d.ts +1 -1
  24. package/dist/migration/index.js +456 -123
  25. package/dist/migration/index.js.map +1 -1
  26. package/dist/migration/snapshot.cjs +432 -118
  27. package/dist/migration/snapshot.cjs.map +1 -1
  28. package/dist/migration/snapshot.d.cts +34 -12
  29. package/dist/migration/snapshot.d.ts +34 -12
  30. package/dist/migration/snapshot.js +430 -117
  31. package/dist/migration/snapshot.js.map +1 -1
  32. package/dist/mutator.d.cts +3 -3
  33. package/dist/mutator.d.ts +3 -3
  34. package/dist/schema.cjs +34 -0
  35. package/dist/schema.cjs.map +1 -1
  36. package/dist/schema.d.cts +1 -1
  37. package/dist/schema.d.ts +1 -1
  38. package/dist/schema.js +33 -1
  39. package/dist/schema.js.map +1 -1
  40. package/dist/types.d.cts +5 -2
  41. package/dist/types.d.ts +5 -2
  42. package/dist/user-_AM523hb.d.cts +123 -0
  43. package/dist/user-_AM523hb.d.ts +123 -0
  44. package/package.json +2 -3
  45. package/dist/user-C39DQ40N.d.cts +0 -53
  46. package/dist/user-C39DQ40N.d.ts +0 -53
@@ -1,7 +1,7 @@
1
1
  'use strict';
2
2
 
3
- var fs = require('fs');
4
- var path = require('path');
3
+ var fs2 = require('fs');
4
+ var path2 = require('path');
5
5
 
6
6
  function _interopNamespace(e) {
7
7
  if (e && e.__esModule) return e;
@@ -21,8 +21,8 @@ function _interopNamespace(e) {
21
21
  return Object.freeze(n);
22
22
  }
23
23
 
24
- var fs__namespace = /*#__PURE__*/_interopNamespace(fs);
25
- var path__namespace = /*#__PURE__*/_interopNamespace(path);
24
+ var fs2__namespace = /*#__PURE__*/_interopNamespace(fs2);
25
+ var path2__namespace = /*#__PURE__*/_interopNamespace(path2);
26
26
 
27
27
  // src/migration/snapshot.ts
28
28
 
@@ -71,10 +71,10 @@ var FileSystemError = class _FileSystemError extends MigrationError {
71
71
  operation;
72
72
  code;
73
73
  originalError;
74
- constructor(message, path2, operation, code, originalError) {
74
+ constructor(message, path3, operation, code, originalError) {
75
75
  super(message);
76
76
  this.name = "FileSystemError";
77
- this.path = path2;
77
+ this.path = path3;
78
78
  this.operation = operation;
79
79
  this.code = code;
80
80
  this.originalError = originalError;
@@ -105,8 +105,358 @@ Cause: ${this.originalError.message}`);
105
105
  }
106
106
  };
107
107
 
108
- // src/migration/snapshot.ts
108
+ // src/migration/pocketbase-converter.ts
109
109
  var SNAPSHOT_VERSION = "1.0.0";
110
+ function resolveCollectionIdToName(collectionId) {
111
+ if (collectionId === "_pb_users_auth_") {
112
+ return "Users";
113
+ }
114
+ const nameMatch = collectionId.match(/app\.findCollectionByNameOrId\s*\(\s*["']([^"']+)["']\s*\)/);
115
+ if (nameMatch) {
116
+ return nameMatch[1];
117
+ }
118
+ return collectionId;
119
+ }
120
+ function convertPocketBaseCollection(pbCollection) {
121
+ const fields = [];
122
+ const systemFieldNames = ["id", "created", "updated", "collectionId", "collectionName", "expand"];
123
+ const authSystemFieldNames = ["email", "emailVisibility", "verified", "password", "tokenKey"];
124
+ if (pbCollection.fields && Array.isArray(pbCollection.fields)) {
125
+ for (const pbField of pbCollection.fields) {
126
+ if (pbField.system || systemFieldNames.includes(pbField.name)) {
127
+ continue;
128
+ }
129
+ if (pbCollection.type === "auth" && authSystemFieldNames.includes(pbField.name)) {
130
+ continue;
131
+ }
132
+ const field = {
133
+ name: pbField.name,
134
+ type: pbField.type,
135
+ required: pbField.required || false
136
+ };
137
+ field.options = pbField.options ? { ...pbField.options } : {};
138
+ if (pbField.type === "select") {
139
+ if (pbField.values && Array.isArray(pbField.values)) {
140
+ field.options.values = pbField.values;
141
+ } else if (pbField.options?.values && Array.isArray(pbField.options.values)) {
142
+ field.options.values = pbField.options.values;
143
+ }
144
+ }
145
+ if (pbField.type === "relation") {
146
+ const collectionId = pbField.collectionId || pbField.options?.collectionId || "";
147
+ const collectionName = resolveCollectionIdToName(collectionId);
148
+ field.relation = {
149
+ collection: collectionName,
150
+ cascadeDelete: pbField.cascadeDelete ?? pbField.options?.cascadeDelete ?? false,
151
+ maxSelect: pbField.maxSelect ?? pbField.options?.maxSelect,
152
+ minSelect: pbField.minSelect ?? pbField.options?.minSelect
153
+ };
154
+ }
155
+ const hasOnlyValues = Object.keys(field.options).length === 1 && field.options.values !== void 0;
156
+ if (Object.keys(field.options).length === 0) {
157
+ delete field.options;
158
+ } else if (pbField.type === "select" && hasOnlyValues) ;
159
+ fields.push(field);
160
+ }
161
+ }
162
+ const schema = {
163
+ name: pbCollection.name,
164
+ type: pbCollection.type || "base",
165
+ fields
166
+ };
167
+ if (pbCollection.indexes && Array.isArray(pbCollection.indexes)) {
168
+ schema.indexes = pbCollection.indexes;
169
+ }
170
+ const rules = {};
171
+ if (pbCollection.listRule !== void 0) rules.listRule = pbCollection.listRule;
172
+ if (pbCollection.viewRule !== void 0) rules.viewRule = pbCollection.viewRule;
173
+ if (pbCollection.createRule !== void 0) rules.createRule = pbCollection.createRule;
174
+ if (pbCollection.updateRule !== void 0) rules.updateRule = pbCollection.updateRule;
175
+ if (pbCollection.deleteRule !== void 0) rules.deleteRule = pbCollection.deleteRule;
176
+ if (pbCollection.manageRule !== void 0) rules.manageRule = pbCollection.manageRule;
177
+ if (Object.keys(rules).length > 0) {
178
+ schema.rules = rules;
179
+ schema.permissions = { ...rules };
180
+ }
181
+ return schema;
182
+ }
183
+ function convertPocketBaseMigration(migrationContent) {
184
+ try {
185
+ const snapshotMatch = migrationContent.match(/const\s+snapshot\s*=\s*(\[[\s\S]*?\]);/);
186
+ if (!snapshotMatch) {
187
+ throw new Error("Could not find snapshot array in migration file");
188
+ }
189
+ const snapshotArrayStr = snapshotMatch[1];
190
+ let snapshotArray;
191
+ try {
192
+ snapshotArray = new Function(`return ${snapshotArrayStr}`)();
193
+ } catch (parseError) {
194
+ throw new Error(`Failed to parse snapshot array: ${parseError}`);
195
+ }
196
+ if (!Array.isArray(snapshotArray)) {
197
+ throw new Error("Snapshot is not an array");
198
+ }
199
+ const collections = /* @__PURE__ */ new Map();
200
+ for (const pbCollection of snapshotArray) {
201
+ if (!pbCollection.name) {
202
+ console.warn("Skipping collection without name");
203
+ continue;
204
+ }
205
+ const schema = convertPocketBaseCollection(pbCollection);
206
+ collections.set(pbCollection.name, schema);
207
+ }
208
+ return {
209
+ version: SNAPSHOT_VERSION,
210
+ timestamp: (/* @__PURE__ */ new Date()).toISOString(),
211
+ collections
212
+ };
213
+ } catch (error) {
214
+ throw new SnapshotError(
215
+ `Failed to convert PocketBase migration: ${error instanceof Error ? error.message : String(error)}`,
216
+ void 0,
217
+ "parse",
218
+ error instanceof Error ? error : void 0
219
+ );
220
+ }
221
+ }
222
+
223
+ // src/migration/migration-parser.ts
224
+ function extractTimestampFromFilename(filename) {
225
+ const match = filename.match(/^(\d+)_/);
226
+ if (match) {
227
+ return parseInt(match[1], 10);
228
+ }
229
+ return null;
230
+ }
231
+ function findMigrationsAfterSnapshot(migrationsPath, snapshotTimestamp) {
232
+ try {
233
+ if (!fs2__namespace.existsSync(migrationsPath)) {
234
+ return [];
235
+ }
236
+ const files = fs2__namespace.readdirSync(migrationsPath);
237
+ const migrationFiles = [];
238
+ for (const file of files) {
239
+ if (file.endsWith("_collections_snapshot.js") || file.endsWith("_snapshot.js")) {
240
+ continue;
241
+ }
242
+ if (!file.endsWith(".js")) {
243
+ continue;
244
+ }
245
+ const timestamp = extractTimestampFromFilename(file);
246
+ if (timestamp && timestamp > snapshotTimestamp) {
247
+ migrationFiles.push({
248
+ path: path2__namespace.join(migrationsPath, file),
249
+ timestamp
250
+ });
251
+ }
252
+ }
253
+ migrationFiles.sort((a, b) => a.timestamp - b.timestamp);
254
+ return migrationFiles.map((f) => f.path);
255
+ } catch (error) {
256
+ console.warn(`Error finding migrations after snapshot: ${error}`);
257
+ return [];
258
+ }
259
+ }
260
+ function parseMigrationOperationsFromContent(content) {
261
+ const collectionsToCreate = [];
262
+ const collectionsToDelete = [];
263
+ try {
264
+ let searchIndex = 0;
265
+ while (true) {
266
+ const collectionStart = content.indexOf("new Collection(", searchIndex);
267
+ if (collectionStart === -1) {
268
+ break;
269
+ }
270
+ const openParen = collectionStart + "new Collection(".length;
271
+ let braceCount = 0;
272
+ let parenCount = 1;
273
+ let inString = false;
274
+ let stringChar = null;
275
+ let i = openParen;
276
+ while (i < content.length && /\s/.test(content[i])) {
277
+ i++;
278
+ }
279
+ if (content[i] !== "{") {
280
+ searchIndex = i + 1;
281
+ continue;
282
+ }
283
+ const objectStart = i;
284
+ braceCount = 1;
285
+ i++;
286
+ while (i < content.length && (braceCount > 0 || parenCount > 0)) {
287
+ const char = content[i];
288
+ const prevChar = i > 0 ? content[i - 1] : "";
289
+ if (!inString && (char === '"' || char === "'")) {
290
+ inString = true;
291
+ stringChar = char;
292
+ } else if (inString && char === stringChar && prevChar !== "\\") {
293
+ inString = false;
294
+ stringChar = null;
295
+ }
296
+ if (!inString) {
297
+ if (char === "{") braceCount++;
298
+ if (char === "}") braceCount--;
299
+ if (char === "(") parenCount++;
300
+ if (char === ")") parenCount--;
301
+ }
302
+ i++;
303
+ }
304
+ if (braceCount === 0 && parenCount === 0) {
305
+ const objectContent = content.substring(objectStart, i - 1);
306
+ try {
307
+ const collectionObj = new Function(`return ${objectContent}`)();
308
+ if (collectionObj && collectionObj.name) {
309
+ const schema = convertPocketBaseCollection(collectionObj);
310
+ collectionsToCreate.push(schema);
311
+ }
312
+ } catch (error) {
313
+ console.warn(`Failed to parse collection definition: ${error}`);
314
+ }
315
+ }
316
+ searchIndex = i;
317
+ }
318
+ const deleteMatches = content.matchAll(
319
+ /app\.delete\s*\(\s*(?:collection_\w+|app\.findCollectionByNameOrId\s*\(\s*["']([^"']+)["']\s*\))\s*\)/g
320
+ );
321
+ for (const match of deleteMatches) {
322
+ if (match[1]) {
323
+ collectionsToDelete.push(match[1]);
324
+ } else {
325
+ const varNameMatch = match[0].match(/collection_(\w+)/);
326
+ if (varNameMatch) {
327
+ const varName = `collection_${varNameMatch[1]}`;
328
+ const deleteIndex = content.indexOf(match[0]);
329
+ const beforeDelete = content.substring(0, deleteIndex);
330
+ const varDefMatch = beforeDelete.match(
331
+ new RegExp(`const\\s+${varName}\\s*=\\s*new\\s+Collection\\(\\s*(\\{[\\s\\S]*?\\})\\s*\\)`, "g")
332
+ );
333
+ if (varDefMatch && varDefMatch.length > 0) {
334
+ const collectionDefMatch = beforeDelete.match(
335
+ new RegExp(`const\\s+${varName}\\s*=\\s*new\\s+Collection\\(\\s*(\\{[\\s\\S]*?\\})\\s*\\)`)
336
+ );
337
+ if (collectionDefMatch) {
338
+ try {
339
+ const collectionDefStr = collectionDefMatch[1];
340
+ const collectionObj = new Function(`return ${collectionDefStr}`)();
341
+ if (collectionObj && collectionObj.name) {
342
+ collectionsToDelete.push(collectionObj.name);
343
+ }
344
+ } catch {
345
+ }
346
+ }
347
+ }
348
+ }
349
+ }
350
+ }
351
+ const findAndDeleteMatches = content.matchAll(
352
+ /app\.findCollectionByNameOrId\s*\(\s*["']([^"']+)["']\s*\)[\s\S]*?app\.delete/g
353
+ );
354
+ for (const match of findAndDeleteMatches) {
355
+ collectionsToDelete.push(match[1]);
356
+ }
357
+ } catch (error) {
358
+ console.warn(`Failed to parse migration operations from content: ${error}`);
359
+ }
360
+ return { collectionsToCreate, collectionsToDelete };
361
+ }
362
+ function parseMigrationOperations(migrationContent) {
363
+ try {
364
+ const migrateMatch = migrationContent.match(/migrate\s*\(\s*/);
365
+ if (!migrateMatch) {
366
+ return parseMigrationOperationsFromContent(migrationContent);
367
+ }
368
+ const startIndex = migrateMatch.index + migrateMatch[0].length;
369
+ let i = startIndex;
370
+ let parenCount = 0;
371
+ let foundFirstParen = false;
372
+ while (i < migrationContent.length) {
373
+ const char = migrationContent[i];
374
+ if (char === "(") {
375
+ parenCount++;
376
+ foundFirstParen = true;
377
+ i++;
378
+ break;
379
+ }
380
+ i++;
381
+ }
382
+ if (!foundFirstParen) {
383
+ return parseMigrationOperationsFromContent(migrationContent);
384
+ }
385
+ let inString = false;
386
+ let stringChar = null;
387
+ let foundBrace = false;
388
+ let braceStart = -1;
389
+ while (i < migrationContent.length && !foundBrace) {
390
+ const char = migrationContent[i];
391
+ const prevChar = i > 0 ? migrationContent[i - 1] : "";
392
+ if (!inString && (char === '"' || char === "'")) {
393
+ inString = true;
394
+ stringChar = char;
395
+ } else if (inString && char === stringChar && prevChar !== "\\") {
396
+ inString = false;
397
+ stringChar = null;
398
+ }
399
+ if (!inString) {
400
+ if (char === "(") parenCount++;
401
+ if (char === ")") {
402
+ parenCount--;
403
+ if (parenCount === 0) {
404
+ i++;
405
+ while (i < migrationContent.length && /\s/.test(migrationContent[i])) {
406
+ i++;
407
+ }
408
+ if (i < migrationContent.length - 1 && migrationContent[i] === "=" && migrationContent[i + 1] === ">") {
409
+ i += 2;
410
+ while (i < migrationContent.length && /\s/.test(migrationContent[i])) {
411
+ i++;
412
+ }
413
+ if (i < migrationContent.length && migrationContent[i] === "{") {
414
+ foundBrace = true;
415
+ braceStart = i + 1;
416
+ break;
417
+ }
418
+ }
419
+ }
420
+ }
421
+ }
422
+ i++;
423
+ }
424
+ if (!foundBrace || braceStart === -1) {
425
+ return parseMigrationOperationsFromContent(migrationContent);
426
+ }
427
+ let braceCount = 1;
428
+ i = braceStart;
429
+ inString = false;
430
+ stringChar = null;
431
+ while (i < migrationContent.length && braceCount > 0) {
432
+ const char = migrationContent[i];
433
+ const prevChar = i > 0 ? migrationContent[i - 1] : "";
434
+ if (!inString && (char === '"' || char === "'")) {
435
+ inString = true;
436
+ stringChar = char;
437
+ } else if (inString && char === stringChar && prevChar !== "\\") {
438
+ inString = false;
439
+ stringChar = null;
440
+ }
441
+ if (!inString) {
442
+ if (char === "{") braceCount++;
443
+ if (char === "}") braceCount--;
444
+ }
445
+ i++;
446
+ }
447
+ if (braceCount === 0) {
448
+ const upMigrationContent = migrationContent.substring(braceStart, i - 1);
449
+ return parseMigrationOperationsFromContent(upMigrationContent);
450
+ }
451
+ return parseMigrationOperationsFromContent(migrationContent);
452
+ } catch (error) {
453
+ console.warn(`Failed to parse migration operations: ${error}`);
454
+ return { collectionsToCreate: [], collectionsToDelete: [] };
455
+ }
456
+ }
457
+
458
+ // src/migration/snapshot.ts
459
+ var SNAPSHOT_VERSION2 = "1.0.0";
110
460
  var DEFAULT_SNAPSHOT_FILENAME = ".migration-snapshot.json";
111
461
  var SNAPSHOT_MIGRATIONS = [
112
462
  // Add migrations here as the format evolves
@@ -121,7 +471,7 @@ var DEFAULT_CONFIG = {
121
471
  snapshotPath: DEFAULT_SNAPSHOT_FILENAME,
122
472
  workspaceRoot: process.cwd(),
123
473
  autoMigrate: true,
124
- version: SNAPSHOT_VERSION
474
+ version: SNAPSHOT_VERSION2
125
475
  };
126
476
  function mergeConfig(config = {}) {
127
477
  return {
@@ -133,15 +483,15 @@ function getSnapshotPath(config = {}) {
133
483
  const mergedConfig = mergeConfig(config);
134
484
  const workspaceRoot = mergedConfig.workspaceRoot;
135
485
  const snapshotFilename = mergedConfig.snapshotPath;
136
- if (path__namespace.isAbsolute(snapshotFilename)) {
486
+ if (path2__namespace.isAbsolute(snapshotFilename)) {
137
487
  return snapshotFilename;
138
488
  }
139
- return path__namespace.join(workspaceRoot, snapshotFilename);
489
+ return path2__namespace.join(workspaceRoot, snapshotFilename);
140
490
  }
141
491
  function snapshotExists(config = {}) {
142
492
  try {
143
493
  const snapshotPath = getSnapshotPath(config);
144
- return fs__namespace.existsSync(snapshotPath);
494
+ return fs2__namespace.existsSync(snapshotPath);
145
495
  } catch {
146
496
  return false;
147
497
  }
@@ -200,13 +550,13 @@ function addSnapshotMetadata(schema, config) {
200
550
  function saveSnapshot(schema, config = {}) {
201
551
  const snapshotPath = getSnapshotPath(config);
202
552
  try {
203
- const snapshotDir = path__namespace.dirname(snapshotPath);
204
- if (!fs__namespace.existsSync(snapshotDir)) {
205
- fs__namespace.mkdirSync(snapshotDir, { recursive: true });
553
+ const snapshotDir = path2__namespace.dirname(snapshotPath);
554
+ if (!fs2__namespace.existsSync(snapshotDir)) {
555
+ fs2__namespace.mkdirSync(snapshotDir, { recursive: true });
206
556
  }
207
557
  const snapshotData = addSnapshotMetadata(schema, config);
208
558
  const jsonContent = JSON.stringify(snapshotData, null, 2);
209
- fs__namespace.writeFileSync(snapshotPath, jsonContent, "utf-8");
559
+ fs2__namespace.writeFileSync(snapshotPath, jsonContent, "utf-8");
210
560
  } catch (error) {
211
561
  handleFileSystemError(error, "write", snapshotPath);
212
562
  }
@@ -301,7 +651,7 @@ function deserializeSnapshot(data) {
301
651
  function loadSnapshot(config = {}) {
302
652
  const snapshotPath = getSnapshotPath(config);
303
653
  try {
304
- const jsonContent = fs__namespace.readFileSync(snapshotPath, "utf-8");
654
+ const jsonContent = fs2__namespace.readFileSync(snapshotPath, "utf-8");
305
655
  const data = parseAndValidateSnapshot(jsonContent, snapshotPath);
306
656
  const migratedData = migrateSnapshotFormat(data, config);
307
657
  return deserializeSnapshot(migratedData);
@@ -336,10 +686,10 @@ function mergeSnapshots(baseSnapshot, customSnapshot) {
336
686
  }
337
687
  function findLatestSnapshot(migrationsPath) {
338
688
  try {
339
- if (!fs__namespace.existsSync(migrationsPath)) {
689
+ if (!fs2__namespace.existsSync(migrationsPath)) {
340
690
  return null;
341
691
  }
342
- const files = fs__namespace.readdirSync(migrationsPath);
692
+ const files = fs2__namespace.readdirSync(migrationsPath);
343
693
  const snapshotFiles = files.filter(
344
694
  (file) => file.endsWith("_collections_snapshot.js") || file.endsWith("_snapshot.js")
345
695
  );
@@ -351,20 +701,74 @@ function findLatestSnapshot(migrationsPath) {
351
701
  if (!latestSnapshot) {
352
702
  return null;
353
703
  }
354
- return path__namespace.join(migrationsPath, latestSnapshot);
704
+ return path2__namespace.join(migrationsPath, latestSnapshot);
355
705
  } catch (error) {
356
706
  console.warn(`Error finding latest snapshot: ${error}`);
357
707
  return null;
358
708
  }
359
709
  }
710
+ function applyMigrationOperations(snapshot, operations) {
711
+ const updatedCollections = new Map(snapshot.collections);
712
+ for (const collectionName of operations.collectionsToDelete) {
713
+ updatedCollections.delete(collectionName);
714
+ }
715
+ for (const collection of operations.collectionsToCreate) {
716
+ updatedCollections.set(collection.name, collection);
717
+ }
718
+ return {
719
+ ...snapshot,
720
+ collections: updatedCollections
721
+ };
722
+ }
723
+ function loadSnapshotWithMigrations(config = {}) {
724
+ const migrationsPath = config.migrationsPath;
725
+ if (!migrationsPath) {
726
+ return null;
727
+ }
728
+ if (fs2__namespace.existsSync(migrationsPath) && fs2__namespace.statSync(migrationsPath).isFile()) {
729
+ try {
730
+ const migrationContent = fs2__namespace.readFileSync(migrationsPath, "utf-8");
731
+ return convertPocketBaseMigration(migrationContent);
732
+ } catch (error) {
733
+ console.warn(`Failed to load snapshot from ${migrationsPath}: ${error}`);
734
+ return null;
735
+ }
736
+ }
737
+ const latestSnapshotPath = findLatestSnapshot(migrationsPath);
738
+ if (!latestSnapshotPath) {
739
+ return null;
740
+ }
741
+ try {
742
+ const migrationContent = fs2__namespace.readFileSync(latestSnapshotPath, "utf-8");
743
+ let snapshot = convertPocketBaseMigration(migrationContent);
744
+ const snapshotFilename = path2__namespace.basename(latestSnapshotPath);
745
+ const snapshotTimestamp = extractTimestampFromFilename(snapshotFilename);
746
+ if (snapshotTimestamp) {
747
+ const migrationFiles = findMigrationsAfterSnapshot(migrationsPath, snapshotTimestamp);
748
+ for (const migrationFile of migrationFiles) {
749
+ try {
750
+ const migrationContent2 = fs2__namespace.readFileSync(migrationFile, "utf-8");
751
+ const operations = parseMigrationOperations(migrationContent2);
752
+ snapshot = applyMigrationOperations(snapshot, operations);
753
+ } catch (error) {
754
+ console.warn(`Failed to apply migration ${migrationFile}: ${error}`);
755
+ }
756
+ }
757
+ }
758
+ return snapshot;
759
+ } catch (error) {
760
+ console.warn(`Failed to load snapshot from ${latestSnapshotPath}: ${error}`);
761
+ return null;
762
+ }
763
+ }
360
764
  function loadSnapshotIfExists(config = {}) {
361
765
  const migrationsPath = config.migrationsPath;
362
766
  if (!migrationsPath) {
363
767
  return null;
364
768
  }
365
- if (fs__namespace.existsSync(migrationsPath) && fs__namespace.statSync(migrationsPath).isFile()) {
769
+ if (fs2__namespace.existsSync(migrationsPath) && fs2__namespace.statSync(migrationsPath).isFile()) {
366
770
  try {
367
- const migrationContent = fs__namespace.readFileSync(migrationsPath, "utf-8");
771
+ const migrationContent = fs2__namespace.readFileSync(migrationsPath, "utf-8");
368
772
  return convertPocketBaseMigration(migrationContent);
369
773
  } catch (error) {
370
774
  console.warn(`Failed to load snapshot from ${migrationsPath}: ${error}`);
@@ -374,7 +778,7 @@ function loadSnapshotIfExists(config = {}) {
374
778
  const latestSnapshotPath = findLatestSnapshot(migrationsPath);
375
779
  if (latestSnapshotPath) {
376
780
  try {
377
- const migrationContent = fs__namespace.readFileSync(latestSnapshotPath, "utf-8");
781
+ const migrationContent = fs2__namespace.readFileSync(latestSnapshotPath, "utf-8");
378
782
  return convertPocketBaseMigration(migrationContent);
379
783
  } catch (error) {
380
784
  console.warn(`Failed to load snapshot from ${latestSnapshotPath}: ${error}`);
@@ -383,100 +787,9 @@ function loadSnapshotIfExists(config = {}) {
383
787
  }
384
788
  return null;
385
789
  }
386
- function convertPocketBaseCollection(pbCollection) {
387
- const fields = [];
388
- const systemFieldNames = ["id", "created", "updated", "collectionId", "collectionName", "expand"];
389
- const authSystemFieldNames = ["email", "emailVisibility", "verified", "password", "tokenKey"];
390
- if (pbCollection.fields && Array.isArray(pbCollection.fields)) {
391
- for (const pbField of pbCollection.fields) {
392
- if (pbField.system || systemFieldNames.includes(pbField.name)) {
393
- continue;
394
- }
395
- if (pbCollection.type === "auth" && authSystemFieldNames.includes(pbField.name)) {
396
- continue;
397
- }
398
- const field = {
399
- name: pbField.name,
400
- type: pbField.type,
401
- required: pbField.required || false
402
- };
403
- if (pbField.options) {
404
- field.options = pbField.options;
405
- }
406
- if (pbField.type === "relation") {
407
- field.relation = {
408
- collection: pbField.options?.collectionId || "",
409
- cascadeDelete: pbField.options?.cascadeDelete || false,
410
- maxSelect: pbField.options?.maxSelect,
411
- minSelect: pbField.options?.minSelect
412
- };
413
- }
414
- fields.push(field);
415
- }
416
- }
417
- const schema = {
418
- name: pbCollection.name,
419
- type: pbCollection.type || "base",
420
- fields
421
- };
422
- if (pbCollection.indexes && Array.isArray(pbCollection.indexes)) {
423
- schema.indexes = pbCollection.indexes;
424
- }
425
- const rules = {};
426
- if (pbCollection.listRule !== void 0) rules.listRule = pbCollection.listRule;
427
- if (pbCollection.viewRule !== void 0) rules.viewRule = pbCollection.viewRule;
428
- if (pbCollection.createRule !== void 0) rules.createRule = pbCollection.createRule;
429
- if (pbCollection.updateRule !== void 0) rules.updateRule = pbCollection.updateRule;
430
- if (pbCollection.deleteRule !== void 0) rules.deleteRule = pbCollection.deleteRule;
431
- if (pbCollection.manageRule !== void 0) rules.manageRule = pbCollection.manageRule;
432
- if (Object.keys(rules).length > 0) {
433
- schema.rules = rules;
434
- schema.permissions = { ...rules };
435
- }
436
- return schema;
437
- }
438
- function convertPocketBaseMigration(migrationContent) {
439
- try {
440
- const snapshotMatch = migrationContent.match(/const\s+snapshot\s*=\s*(\[[\s\S]*?\]);/);
441
- if (!snapshotMatch) {
442
- throw new Error("Could not find snapshot array in migration file");
443
- }
444
- const snapshotArrayStr = snapshotMatch[1];
445
- let snapshotArray;
446
- try {
447
- snapshotArray = new Function(`return ${snapshotArrayStr}`)();
448
- } catch (parseError) {
449
- throw new Error(`Failed to parse snapshot array: ${parseError}`);
450
- }
451
- if (!Array.isArray(snapshotArray)) {
452
- throw new Error("Snapshot is not an array");
453
- }
454
- const collections = /* @__PURE__ */ new Map();
455
- for (const pbCollection of snapshotArray) {
456
- if (!pbCollection.name) {
457
- console.warn("Skipping collection without name");
458
- continue;
459
- }
460
- const schema = convertPocketBaseCollection(pbCollection);
461
- collections.set(pbCollection.name, schema);
462
- }
463
- return {
464
- version: SNAPSHOT_VERSION,
465
- timestamp: (/* @__PURE__ */ new Date()).toISOString(),
466
- collections
467
- };
468
- } catch (error) {
469
- throw new SnapshotError(
470
- `Failed to convert PocketBase migration: ${error instanceof Error ? error.message : String(error)}`,
471
- void 0,
472
- "parse",
473
- error instanceof Error ? error : void 0
474
- );
475
- }
476
- }
477
790
  function loadBaseMigration(migrationPath) {
478
791
  try {
479
- if (!fs__namespace.existsSync(migrationPath)) {
792
+ if (!fs2__namespace.existsSync(migrationPath)) {
480
793
  throw new SnapshotError(
481
794
  `Base migration file not found: ${migrationPath}
482
795
 
@@ -487,7 +800,7 @@ If the file exists in a different location, update the configuration.`,
487
800
  "read"
488
801
  );
489
802
  }
490
- const migrationContent = fs__namespace.readFileSync(migrationPath, "utf-8");
803
+ const migrationContent = fs2__namespace.readFileSync(migrationPath, "utf-8");
491
804
  const snapshot = convertPocketBaseMigration(migrationContent);
492
805
  return snapshot;
493
806
  } catch (error) {
@@ -523,14 +836,14 @@ Please ensure PocketBase is properly set up by running 'yarn setup'.`,
523
836
  }
524
837
  }
525
838
  function getSnapshotVersion() {
526
- return SNAPSHOT_VERSION;
839
+ return SNAPSHOT_VERSION2;
527
840
  }
528
841
  function validateSnapshot(snapshot) {
529
842
  const issues = [];
530
843
  if (!snapshot.version) {
531
844
  issues.push("Missing version field");
532
- } else if (compareVersions(snapshot.version, SNAPSHOT_VERSION) > 0) {
533
- issues.push(`Snapshot version ${snapshot.version} is newer than supported version ${SNAPSHOT_VERSION}`);
845
+ } else if (compareVersions(snapshot.version, SNAPSHOT_VERSION2) > 0) {
846
+ issues.push(`Snapshot version ${snapshot.version} is newer than supported version ${SNAPSHOT_VERSION2}`);
534
847
  }
535
848
  if (!snapshot.timestamp) {
536
849
  issues.push("Missing timestamp field");
@@ -602,6 +915,7 @@ exports.getSnapshotVersion = getSnapshotVersion;
602
915
  exports.loadBaseMigration = loadBaseMigration;
603
916
  exports.loadSnapshot = loadSnapshot;
604
917
  exports.loadSnapshotIfExists = loadSnapshotIfExists;
918
+ exports.loadSnapshotWithMigrations = loadSnapshotWithMigrations;
605
919
  exports.mergeSnapshots = mergeSnapshots;
606
920
  exports.saveSnapshot = saveSnapshot;
607
921
  exports.snapshotExists = snapshotExists;