@famgia/omnify-cli 0.0.162 → 0.0.164

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -6,10 +6,229 @@ var __require = /* @__PURE__ */ ((x) => typeof require !== "undefined" ? require
6
6
  });
7
7
 
8
8
  // src/config/loader.ts
9
- import { existsSync } from "fs";
10
- import { resolve, dirname } from "path";
9
+ import { existsSync as existsSync2 } from "fs";
10
+ import { resolve as resolve2, dirname as dirname2 } from "path";
11
11
  import { createJiti } from "jiti";
12
12
  import { configError, configNotFoundError } from "@famgia/omnify-core";
13
+
14
+ // src/config/discovery.ts
15
+ import { existsSync, readFileSync } from "fs";
16
+ import { resolve } from "path";
17
+
18
+ // src/output/logger.ts
19
+ import pc from "picocolors";
20
+ import { formatError, getExitCode } from "@famgia/omnify-core";
21
+ var Logger = class {
22
+ _verbose;
23
+ _quiet;
24
+ _startTime;
25
+ constructor(options = {}) {
26
+ this._verbose = options.verbose ?? false;
27
+ this._quiet = options.quiet ?? false;
28
+ this._startTime = Date.now();
29
+ }
30
+ /**
31
+ * Enable or disable verbose mode.
32
+ */
33
+ setVerbose(verbose) {
34
+ this._verbose = verbose;
35
+ }
36
+ /**
37
+ * Enable or disable quiet mode.
38
+ */
39
+ setQuiet(quiet) {
40
+ this._quiet = quiet;
41
+ }
42
+ /**
43
+ * Log an info message.
44
+ */
45
+ info(message) {
46
+ if (!this._quiet) {
47
+ console.log(message);
48
+ }
49
+ }
50
+ /**
51
+ * Log a success message.
52
+ */
53
+ success(message) {
54
+ if (!this._quiet) {
55
+ console.log(pc.green("\u2713") + " " + message);
56
+ }
57
+ }
58
+ /**
59
+ * Log a warning message.
60
+ */
61
+ warn(message) {
62
+ if (!this._quiet) {
63
+ console.log(pc.yellow("\u26A0") + " " + pc.yellow(message));
64
+ }
65
+ }
66
+ /**
67
+ * Log an error message.
68
+ */
69
+ error(message) {
70
+ console.error(pc.red("\u2717") + " " + pc.red(message));
71
+ }
72
+ /**
73
+ * Log a debug message (only in verbose mode).
74
+ */
75
+ debug(message) {
76
+ if (this._verbose && !this._quiet) {
77
+ console.log(pc.dim(" " + message));
78
+ }
79
+ }
80
+ /**
81
+ * Log a step message.
82
+ */
83
+ step(message) {
84
+ if (!this._quiet) {
85
+ console.log(pc.cyan("\u2192") + " " + message);
86
+ }
87
+ }
88
+ /**
89
+ * Log a header.
90
+ */
91
+ header(message) {
92
+ if (!this._quiet) {
93
+ console.log();
94
+ console.log(pc.bold(message));
95
+ console.log();
96
+ }
97
+ }
98
+ /**
99
+ * Log a list item.
100
+ */
101
+ list(items) {
102
+ if (!this._quiet) {
103
+ for (const item of items) {
104
+ console.log(" \u2022 " + item);
105
+ }
106
+ }
107
+ }
108
+ /**
109
+ * Log a timing message.
110
+ */
111
+ timing(message) {
112
+ if (this._verbose && !this._quiet) {
113
+ const elapsed = Date.now() - this._startTime;
114
+ console.log(pc.dim(` [${elapsed}ms] ${message}`));
115
+ }
116
+ }
117
+ /**
118
+ * Log an empty line.
119
+ */
120
+ newline() {
121
+ if (!this._quiet) {
122
+ console.log();
123
+ }
124
+ }
125
+ /**
126
+ * Format and log an OmnifyError.
127
+ */
128
+ formatError(error) {
129
+ const formatted = formatError(error, { color: true });
130
+ console.error(formatted);
131
+ }
132
+ /**
133
+ * Get exit code for an error.
134
+ */
135
+ getExitCode(error) {
136
+ return getExitCode(error);
137
+ }
138
+ };
139
+ var logger = new Logger();
140
+
141
+ // src/config/discovery.ts
142
+ var MANIFEST_FILENAME = ".omnify-packages.json";
143
+ var MANIFEST_VERSION = 1;
144
+ function loadPackageManifest(projectRoot) {
145
+ const manifestPath = resolve(projectRoot, MANIFEST_FILENAME);
146
+ if (!existsSync(manifestPath)) {
147
+ logger.debug(`Package manifest not found: ${manifestPath}`);
148
+ return null;
149
+ }
150
+ try {
151
+ const content = readFileSync(manifestPath, "utf-8");
152
+ const manifest = JSON.parse(content);
153
+ if (manifest.version !== MANIFEST_VERSION) {
154
+ logger.warn(
155
+ `Package manifest version mismatch: expected ${MANIFEST_VERSION}, got ${manifest.version}. Run \`composer dump-autoload\` to regenerate.`
156
+ );
157
+ }
158
+ return manifest;
159
+ } catch (error) {
160
+ const message = error instanceof Error ? error.message : String(error);
161
+ logger.warn(`Failed to read package manifest: ${message}`);
162
+ return null;
163
+ }
164
+ }
165
+ function packageConfigToSchemaPath(packageName, config) {
166
+ const result = {
167
+ path: config.schemas,
168
+ namespace: config.namespace
169
+ };
170
+ if (config.options) {
171
+ const opts = config.options;
172
+ const basePath = config.schemas.replace(/\/database\/schemas\/?$/, "");
173
+ const laravelOutput = {
174
+ base: basePath
175
+ };
176
+ if (opts.modelNamespace) {
177
+ laravelOutput.modelsNamespace = opts.modelNamespace;
178
+ }
179
+ if (opts.migrationsPath) {
180
+ laravelOutput.migrationsPath = opts.migrationsPath.replace(basePath + "/", "");
181
+ }
182
+ if (opts.factoriesPath) {
183
+ laravelOutput.factoriesPath = opts.factoriesPath.replace(basePath + "/", "");
184
+ }
185
+ if (opts.generateServiceProvider !== void 0) {
186
+ laravelOutput.generateServiceProvider = opts.generateServiceProvider;
187
+ }
188
+ if (opts.generateMigrations !== void 0) {
189
+ laravelOutput.generateMigrations = opts.generateMigrations;
190
+ }
191
+ if (opts.generateModels !== void 0) {
192
+ laravelOutput.generateModels = opts.generateModels;
193
+ }
194
+ result.output = { laravel: laravelOutput };
195
+ }
196
+ return result;
197
+ }
198
+ function discoverPackages(projectRoot, discoveryConfig, explicitPaths) {
199
+ const result = [];
200
+ const excludeSet = new Set(discoveryConfig.exclude ?? []);
201
+ if (discoveryConfig.enabled !== false) {
202
+ const manifest = loadPackageManifest(projectRoot);
203
+ if (manifest) {
204
+ const sortedPackages = Object.entries(manifest.packages).sort(
205
+ ([, a], [, b]) => (a.priority ?? 100) - (b.priority ?? 100)
206
+ );
207
+ for (const [packageName, config] of sortedPackages) {
208
+ if (excludeSet.has(packageName)) {
209
+ logger.debug(`Skipping excluded package: ${packageName}`);
210
+ continue;
211
+ }
212
+ const schemasPath = resolve(projectRoot, config.schemas);
213
+ if (!existsSync(schemasPath)) {
214
+ logger.debug(`Package schemas not found, skipping: ${schemasPath}`);
215
+ continue;
216
+ }
217
+ result.push(packageConfigToSchemaPath(packageName, config));
218
+ logger.debug(`Discovered package: ${packageName} (${config.namespace ?? "no namespace"})`);
219
+ }
220
+ if (result.length > 0) {
221
+ logger.info(`Auto-discovered ${result.length} package(s) from ${MANIFEST_FILENAME}`);
222
+ }
223
+ }
224
+ }
225
+ if (explicitPaths?.length) {
226
+ result.push(...explicitPaths);
227
+ }
228
+ return result;
229
+ }
230
+
231
+ // src/config/loader.ts
13
232
  var CONFIG_FILES = [
14
233
  "omnify.config.ts",
15
234
  "omnify.config.js",
@@ -17,10 +236,10 @@ var CONFIG_FILES = [
17
236
  "omnify.config.cjs"
18
237
  ];
19
238
  function findConfigFile(startDir) {
20
- const cwd = resolve(startDir);
239
+ const cwd = resolve2(startDir);
21
240
  for (const filename of CONFIG_FILES) {
22
- const configPath = resolve(cwd, filename);
23
- if (existsSync(configPath)) {
241
+ const configPath = resolve2(cwd, filename);
242
+ if (existsSync2(configPath)) {
24
243
  return configPath;
25
244
  }
26
245
  }
@@ -51,7 +270,7 @@ async function resolvePlugins(plugins, configPath) {
51
270
  return [];
52
271
  }
53
272
  const resolved = [];
54
- const configDir = configPath ? dirname(configPath) : process.cwd();
273
+ const configDir = configPath ? dirname2(configPath) : process.cwd();
55
274
  for (const plugin of plugins) {
56
275
  if (typeof plugin === "string") {
57
276
  const jiti = createJiti(configDir, {
@@ -77,6 +296,16 @@ async function resolvePlugins(plugins, configPath) {
77
296
  }
78
297
  async function resolveConfig(userConfig, configPath) {
79
298
  const plugins = await resolvePlugins(userConfig.plugins, configPath);
299
+ const projectRoot = configPath ? dirname2(configPath) : process.cwd();
300
+ const discovery = {
301
+ enabled: userConfig.discovery?.enabled ?? true,
302
+ exclude: userConfig.discovery?.exclude
303
+ };
304
+ const allSchemaPaths = discoverPackages(
305
+ projectRoot,
306
+ discovery,
307
+ userConfig.additionalSchemaPaths
308
+ );
80
309
  const databaseConfig = {
81
310
  driver: userConfig.database.driver,
82
311
  enableFieldComments: userConfig.database.enableFieldComments ?? false
@@ -105,8 +334,9 @@ async function resolveConfig(userConfig, configPath) {
105
334
  plugins,
106
335
  verbose: userConfig.verbose ?? false,
107
336
  lockFilePath: userConfig.lockFilePath ?? ".omnify.lock",
337
+ discovery,
108
338
  ...userConfig.locale && { locale: userConfig.locale },
109
- ...userConfig.additionalSchemaPaths && { additionalSchemaPaths: userConfig.additionalSchemaPaths }
339
+ ...allSchemaPaths.length > 0 && { additionalSchemaPaths: allSchemaPaths }
110
340
  };
111
341
  return result;
112
342
  }
@@ -136,8 +366,8 @@ function buildLaravelConfig(base, userLaravel) {
136
366
  return config;
137
367
  }
138
368
  function validateConfig(config, rootDir) {
139
- const schemaPath = resolve(rootDir, config.schemasDir);
140
- if (!existsSync(schemaPath)) {
369
+ const schemaPath = resolve2(rootDir, config.schemasDir);
370
+ if (!existsSync2(schemaPath)) {
141
371
  throw configError(
142
372
  `Schema directory not found: ${schemaPath}. Create the '${config.schemasDir}' directory or update schemasDir in config.`,
143
373
  "E002"
@@ -153,7 +383,7 @@ function requireDevUrl(config) {
153
383
  }
154
384
  }
155
385
  async function loadConfig(startDir = process.cwd()) {
156
- const cwd = resolve(startDir);
386
+ const cwd = resolve2(startDir);
157
387
  const configPath = findConfigFile(cwd);
158
388
  if (configPath) {
159
389
  const userConfig = await loadConfigFile(configPath);
@@ -163,140 +393,15 @@ async function loadConfig(startDir = process.cwd()) {
163
393
  configPath
164
394
  };
165
395
  }
166
- throw configNotFoundError(resolve(cwd, "omnify.config.ts"));
396
+ throw configNotFoundError(resolve2(cwd, "omnify.config.ts"));
167
397
  }
168
398
  function defineConfig(config) {
169
399
  return config;
170
400
  }
171
401
 
172
402
  // src/config/alias-config.ts
173
- import { existsSync as existsSync2, readFileSync, writeFileSync } from "fs";
174
- import { resolve as resolve2 } from "path";
175
-
176
- // src/output/logger.ts
177
- import pc from "picocolors";
178
- import { formatError, getExitCode } from "@famgia/omnify-core";
179
- var Logger = class {
180
- _verbose;
181
- _quiet;
182
- _startTime;
183
- constructor(options = {}) {
184
- this._verbose = options.verbose ?? false;
185
- this._quiet = options.quiet ?? false;
186
- this._startTime = Date.now();
187
- }
188
- /**
189
- * Enable or disable verbose mode.
190
- */
191
- setVerbose(verbose) {
192
- this._verbose = verbose;
193
- }
194
- /**
195
- * Enable or disable quiet mode.
196
- */
197
- setQuiet(quiet) {
198
- this._quiet = quiet;
199
- }
200
- /**
201
- * Log an info message.
202
- */
203
- info(message) {
204
- if (!this._quiet) {
205
- console.log(message);
206
- }
207
- }
208
- /**
209
- * Log a success message.
210
- */
211
- success(message) {
212
- if (!this._quiet) {
213
- console.log(pc.green("\u2713") + " " + message);
214
- }
215
- }
216
- /**
217
- * Log a warning message.
218
- */
219
- warn(message) {
220
- if (!this._quiet) {
221
- console.log(pc.yellow("\u26A0") + " " + pc.yellow(message));
222
- }
223
- }
224
- /**
225
- * Log an error message.
226
- */
227
- error(message) {
228
- console.error(pc.red("\u2717") + " " + pc.red(message));
229
- }
230
- /**
231
- * Log a debug message (only in verbose mode).
232
- */
233
- debug(message) {
234
- if (this._verbose && !this._quiet) {
235
- console.log(pc.dim(" " + message));
236
- }
237
- }
238
- /**
239
- * Log a step message.
240
- */
241
- step(message) {
242
- if (!this._quiet) {
243
- console.log(pc.cyan("\u2192") + " " + message);
244
- }
245
- }
246
- /**
247
- * Log a header.
248
- */
249
- header(message) {
250
- if (!this._quiet) {
251
- console.log();
252
- console.log(pc.bold(message));
253
- console.log();
254
- }
255
- }
256
- /**
257
- * Log a list item.
258
- */
259
- list(items) {
260
- if (!this._quiet) {
261
- for (const item of items) {
262
- console.log(" \u2022 " + item);
263
- }
264
- }
265
- }
266
- /**
267
- * Log a timing message.
268
- */
269
- timing(message) {
270
- if (this._verbose && !this._quiet) {
271
- const elapsed = Date.now() - this._startTime;
272
- console.log(pc.dim(` [${elapsed}ms] ${message}`));
273
- }
274
- }
275
- /**
276
- * Log an empty line.
277
- */
278
- newline() {
279
- if (!this._quiet) {
280
- console.log();
281
- }
282
- }
283
- /**
284
- * Format and log an OmnifyError.
285
- */
286
- formatError(error) {
287
- const formatted = formatError(error, { color: true });
288
- console.error(formatted);
289
- }
290
- /**
291
- * Get exit code for an error.
292
- */
293
- getExitCode(error) {
294
- return getExitCode(error);
295
- }
296
- };
297
- var logger = new Logger();
298
-
299
- // src/config/alias-config.ts
403
+ import { existsSync as existsSync3, readFileSync as readFileSync2, writeFileSync } from "fs";
404
+ import { resolve as resolve3 } from "path";
300
405
  function hasViteOmnifyAlias(content) {
301
406
  return content.includes("'@omnify'") || content.includes('"@omnify"') || content.includes("@omnify:") || content.includes("'@omnify/");
302
407
  }
@@ -305,17 +410,17 @@ function hasTsconfigOmnifyPath(content) {
305
410
  }
306
411
  function updateViteConfig(rootDir, omnifyPath = "omnify") {
307
412
  const configPaths = [
308
- resolve2(rootDir, "vite.config.ts"),
309
- resolve2(rootDir, "vite.config.js"),
310
- resolve2(rootDir, "vite.config.mts"),
311
- resolve2(rootDir, "vite.config.mjs")
413
+ resolve3(rootDir, "vite.config.ts"),
414
+ resolve3(rootDir, "vite.config.js"),
415
+ resolve3(rootDir, "vite.config.mts"),
416
+ resolve3(rootDir, "vite.config.mjs")
312
417
  ];
313
- const configPath = configPaths.find((p) => existsSync2(p));
418
+ const configPath = configPaths.find((p) => existsSync3(p));
314
419
  if (!configPath) {
315
420
  return { updated: false, skipped: true };
316
421
  }
317
422
  try {
318
- let content = readFileSync(configPath, "utf-8");
423
+ let content = readFileSync2(configPath, "utf-8");
319
424
  if (hasViteOmnifyAlias(content)) {
320
425
  return { updated: false, skipped: true };
321
426
  }
@@ -396,12 +501,12 @@ function updateViteConfig(rootDir, omnifyPath = "omnify") {
396
501
  }
397
502
  }
398
503
  function updateTsconfig(rootDir, omnifyPath = "omnify") {
399
- const configPath = resolve2(rootDir, "tsconfig.json");
400
- if (!existsSync2(configPath)) {
504
+ const configPath = resolve3(rootDir, "tsconfig.json");
505
+ if (!existsSync3(configPath)) {
401
506
  return { updated: false, skipped: true };
402
507
  }
403
508
  try {
404
- const content = readFileSync(configPath, "utf-8");
509
+ const content = readFileSync2(configPath, "utf-8");
405
510
  if (hasTsconfigOmnifyPath(content)) {
406
511
  return { updated: false, skipped: true };
407
512
  }
@@ -473,8 +578,8 @@ function configureOmnifyAlias(rootDir, omnifyPath = "omnify", silent = false) {
473
578
  }
474
579
 
475
580
  // src/commands/init.ts
476
- import { existsSync as existsSync3, mkdirSync, writeFileSync as writeFileSync2 } from "fs";
477
- import { resolve as resolve3 } from "path";
581
+ import { existsSync as existsSync4, mkdirSync, writeFileSync as writeFileSync2 } from "fs";
582
+ import { resolve as resolve4 } from "path";
478
583
  import { select, confirm, input } from "@inquirer/prompts";
479
584
  var EXAMPLE_SCHEMA = `# Example User schema
480
585
  # See https://github.com/famgia/omnify for documentation
@@ -563,8 +668,8 @@ async function runInit(options) {
563
668
  const cwd = process.cwd();
564
669
  logger.header("Omnify Project Setup");
565
670
  logger.newline();
566
- const configPath = resolve3(cwd, "omnify.config.ts");
567
- if (existsSync3(configPath) && !options.force) {
671
+ const configPath = resolve4(cwd, "omnify.config.ts");
672
+ if (existsSync4(configPath) && !options.force) {
568
673
  logger.warn("omnify.config.ts already exists. Use --force to overwrite.");
569
674
  return;
570
675
  }
@@ -640,13 +745,13 @@ async function runInit(options) {
640
745
  }
641
746
  logger.newline();
642
747
  logger.step("Creating project files...");
643
- const schemasDir = resolve3(cwd, config.schemasDir);
644
- if (!existsSync3(schemasDir)) {
748
+ const schemasDir = resolve4(cwd, config.schemasDir);
749
+ if (!existsSync4(schemasDir)) {
645
750
  mkdirSync(schemasDir, { recursive: true });
646
751
  logger.debug(`Created ${config.schemasDir}/ directory`);
647
752
  }
648
- const examplePath = resolve3(schemasDir, "User.yaml");
649
- if (!existsSync3(examplePath) || options.force) {
753
+ const examplePath = resolve4(schemasDir, "User.yaml");
754
+ if (!existsSync4(examplePath) || options.force) {
650
755
  writeFileSync2(examplePath, EXAMPLE_SCHEMA);
651
756
  logger.debug("Created example schema: User.yaml");
652
757
  }
@@ -709,8 +814,8 @@ function registerInitCommand(program) {
709
814
  }
710
815
 
711
816
  // src/commands/validate.ts
712
- import { existsSync as existsSync4 } from "fs";
713
- import { resolve as resolve4, dirname as dirname2 } from "path";
817
+ import { existsSync as existsSync5 } from "fs";
818
+ import { resolve as resolve5, dirname as dirname3 } from "path";
714
819
  import { loadSchemas, mergePartialSchemas, validateSchemas, OmnifyError as OmnifyError2 } from "@famgia/omnify-core";
715
820
  async function runValidate(options) {
716
821
  logger.setVerbose(options.verbose ?? false);
@@ -719,9 +824,9 @@ async function runValidate(options) {
719
824
  logger.timing("Config load start");
720
825
  const { config, configPath } = await loadConfig();
721
826
  logger.timing("Config loaded");
722
- const rootDir = configPath ? dirname2(configPath) : process.cwd();
827
+ const rootDir = configPath ? dirname3(configPath) : process.cwd();
723
828
  validateConfig(config, rootDir);
724
- const schemaPath = resolve4(rootDir, config.schemasDir);
829
+ const schemaPath = resolve5(rootDir, config.schemasDir);
725
830
  logger.step(`Loading schemas from ${schemaPath}`);
726
831
  logger.timing("Schema load start");
727
832
  let schemas = await loadSchemas(schemaPath);
@@ -731,9 +836,9 @@ async function runValidate(options) {
731
836
  if (additionalPaths.length > 0) {
732
837
  logger.step(`Loading schemas from ${additionalPaths.length} additional path(s)`);
733
838
  for (const entry of additionalPaths) {
734
- const absolutePath = resolve4(rootDir, entry.path);
839
+ const absolutePath = resolve5(rootDir, entry.path);
735
840
  logger.debug(` Checking: ${entry.path} \u2192 ${absolutePath}`);
736
- if (existsSync4(absolutePath)) {
841
+ if (existsSync5(absolutePath)) {
737
842
  const packageSchemas = await loadSchemas(absolutePath, { skipPartialResolution: true });
738
843
  const count = Object.keys(packageSchemas).filter((k) => !k.startsWith("__partial__")).length;
739
844
  const partialCount = Object.keys(packageSchemas).filter((k) => k.startsWith("__partial__")).length;
@@ -791,8 +896,8 @@ function registerValidateCommand(program) {
791
896
  }
792
897
 
793
898
  // src/commands/diff.ts
794
- import { existsSync as existsSync5 } from "fs";
795
- import { resolve as resolve5, dirname as dirname3 } from "path";
899
+ import { existsSync as existsSync6 } from "fs";
900
+ import { resolve as resolve6, dirname as dirname4 } from "path";
796
901
  import { loadSchemas as loadSchemas2, mergePartialSchemas as mergePartialSchemas2, validateSchemas as validateSchemas2, OmnifyError as OmnifyError3 } from "@famgia/omnify-core";
797
902
 
798
903
  // src/operations/diff.ts
@@ -827,10 +932,10 @@ async function runDiff(options) {
827
932
  logger.header("Checking for Schema Changes");
828
933
  logger.debug("Loading configuration...");
829
934
  const { config, configPath } = await loadConfig();
830
- const rootDir = configPath ? dirname3(configPath) : process.cwd();
935
+ const rootDir = configPath ? dirname4(configPath) : process.cwd();
831
936
  validateConfig(config, rootDir);
832
937
  requireDevUrl(config);
833
- const schemaPath = resolve5(rootDir, config.schemasDir);
938
+ const schemaPath = resolve6(rootDir, config.schemasDir);
834
939
  logger.step(`Loading schemas from ${schemaPath}`);
835
940
  let schemas = await loadSchemas2(schemaPath);
836
941
  logger.debug(`Found ${Object.keys(schemas).length} schema(s) in main directory`);
@@ -839,9 +944,9 @@ async function runDiff(options) {
839
944
  if (additionalPaths.length > 0) {
840
945
  logger.step(`Loading schemas from ${additionalPaths.length} additional path(s)`);
841
946
  for (const entry of additionalPaths) {
842
- const absolutePath = resolve5(rootDir, entry.path);
947
+ const absolutePath = resolve6(rootDir, entry.path);
843
948
  logger.debug(` Checking: ${entry.path} \u2192 ${absolutePath}`);
844
- if (existsSync5(absolutePath)) {
949
+ if (existsSync6(absolutePath)) {
845
950
  const packageSchemas = await loadSchemas2(absolutePath, { skipPartialResolution: true });
846
951
  const count = Object.keys(packageSchemas).filter((k) => !k.startsWith("__partial__")).length;
847
952
  const partialCount = Object.keys(packageSchemas).filter((k) => k.startsWith("__partial__")).length;
@@ -874,7 +979,7 @@ async function runDiff(options) {
874
979
  process.exit(2);
875
980
  }
876
981
  logger.step("Running Atlas diff...");
877
- const lockPath = resolve5(rootDir, config.lockFilePath);
982
+ const lockPath = resolve6(rootDir, config.lockFilePath);
878
983
  const diffResult = await runDiffOperation({
879
984
  schemas,
880
985
  devUrl: config.database.devUrl,
@@ -920,8 +1025,8 @@ function registerDiffCommand(program) {
920
1025
  }
921
1026
 
922
1027
  // src/commands/generate.ts
923
- import { existsSync as existsSync7, mkdirSync as mkdirSync3, writeFileSync as writeFileSync4, readdirSync as readdirSync2 } from "fs";
924
- import { resolve as resolve7, dirname as dirname5, relative } from "path";
1028
+ import { existsSync as existsSync8, mkdirSync as mkdirSync3, writeFileSync as writeFileSync4, readdirSync as readdirSync2 } from "fs";
1029
+ import { resolve as resolve8, dirname as dirname6, relative } from "path";
925
1030
  import {
926
1031
  loadSchemas as loadSchemas3,
927
1032
  mergePartialSchemas as mergePartialSchemas3,
@@ -954,8 +1059,8 @@ import {
954
1059
  import { generateTypeScript, copyStubs, generateAIGuides as generateTypescriptAIGuides, shouldGenerateAIGuides as shouldGenerateTypescriptAIGuides } from "@famgia/omnify-typescript";
955
1060
 
956
1061
  // src/guides/index.ts
957
- import { existsSync as existsSync6, writeFileSync as writeFileSync3, mkdirSync as mkdirSync2, readdirSync, readFileSync as readFileSync2 } from "fs";
958
- import { resolve as resolve6, dirname as dirname4, join } from "path";
1062
+ import { existsSync as existsSync7, writeFileSync as writeFileSync3, mkdirSync as mkdirSync2, readdirSync, readFileSync as readFileSync3 } from "fs";
1063
+ import { resolve as resolve7, dirname as dirname5, join } from "path";
959
1064
  import "url";
960
1065
  var CLAUDE_MD = `# Omnify Project
961
1066
 
@@ -1012,35 +1117,35 @@ Add your personal preferences in \`CLAUDE.local.md\` (gitignored).
1012
1117
  function copyOmnifyGuides(rootDir) {
1013
1118
  let filesWritten = 0;
1014
1119
  const omnifyPkgPaths = [
1015
- resolve6(rootDir, "node_modules", "@famgia", "omnify", "stubs", "ai-guides", "omnify"),
1016
- resolve6(rootDir, "node_modules", ".pnpm", "@famgia+omnify@*", "node_modules", "@famgia", "omnify", "stubs", "ai-guides", "omnify")
1120
+ resolve7(rootDir, "node_modules", "@famgia", "omnify", "stubs", "ai-guides", "omnify"),
1121
+ resolve7(rootDir, "node_modules", ".pnpm", "@famgia+omnify@*", "node_modules", "@famgia", "omnify", "stubs", "ai-guides", "omnify")
1017
1122
  ];
1018
1123
  let stubsDir = null;
1019
1124
  for (const pkgPath of omnifyPkgPaths) {
1020
1125
  if (pkgPath.includes("*")) {
1021
- const parentDir = dirname4(dirname4(pkgPath));
1022
- if (existsSync6(parentDir)) {
1126
+ const parentDir = dirname5(dirname5(pkgPath));
1127
+ if (existsSync7(parentDir)) {
1023
1128
  const entries = readdirSync(parentDir);
1024
1129
  for (const entry of entries) {
1025
1130
  if (entry.startsWith("@famgia+omnify@")) {
1026
1131
  const testPath = join(parentDir, entry, "node_modules", "@famgia", "omnify", "stubs", "ai-guides", "omnify");
1027
- if (existsSync6(testPath)) {
1132
+ if (existsSync7(testPath)) {
1028
1133
  stubsDir = testPath;
1029
1134
  break;
1030
1135
  }
1031
1136
  }
1032
1137
  }
1033
1138
  }
1034
- } else if (existsSync6(pkgPath)) {
1139
+ } else if (existsSync7(pkgPath)) {
1035
1140
  stubsDir = pkgPath;
1036
1141
  break;
1037
1142
  }
1038
1143
  }
1039
1144
  if (!stubsDir) {
1040
1145
  try {
1041
- const omnifyPath = dirname4(__require.resolve("@famgia/omnify/package.json", { paths: [rootDir] }));
1146
+ const omnifyPath = dirname5(__require.resolve("@famgia/omnify/package.json", { paths: [rootDir] }));
1042
1147
  const testPath = join(omnifyPath, "stubs", "ai-guides", "omnify");
1043
- if (existsSync6(testPath)) {
1148
+ if (existsSync7(testPath)) {
1044
1149
  stubsDir = testPath;
1045
1150
  }
1046
1151
  } catch {
@@ -1049,13 +1154,13 @@ function copyOmnifyGuides(rootDir) {
1049
1154
  if (!stubsDir) {
1050
1155
  return 0;
1051
1156
  }
1052
- const destDir = resolve6(rootDir, ".claude", "omnify", "guides", "omnify");
1157
+ const destDir = resolve7(rootDir, ".claude", "omnify", "guides", "omnify");
1053
1158
  mkdirSync2(destDir, { recursive: true });
1054
1159
  const files = readdirSync(stubsDir).filter((f) => f.endsWith(".stub"));
1055
1160
  for (const file of files) {
1056
1161
  const srcPath = join(stubsDir, file);
1057
1162
  const destPath = join(destDir, file.replace(".stub", ""));
1058
- const content = readFileSync2(srcPath, "utf8");
1163
+ const content = readFileSync3(srcPath, "utf8");
1059
1164
  writeFileSync3(destPath, content);
1060
1165
  filesWritten++;
1061
1166
  }
@@ -1063,8 +1168,8 @@ function copyOmnifyGuides(rootDir) {
1063
1168
  }
1064
1169
  function generateAIGuides(rootDir, _plugins) {
1065
1170
  let filesWritten = 0;
1066
- const claudeMdPath = resolve6(rootDir, "CLAUDE.md");
1067
- if (!existsSync6(claudeMdPath)) {
1171
+ const claudeMdPath = resolve7(rootDir, "CLAUDE.md");
1172
+ if (!existsSync7(claudeMdPath)) {
1068
1173
  writeFileSync3(claudeMdPath, CLAUDE_MD);
1069
1174
  filesWritten++;
1070
1175
  }
@@ -1078,7 +1183,7 @@ function hasPluginGenerators(plugins) {
1078
1183
  }
1079
1184
  function getExistingMigrationTables(migrationsDir) {
1080
1185
  const existingTables = /* @__PURE__ */ new Set();
1081
- if (!existsSync7(migrationsDir)) {
1186
+ if (!existsSync8(migrationsDir)) {
1082
1187
  return existingTables;
1083
1188
  }
1084
1189
  try {
@@ -1271,13 +1376,13 @@ function schemaChangeToVersionChange(change) {
1271
1376
  function writeGeneratorOutputs(outputs, rootDir) {
1272
1377
  const counts = { migrations: 0, types: 0, models: 0, factories: 0, other: 0 };
1273
1378
  for (const output of outputs) {
1274
- const filePath = resolve7(rootDir, output.path);
1275
- const dir = dirname5(filePath);
1276
- if (!existsSync7(dir)) {
1379
+ const filePath = resolve8(rootDir, output.path);
1380
+ const dir = dirname6(filePath);
1381
+ if (!existsSync8(dir)) {
1277
1382
  mkdirSync3(dir, { recursive: true });
1278
1383
  logger.debug(`Created directory: ${dir}`);
1279
1384
  }
1280
- if (output.skipIfExists && existsSync7(filePath)) {
1385
+ if (output.skipIfExists && existsSync8(filePath)) {
1281
1386
  logger.debug(`Skipped (exists): ${output.path}`);
1282
1387
  continue;
1283
1388
  }
@@ -1337,8 +1442,8 @@ function runDirectGeneration(schemas, config, rootDir, options, changes) {
1337
1442
  }
1338
1443
  if (!options.typesOnly && config.output.laravel) {
1339
1444
  logger.step("Generating Laravel migrations...");
1340
- const migrationsDir = resolve7(rootDir, config.output.laravel.migrationsPath);
1341
- if (!existsSync7(migrationsDir)) {
1445
+ const migrationsDir = resolve8(rootDir, config.output.laravel.migrationsPath);
1446
+ if (!existsSync8(migrationsDir)) {
1342
1447
  mkdirSync3(migrationsDir, { recursive: true });
1343
1448
  logger.debug(`Created directory: ${migrationsDir}`);
1344
1449
  }
@@ -1360,7 +1465,7 @@ function runDirectGeneration(schemas, config, rootDir, options, changes) {
1360
1465
  logger.debug(`Skipped CREATE for ${tableName} (already exists)`);
1361
1466
  continue;
1362
1467
  }
1363
- const filePath = resolve7(migrationsDir, migration.fileName);
1468
+ const filePath = resolve8(migrationsDir, migration.fileName);
1364
1469
  writeFileSync4(filePath, migration.content);
1365
1470
  logger.debug(`Created: ${migration.fileName}`);
1366
1471
  migrationsGenerated++;
@@ -1369,7 +1474,7 @@ function runDirectGeneration(schemas, config, rootDir, options, changes) {
1369
1474
  if (alterChanges.length > 0) {
1370
1475
  const alterMigrations = generateMigrationsFromChanges(alterChanges);
1371
1476
  for (const migration of alterMigrations) {
1372
- const filePath = resolve7(migrationsDir, migration.fileName);
1477
+ const filePath = resolve8(migrationsDir, migration.fileName);
1373
1478
  writeFileSync4(filePath, migration.content);
1374
1479
  logger.debug(`Created: ${migration.fileName}`);
1375
1480
  migrationsGenerated++;
@@ -1381,12 +1486,12 @@ function runDirectGeneration(schemas, config, rootDir, options, changes) {
1381
1486
  logger.step("Generating Laravel models...");
1382
1487
  const modelsPath = config.output.laravel.modelsPath;
1383
1488
  const baseModelsPath = config.output.laravel.baseModelsPath ?? `${modelsPath}/OmnifyBase`;
1384
- const modelsDir = resolve7(rootDir, modelsPath);
1385
- const baseModelsDir = resolve7(rootDir, baseModelsPath);
1386
- if (!existsSync7(modelsDir)) {
1489
+ const modelsDir = resolve8(rootDir, modelsPath);
1490
+ const baseModelsDir = resolve8(rootDir, baseModelsPath);
1491
+ if (!existsSync8(modelsDir)) {
1387
1492
  mkdirSync3(modelsDir, { recursive: true });
1388
1493
  }
1389
- if (!existsSync7(baseModelsDir)) {
1494
+ if (!existsSync8(baseModelsDir)) {
1390
1495
  mkdirSync3(baseModelsDir, { recursive: true });
1391
1496
  }
1392
1497
  const providersPath = config.output.laravel.providersPath ?? "app/Providers";
@@ -1397,12 +1502,12 @@ function runDirectGeneration(schemas, config, rootDir, options, changes) {
1397
1502
  customTypes: customTypesMap
1398
1503
  });
1399
1504
  for (const model of models) {
1400
- const filePath = resolve7(rootDir, getModelPath(model));
1401
- const fileDir = dirname5(filePath);
1402
- if (!existsSync7(fileDir)) {
1505
+ const filePath = resolve8(rootDir, getModelPath(model));
1506
+ const fileDir = dirname6(filePath);
1507
+ if (!existsSync8(fileDir)) {
1403
1508
  mkdirSync3(fileDir, { recursive: true });
1404
1509
  }
1405
- if (!model.overwrite && existsSync7(filePath)) {
1510
+ if (!model.overwrite && existsSync8(filePath)) {
1406
1511
  logger.debug(`Skipped (exists): ${getModelPath(model)}`);
1407
1512
  continue;
1408
1513
  }
@@ -1415,20 +1520,20 @@ function runDirectGeneration(schemas, config, rootDir, options, changes) {
1415
1520
  if (!options.typesOnly && config.output.laravel?.factoriesPath) {
1416
1521
  logger.step("Generating Laravel factories...");
1417
1522
  const factoriesPath = config.output.laravel.factoriesPath;
1418
- const factoriesDir = resolve7(rootDir, factoriesPath);
1419
- if (!existsSync7(factoriesDir)) {
1523
+ const factoriesDir = resolve8(rootDir, factoriesPath);
1524
+ if (!existsSync8(factoriesDir)) {
1420
1525
  mkdirSync3(factoriesDir, { recursive: true });
1421
1526
  }
1422
1527
  const factories = generateFactories(schemas, {
1423
1528
  factoryPath: factoriesPath
1424
1529
  });
1425
1530
  for (const factory of factories) {
1426
- const filePath = resolve7(rootDir, getFactoryPath(factory));
1427
- const fileDir = dirname5(filePath);
1428
- if (!existsSync7(fileDir)) {
1531
+ const filePath = resolve8(rootDir, getFactoryPath(factory));
1532
+ const fileDir = dirname6(filePath);
1533
+ if (!existsSync8(fileDir)) {
1429
1534
  mkdirSync3(fileDir, { recursive: true });
1430
1535
  }
1431
- if (!factory.overwrite && existsSync7(filePath)) {
1536
+ if (!factory.overwrite && existsSync8(filePath)) {
1432
1537
  logger.debug(`Skipped (exists): ${getFactoryPath(factory)}`);
1433
1538
  continue;
1434
1539
  }
@@ -1441,15 +1546,15 @@ function runDirectGeneration(schemas, config, rootDir, options, changes) {
1441
1546
  if (!options.migrationsOnly && config.output.typescript) {
1442
1547
  logger.step("Generating TypeScript types...");
1443
1548
  const tsConfig = config.output.typescript;
1444
- const basePath = resolve7(rootDir, tsConfig.path);
1445
- const schemasDir = resolve7(basePath, tsConfig.schemasDir ?? "schemas");
1446
- const enumDir = resolve7(basePath, tsConfig.enumDir ?? "enum");
1549
+ const basePath = resolve8(rootDir, tsConfig.path);
1550
+ const schemasDir = resolve8(basePath, tsConfig.schemasDir ?? "schemas");
1551
+ const enumDir = resolve8(basePath, tsConfig.enumDir ?? "enum");
1447
1552
  const enumImportPrefix = relative(schemasDir, enumDir).replace(/\\/g, "/");
1448
- if (!existsSync7(schemasDir)) {
1553
+ if (!existsSync8(schemasDir)) {
1449
1554
  mkdirSync3(schemasDir, { recursive: true });
1450
1555
  logger.debug(`Created directory: ${schemasDir}`);
1451
1556
  }
1452
- if (!existsSync7(enumDir)) {
1557
+ if (!existsSync8(enumDir)) {
1453
1558
  mkdirSync3(enumDir, { recursive: true });
1454
1559
  logger.debug(`Created directory: ${enumDir}`);
1455
1560
  }
@@ -1465,12 +1570,12 @@ function runDirectGeneration(schemas, config, rootDir, options, changes) {
1465
1570
  });
1466
1571
  for (const file of typeFiles) {
1467
1572
  const outputDir = file.category === "enum" ? enumDir : schemasDir;
1468
- const filePath = resolve7(outputDir, file.filePath);
1469
- const fileDir = dirname5(filePath);
1470
- if (!existsSync7(fileDir)) {
1573
+ const filePath = resolve8(outputDir, file.filePath);
1574
+ const fileDir = dirname6(filePath);
1575
+ if (!existsSync8(fileDir)) {
1471
1576
  mkdirSync3(fileDir, { recursive: true });
1472
1577
  }
1473
- if (!file.overwrite && existsSync7(filePath)) {
1578
+ if (!file.overwrite && existsSync8(filePath)) {
1474
1579
  logger.debug(`Skipped (exists): ${file.filePath}`);
1475
1580
  continue;
1476
1581
  }
@@ -1501,9 +1606,9 @@ async function runGenerate(options) {
1501
1606
  logger.header("Generating Outputs");
1502
1607
  logger.debug("Loading configuration...");
1503
1608
  const { config, configPath } = await loadConfig();
1504
- const rootDir = configPath ? dirname5(configPath) : process.cwd();
1609
+ const rootDir = configPath ? dirname6(configPath) : process.cwd();
1505
1610
  validateConfig(config, rootDir);
1506
- const schemaPath = resolve7(rootDir, config.schemasDir);
1611
+ const schemaPath = resolve8(rootDir, config.schemasDir);
1507
1612
  logger.step(`Loading schemas from ${schemaPath}`);
1508
1613
  let schemas = await loadSchemas3(schemaPath);
1509
1614
  logger.debug(`Found ${Object.keys(schemas).length} schema(s) in main directory`);
@@ -1512,9 +1617,9 @@ async function runGenerate(options) {
1512
1617
  if (additionalPaths.length > 0) {
1513
1618
  logger.step(`Loading schemas from ${additionalPaths.length} additional path(s)`);
1514
1619
  for (const entry of additionalPaths) {
1515
- const absolutePath = resolve7(rootDir, entry.path);
1620
+ const absolutePath = resolve8(rootDir, entry.path);
1516
1621
  logger.debug(` Checking: ${entry.path} \u2192 ${absolutePath}`);
1517
- if (existsSync7(absolutePath)) {
1622
+ if (existsSync8(absolutePath)) {
1518
1623
  let packageSchemas = await loadSchemas3(absolutePath, { skipPartialResolution: true });
1519
1624
  if (entry.output) {
1520
1625
  const schemasWithOutput = {};
@@ -1569,12 +1674,12 @@ async function runGenerate(options) {
1569
1674
  process.exit(2);
1570
1675
  }
1571
1676
  logger.step("Checking for changes...");
1572
- const lockPath = resolve7(rootDir, config.lockFilePath);
1677
+ const lockPath = resolve8(rootDir, config.lockFilePath);
1573
1678
  const existingLock = await readLockFile(lockPath);
1574
1679
  const currentSnapshots = await buildSchemaSnapshots(schemas);
1575
1680
  const v2Lock = existingLock && isLockFileV2(existingLock) ? existingLock : null;
1576
1681
  const comparison = compareSchemasDeep(currentSnapshots, v2Lock);
1577
- const chainFilePath = resolve7(rootDir, VERSION_CHAIN_FILE);
1682
+ const chainFilePath = resolve8(rootDir, VERSION_CHAIN_FILE);
1578
1683
  const versionChain = await readVersionChain(chainFilePath);
1579
1684
  if (versionChain && comparison.hasChanges) {
1580
1685
  const schemaActions = [];
@@ -1611,7 +1716,7 @@ async function runGenerate(options) {
1611
1716
  }
1612
1717
  }
1613
1718
  if (existingLock && config.output.laravel?.migrationsPath) {
1614
- const migrationsDir = resolve7(rootDir, config.output.laravel.migrationsPath);
1719
+ const migrationsDir = resolve8(rootDir, config.output.laravel.migrationsPath);
1615
1720
  const migrationValidation = await validateMigrations(existingLock, migrationsDir);
1616
1721
  if (!migrationValidation.valid) {
1617
1722
  logger.newline();
@@ -1735,15 +1840,15 @@ async function runGenerate(options) {
1735
1840
  if (!options.migrationsOnly && config.output.typescript && typesGenerated === 0) {
1736
1841
  logger.step("Generating TypeScript types...");
1737
1842
  const tsConfig2 = config.output.typescript;
1738
- const basePath2 = resolve7(rootDir, tsConfig2.path);
1739
- const schemasDir2 = resolve7(basePath2, tsConfig2.schemasDir ?? "schemas");
1740
- const enumDir2 = resolve7(basePath2, tsConfig2.enumDir ?? "enum");
1843
+ const basePath2 = resolve8(rootDir, tsConfig2.path);
1844
+ const schemasDir2 = resolve8(basePath2, tsConfig2.schemasDir ?? "schemas");
1845
+ const enumDir2 = resolve8(basePath2, tsConfig2.enumDir ?? "enum");
1741
1846
  const enumImportPrefix2 = relative(schemasDir2, enumDir2).replace(/\\/g, "/");
1742
- if (!existsSync7(schemasDir2)) {
1847
+ if (!existsSync8(schemasDir2)) {
1743
1848
  mkdirSync3(schemasDir2, { recursive: true });
1744
1849
  logger.debug(`Created directory: ${schemasDir2}`);
1745
1850
  }
1746
- if (!existsSync7(enumDir2)) {
1851
+ if (!existsSync8(enumDir2)) {
1747
1852
  mkdirSync3(enumDir2, { recursive: true });
1748
1853
  logger.debug(`Created directory: ${enumDir2}`);
1749
1854
  }
@@ -1759,12 +1864,12 @@ async function runGenerate(options) {
1759
1864
  });
1760
1865
  for (const file of typeFiles) {
1761
1866
  const outputDir2 = file.category === "enum" ? enumDir2 : schemasDir2;
1762
- const filePath = resolve7(outputDir2, file.filePath);
1763
- const fileDir = dirname5(filePath);
1764
- if (!existsSync7(fileDir)) {
1867
+ const filePath = resolve8(outputDir2, file.filePath);
1868
+ const fileDir = dirname6(filePath);
1869
+ if (!existsSync8(fileDir)) {
1765
1870
  mkdirSync3(fileDir, { recursive: true });
1766
1871
  }
1767
- if (!file.overwrite && existsSync7(filePath)) {
1872
+ if (!file.overwrite && existsSync8(filePath)) {
1768
1873
  logger.debug(`Skipped (exists): ${file.filePath}`);
1769
1874
  continue;
1770
1875
  }