@geekmidas/cli 0.22.0 → 0.24.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/dist/index.cjs CHANGED
@@ -1,8 +1,8 @@
1
1
  #!/usr/bin/env -S npx tsx
2
2
  const require_chunk = require('./chunk-CUT6urMc.cjs');
3
3
  const require_workspace = require('./workspace-iWgBlX6h.cjs');
4
- const require_config = require('./config-CxrLu8ia.cjs');
5
- const require_openapi = require('./openapi-DfpxS0xv.cjs');
4
+ const require_config = require('./config-CTftATBX.cjs');
5
+ const require_openapi = require('./openapi-BrhkPKM7.cjs');
6
6
  const require_storage = require('./storage-BPRgh3DU.cjs');
7
7
  const require_dokploy_api = require('./dokploy-api-C5czOZoc.cjs');
8
8
  const require_openapi_react_query = require('./openapi-react-query-DvNpdDpM.cjs');
@@ -27,7 +27,7 @@ const node_module = require_chunk.__toESM(require("node:module"));
27
27
 
28
28
  //#region package.json
29
29
  var name = "@geekmidas/cli";
30
- var version = "0.22.0";
30
+ var version = "0.24.0";
31
31
  var description = "CLI tools for building Lambda handlers, server applications, and generating OpenAPI specs";
32
32
  var private$1 = false;
33
33
  var type = "module";
@@ -80,6 +80,7 @@ var dependencies = {
80
80
  "commander": "^12.1.0",
81
81
  "dotenv": "~17.2.3",
82
82
  "fast-glob": "^3.3.2",
83
+ "hono": "~4.8.0",
83
84
  "lodash.kebabcase": "^4.1.1",
84
85
  "openapi-typescript": "^7.4.2",
85
86
  "prompts": "~2.4.2"
@@ -976,10 +977,10 @@ function normalizeStudioConfig(config) {
976
977
  * Normalize hooks configuration
977
978
  * @internal Exported for testing
978
979
  */
979
- function normalizeHooksConfig(config) {
980
+ function normalizeHooksConfig(config, cwd = process.cwd()) {
980
981
  if (!config?.server) return void 0;
981
982
  const serverPath = config.server.endsWith(".ts") ? config.server : `${config.server}.ts`;
982
- const resolvedPath = (0, node_path.resolve)(process.cwd(), serverPath);
983
+ const resolvedPath = (0, node_path.resolve)(cwd, serverPath);
983
984
  return { serverHooksPath: resolvedPath };
984
985
  }
985
986
  /**
@@ -1013,14 +1014,32 @@ function getProductionConfigFromGkm(config) {
1013
1014
  async function devCommand(options) {
1014
1015
  const defaultEnv = loadEnvFiles(".env");
1015
1016
  if (defaultEnv.loaded.length > 0) logger$8.log(`📦 Loaded env: ${defaultEnv.loaded.join(", ")}`);
1016
- const loadedConfig = await require_config.loadWorkspaceConfig();
1017
- if (loadedConfig.type === "workspace") {
1018
- logger$8.log("📦 Detected workspace configuration");
1019
- return workspaceDevCommand(loadedConfig.workspace, options);
1017
+ const appName = require_config.getAppNameFromCwd();
1018
+ let config;
1019
+ let appRoot = process.cwd();
1020
+ if (appName) try {
1021
+ const appConfig = await require_config.loadAppConfig();
1022
+ config = appConfig.gkmConfig;
1023
+ appRoot = appConfig.appRoot;
1024
+ logger$8.log(`📦 Running app: ${appConfig.appName}`);
1025
+ } catch {
1026
+ const loadedConfig = await require_config.loadWorkspaceConfig();
1027
+ if (loadedConfig.type === "workspace") {
1028
+ logger$8.log("📦 Detected workspace configuration");
1029
+ return workspaceDevCommand(loadedConfig.workspace, options);
1030
+ }
1031
+ config = loadedConfig.raw;
1032
+ }
1033
+ else {
1034
+ const loadedConfig = await require_config.loadWorkspaceConfig();
1035
+ if (loadedConfig.type === "workspace") {
1036
+ logger$8.log("📦 Detected workspace configuration");
1037
+ return workspaceDevCommand(loadedConfig.workspace, options);
1038
+ }
1039
+ config = loadedConfig.raw;
1020
1040
  }
1021
- const config = loadedConfig.raw;
1022
1041
  if (config.env) {
1023
- const { loaded, missing } = loadEnvFiles(config.env);
1042
+ const { loaded, missing } = loadEnvFiles(config.env, appRoot);
1024
1043
  if (loaded.length > 0) logger$8.log(`📦 Loaded env: ${loaded.join(", ")}`);
1025
1044
  if (missing.length > 0) logger$8.warn(`⚠️ Missing env files: ${missing.join(", ")}`);
1026
1045
  }
@@ -1037,7 +1056,7 @@ async function devCommand(options) {
1037
1056
  if (telescope) logger$8.log(`🔭 Telescope enabled at ${telescope.path}`);
1038
1057
  const studio = normalizeStudioConfig(config.studio);
1039
1058
  if (studio) logger$8.log(`🗄️ Studio enabled at ${studio.path}`);
1040
- const hooks = normalizeHooksConfig(config.hooks);
1059
+ const hooks = normalizeHooksConfig(config.hooks, appRoot);
1041
1060
  if (hooks) logger$8.log(`🪝 Server hooks enabled from ${config.hooks?.server}`);
1042
1061
  const openApiConfig = require_openapi.resolveOpenApiConfig(config);
1043
1062
  const enableOpenApi = openApiConfig.enabled || resolved.enableOpenApi;
@@ -1051,10 +1070,10 @@ async function devCommand(options) {
1051
1070
  studio,
1052
1071
  hooks
1053
1072
  };
1054
- await buildServer(config, buildContext, resolved.providers[0], enableOpenApi);
1073
+ await buildServer(config, buildContext, resolved.providers[0], enableOpenApi, appRoot);
1055
1074
  if (enableOpenApi) await require_openapi.generateOpenApi(config);
1056
1075
  const runtime = config.runtime ?? "node";
1057
- const devServer = new DevServer(resolved.providers[0], options.port || 3e3, options.portExplicit ?? false, enableOpenApi, telescope, studio, runtime);
1076
+ const devServer = new DevServer(resolved.providers[0], options.port || 3e3, options.portExplicit ?? false, enableOpenApi, telescope, studio, runtime, appRoot);
1058
1077
  await devServer.start();
1059
1078
  const envParserFile = config.envParser.split("#")[0] ?? config.envParser;
1060
1079
  const loggerFile = config.logger.split("#")[0] ?? config.logger;
@@ -1072,7 +1091,7 @@ async function devCommand(options) {
1072
1091
  const normalizedPatterns = watchPatterns.map((p) => p.startsWith("./") ? p.slice(2) : p);
1073
1092
  logger$8.log(`👀 Watching for changes in: ${normalizedPatterns.join(", ")}`);
1074
1093
  const resolvedFiles = await (0, fast_glob.default)(normalizedPatterns, {
1075
- cwd: process.cwd(),
1094
+ cwd: appRoot,
1076
1095
  absolute: false,
1077
1096
  onlyFiles: true
1078
1097
  });
@@ -1085,7 +1104,7 @@ async function devCommand(options) {
1085
1104
  ignored: /(^|[/\\])\../,
1086
1105
  persistent: true,
1087
1106
  ignoreInitial: true,
1088
- cwd: process.cwd()
1107
+ cwd: appRoot
1089
1108
  });
1090
1109
  watcher.on("ready", () => {
1091
1110
  logger$8.log("🔍 File watcher ready");
@@ -1100,7 +1119,7 @@ async function devCommand(options) {
1100
1119
  rebuildTimeout = setTimeout(async () => {
1101
1120
  try {
1102
1121
  logger$8.log("🔄 Rebuilding...");
1103
- await buildServer(config, buildContext, resolved.providers[0], enableOpenApi);
1122
+ await buildServer(config, buildContext, resolved.providers[0], enableOpenApi, appRoot);
1104
1123
  if (enableOpenApi) await require_openapi.generateOpenApi(config, { silent: true });
1105
1124
  logger$8.log("✅ Rebuild complete, restarting server...");
1106
1125
  await devServer.restart();
@@ -1322,11 +1341,25 @@ async function workspaceDevCommand(workspace, options) {
1322
1341
  const deps = app.dependencies.length > 0 ? ` (depends on: ${app.dependencies.join(", ")})` : "";
1323
1342
  logger$8.log(` ${app.type === "backend" ? "🔧" : "🌐"} ${appName} → http://localhost:${app.port}${deps}`);
1324
1343
  }
1344
+ const configFiles = [
1345
+ "gkm.config.ts",
1346
+ "gkm.config.js",
1347
+ "gkm.config.json"
1348
+ ];
1349
+ let configPath = "";
1350
+ for (const file of configFiles) {
1351
+ const fullPath = (0, node_path.join)(workspace.root, file);
1352
+ if ((0, node_fs.existsSync)(fullPath)) {
1353
+ configPath = fullPath;
1354
+ break;
1355
+ }
1356
+ }
1325
1357
  const turboEnv = {
1326
1358
  ...process.env,
1327
1359
  ...secretsEnv,
1328
1360
  ...dependencyEnv,
1329
- NODE_ENV: "development"
1361
+ NODE_ENV: "development",
1362
+ ...configPath ? { GKM_CONFIG_PATH: configPath } : {}
1330
1363
  };
1331
1364
  logger$8.log("\n🏃 Starting turbo run dev...\n");
1332
1365
  const turboProcess = (0, node_child_process.spawn)("pnpm", [
@@ -1429,18 +1462,18 @@ async function workspaceDevCommand(workspace, options) {
1429
1462
  });
1430
1463
  });
1431
1464
  }
1432
- async function buildServer(config, context, provider, enableOpenApi) {
1465
+ async function buildServer(config, context, provider, enableOpenApi, appRoot = process.cwd()) {
1433
1466
  const endpointGenerator = new require_openapi.EndpointGenerator();
1434
1467
  const functionGenerator = new FunctionGenerator();
1435
1468
  const cronGenerator = new CronGenerator();
1436
1469
  const subscriberGenerator = new SubscriberGenerator();
1437
1470
  const [allEndpoints, allFunctions, allCrons, allSubscribers] = await Promise.all([
1438
- endpointGenerator.load(config.routes),
1439
- config.functions ? functionGenerator.load(config.functions) : [],
1440
- config.crons ? cronGenerator.load(config.crons) : [],
1441
- config.subscribers ? subscriberGenerator.load(config.subscribers) : []
1471
+ endpointGenerator.load(config.routes, appRoot),
1472
+ config.functions ? functionGenerator.load(config.functions, appRoot) : [],
1473
+ config.crons ? cronGenerator.load(config.crons, appRoot) : [],
1474
+ config.subscribers ? subscriberGenerator.load(config.subscribers, appRoot) : []
1442
1475
  ]);
1443
- const outputDir = (0, node_path.join)(process.cwd(), ".gkm", provider);
1476
+ const outputDir = (0, node_path.join)(appRoot, ".gkm", provider);
1444
1477
  await (0, node_fs_promises.mkdir)(outputDir, { recursive: true });
1445
1478
  await Promise.all([
1446
1479
  endpointGenerator.build(context, allEndpoints, outputDir, {
@@ -1456,7 +1489,7 @@ var DevServer = class {
1456
1489
  serverProcess = null;
1457
1490
  isRunning = false;
1458
1491
  actualPort;
1459
- constructor(provider, requestedPort, portExplicit, enableOpenApi, telescope, studio, runtime = "node") {
1492
+ constructor(provider, requestedPort, portExplicit, enableOpenApi, telescope, studio, runtime = "node", appRoot = process.cwd()) {
1460
1493
  this.provider = provider;
1461
1494
  this.requestedPort = requestedPort;
1462
1495
  this.portExplicit = portExplicit;
@@ -1464,6 +1497,7 @@ var DevServer = class {
1464
1497
  this.telescope = telescope;
1465
1498
  this.studio = studio;
1466
1499
  this.runtime = runtime;
1500
+ this.appRoot = appRoot;
1467
1501
  this.actualPort = requestedPort;
1468
1502
  }
1469
1503
  async start() {
@@ -1476,7 +1510,7 @@ var DevServer = class {
1476
1510
  this.actualPort = await findAvailablePort(this.requestedPort);
1477
1511
  if (this.actualPort !== this.requestedPort) logger$8.log(`ℹ️ Port ${this.requestedPort} was in use, using port ${this.actualPort} instead`);
1478
1512
  }
1479
- const serverEntryPath = (0, node_path.join)(process.cwd(), ".gkm", this.provider, "server.ts");
1513
+ const serverEntryPath = (0, node_path.join)(this.appRoot, ".gkm", this.provider, "server.ts");
1480
1514
  await this.createServerEntry();
1481
1515
  logger$8.log(`\n✨ Starting server on port ${this.actualPort}...`);
1482
1516
  this.serverProcess = (0, node_child_process.spawn)("npx", [
@@ -1544,7 +1578,7 @@ var DevServer = class {
1544
1578
  async createServerEntry() {
1545
1579
  const { writeFile: writeFile$9 } = await import("node:fs/promises");
1546
1580
  const { relative: relative$7, dirname: dirname$7 } = await import("node:path");
1547
- const serverPath = (0, node_path.join)(process.cwd(), ".gkm", this.provider, "server.ts");
1581
+ const serverPath = (0, node_path.join)(this.appRoot, ".gkm", this.provider, "server.ts");
1548
1582
  const relativeAppPath = relative$7(dirname$7(serverPath), (0, node_path.join)(dirname$7(serverPath), "app.js"));
1549
1583
  const serveCode = this.runtime === "bun" ? `Bun.serve({
1550
1584
  port,
@@ -3069,7 +3103,7 @@ async function workspaceDockerCommand(workspace, options) {
3069
3103
  * Get app name from package.json in the current working directory
3070
3104
  * Used for Dokploy app/project naming
3071
3105
  */
3072
- function getAppNameFromCwd() {
3106
+ function getAppNameFromCwd$1() {
3073
3107
  const packageJsonPath = (0, node_path.join)(process.cwd(), "package.json");
3074
3108
  if (!(0, node_fs.existsSync)(packageJsonPath)) return void 0;
3075
3109
  try {
@@ -3187,7 +3221,7 @@ async function deployDocker(options) {
3187
3221
  */
3188
3222
  function resolveDockerConfig(config) {
3189
3223
  const projectName = getAppNameFromPackageJson() ?? "app";
3190
- const appName = getAppNameFromCwd() ?? projectName;
3224
+ const appName = getAppNameFromCwd$1() ?? projectName;
3191
3225
  const imageName = config.docker?.imageName ?? appName;
3192
3226
  return {
3193
3227
  registry: config.docker?.registry,
@@ -4223,7 +4257,14 @@ function rotateServicePassword(secrets, service) {
4223
4257
  //#endregion
4224
4258
  //#region src/init/versions.ts
4225
4259
  const require$1 = (0, node_module.createRequire)(require("url").pathToFileURL(__filename).href);
4226
- const pkg = require$1("../package.json");
4260
+ function loadPackageJson() {
4261
+ try {
4262
+ return require$1("../package.json");
4263
+ } catch {
4264
+ return require$1("../../package.json");
4265
+ }
4266
+ }
4267
+ const pkg = loadPackageJson();
4227
4268
  /**
4228
4269
  * CLI version from package.json (used for scaffolded projects)
4229
4270
  */
@@ -4753,7 +4794,7 @@ function generateDockerFiles(options, template, dbApps) {
4753
4794
  retries: 5`);
4754
4795
  volumes.push(" rabbitmq_data:");
4755
4796
  }
4756
- if (options.services.mail) services.push(` mailpit:
4797
+ if (options.services?.mail) services.push(` mailpit:
4757
4798
  image: axllent/mailpit:latest
4758
4799
  container_name: ${options.name}-mailpit
4759
4800
  restart: unless-stopped