@korajs/cli 1.0.0-beta.1 → 1.0.0-beta.10

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 (74) hide show
  1. package/dist/bin.cjs +593 -290
  2. package/dist/bin.cjs.map +1 -1
  3. package/dist/bin.js +122 -35
  4. package/dist/bin.js.map +1 -1
  5. package/dist/{chunk-EOWLAAIV.js → chunk-4IKCHRJ6.js} +273 -57
  6. package/dist/chunk-4IKCHRJ6.js.map +1 -0
  7. package/dist/{chunk-B5YS4STN.js → chunk-G2PBYMMA.js} +2 -2
  8. package/dist/{chunk-B5YS4STN.js.map → chunk-G2PBYMMA.js.map} +1 -1
  9. package/dist/{chunk-BWTKRKNJ.js → chunk-Z7GCXMGW.js} +9 -5
  10. package/dist/chunk-Z7GCXMGW.js.map +1 -0
  11. package/dist/create.cjs +8 -4
  12. package/dist/create.cjs.map +1 -1
  13. package/dist/create.js +2 -2
  14. package/dist/index.cjs +389 -166
  15. package/dist/index.cjs.map +1 -1
  16. package/dist/index.d.cts +58 -1
  17. package/dist/index.d.ts +58 -1
  18. package/dist/index.js +12 -2
  19. package/package.json +8 -8
  20. package/templates/react-basic/README.md.hbs +1 -1
  21. package/templates/react-basic/src/main.tsx +1 -1
  22. package/templates/react-basic/src/vite-env.d.ts +1 -0
  23. package/templates/react-basic/vite.config.ts +7 -4
  24. package/templates/react-sync/README.md.hbs +6 -5
  25. package/templates/react-sync/server.ts +46 -3
  26. package/templates/react-sync/src/main.tsx +1 -1
  27. package/templates/react-sync/src/vite-env.d.ts +1 -0
  28. package/templates/react-sync/vite.config.ts +14 -4
  29. package/templates/react-tailwind/README.md.hbs +1 -1
  30. package/templates/react-tailwind/src/main.tsx +1 -1
  31. package/templates/react-tailwind/src/vite-env.d.ts +1 -0
  32. package/templates/react-tailwind/vite.config.ts +7 -4
  33. package/templates/react-tailwind-sync/README.md.hbs +6 -5
  34. package/templates/react-tailwind-sync/server.ts +46 -3
  35. package/templates/react-tailwind-sync/src/main.tsx +1 -1
  36. package/templates/react-tailwind-sync/src/vite-env.d.ts +1 -0
  37. package/templates/react-tailwind-sync/vite.config.ts +14 -4
  38. package/templates/svelte-basic/README.md.hbs +1 -1
  39. package/templates/svelte-basic/src/main.ts +1 -1
  40. package/templates/svelte-basic/vite.config.ts +4 -2
  41. package/templates/svelte-sync/README.md.hbs +6 -5
  42. package/templates/svelte-sync/server.ts +46 -3
  43. package/templates/svelte-sync/src/main.ts +1 -1
  44. package/templates/svelte-sync/src/vite-env.d.ts +1 -0
  45. package/templates/svelte-sync/vite.config.ts +11 -2
  46. package/templates/svelte-tailwind/README.md.hbs +1 -1
  47. package/templates/svelte-tailwind/src/main.ts +1 -1
  48. package/templates/svelte-tailwind/vite.config.ts +4 -2
  49. package/templates/svelte-tailwind-sync/README.md.hbs +6 -5
  50. package/templates/svelte-tailwind-sync/server.ts +46 -3
  51. package/templates/svelte-tailwind-sync/src/main.ts +1 -1
  52. package/templates/svelte-tailwind-sync/src/vite-env.d.ts +1 -0
  53. package/templates/svelte-tailwind-sync/vite.config.ts +11 -2
  54. package/templates/tauri-react/server.ts +44 -1
  55. package/templates/tauri-react/src/AppShell.tsx +1 -1
  56. package/templates/tauri-react/src/vite-env.d.ts +1 -0
  57. package/templates/vue-basic/README.md.hbs +1 -1
  58. package/templates/vue-basic/src/main.ts +1 -1
  59. package/templates/vue-basic/vite.config.ts +4 -2
  60. package/templates/vue-sync/README.md.hbs +6 -5
  61. package/templates/vue-sync/server.ts +46 -3
  62. package/templates/vue-sync/src/main.ts +1 -1
  63. package/templates/vue-sync/src/vite-env.d.ts +1 -0
  64. package/templates/vue-sync/vite.config.ts +11 -2
  65. package/templates/vue-tailwind/README.md.hbs +1 -1
  66. package/templates/vue-tailwind/src/main.ts +1 -1
  67. package/templates/vue-tailwind/vite.config.ts +4 -2
  68. package/templates/vue-tailwind-sync/README.md.hbs +6 -5
  69. package/templates/vue-tailwind-sync/server.ts +46 -3
  70. package/templates/vue-tailwind-sync/src/main.ts +1 -1
  71. package/templates/vue-tailwind-sync/src/vite-env.d.ts +1 -0
  72. package/templates/vue-tailwind-sync/vite.config.ts +11 -2
  73. package/dist/chunk-BWTKRKNJ.js.map +0 -1
  74. package/dist/chunk-EOWLAAIV.js.map +0 -1
package/dist/bin.js CHANGED
@@ -1,18 +1,19 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
3
  createCommand
4
- } from "./chunk-BWTKRKNJ.js";
4
+ } from "./chunk-Z7GCXMGW.js";
5
5
  import {
6
+ agentsCommand,
6
7
  deployCommand,
7
8
  generateTypes
8
- } from "./chunk-EOWLAAIV.js";
9
+ } from "./chunk-4IKCHRJ6.js";
9
10
  import {
10
11
  DevServerError,
11
12
  InvalidProjectError,
12
13
  SchemaNotFoundError,
13
14
  createLogger,
14
15
  promptConfirm
15
- } from "./chunk-B5YS4STN.js";
16
+ } from "./chunk-G2PBYMMA.js";
16
17
  import {
17
18
  loadSchemaDefinition
18
19
  } from "./chunk-6C4BHSRA.js";
@@ -361,6 +362,7 @@ var compactCommand = defineCommand2({
361
362
  });
362
363
 
363
364
  // src/commands/dev/dev-command.ts
365
+ import { existsSync, readFileSync } from "fs";
364
366
  import { access as access2 } from "fs/promises";
365
367
  import { join as join4 } from "path";
366
368
  import { resolve as resolve2 } from "path";
@@ -371,6 +373,7 @@ import { spawn as spawnChild } from "child_process";
371
373
  var ProcessManager = class {
372
374
  processes = /* @__PURE__ */ new Map();
373
375
  spawn(config) {
376
+ this.processes.get(config.label)?.child.kill("SIGTERM");
374
377
  const options = {
375
378
  cwd: config.cwd,
376
379
  env: { ...process.env, ...config.env },
@@ -414,6 +417,20 @@ var ProcessManager = class {
414
417
  hasRunning() {
415
418
  return this.processes.size > 0;
416
419
  }
420
+ async restart(config) {
421
+ await this.stop(config.label);
422
+ this.spawn(config);
423
+ }
424
+ async stop(label) {
425
+ const running = this.processes.get(label);
426
+ if (!running) return;
427
+ running.child.kill("SIGTERM");
428
+ await Promise.race([running.exitPromise, delay(5e3)]);
429
+ const remaining = this.processes.get(label);
430
+ if (!remaining) return;
431
+ remaining.child.kill("SIGKILL");
432
+ await remaining.exitPromise;
433
+ }
417
434
  async shutdownAll() {
418
435
  const running = Array.from(this.processes.values());
419
436
  if (running.length === 0) return;
@@ -466,6 +483,7 @@ var SchemaWatcher = class {
466
483
  debounceMs;
467
484
  watcher = null;
468
485
  debounceTimer = null;
486
+ schemaVersion = null;
469
487
  start() {
470
488
  if (this.watcher) return;
471
489
  this.watcher = watch(this.config.schemaPath, () => {
@@ -474,6 +492,9 @@ var SchemaWatcher = class {
474
492
  this.watcher.on("error", (error) => {
475
493
  this.config.onError?.(toError(error));
476
494
  });
495
+ void this.refreshSchemaVersion().catch((error) => {
496
+ this.config.onError?.(toError(error));
497
+ });
477
498
  }
478
499
  stop() {
479
500
  if (this.debounceTimer) {
@@ -497,6 +518,15 @@ var SchemaWatcher = class {
497
518
  const args = hasTsx ? ["--import", "tsx", koraBinJs, "generate", "types", "--schema", this.config.schemaPath] : [koraBinJs, "generate", "types", "--schema", this.config.schemaPath];
498
519
  await spawnCommand(command, args, this.config.projectRoot);
499
520
  this.config.onRegenerate?.();
521
+ await this.refreshSchemaVersion();
522
+ }
523
+ async refreshSchemaVersion() {
524
+ const schema = await loadSchemaDefinition(this.config.schemaPath, this.config.projectRoot);
525
+ const previous = this.schemaVersion;
526
+ this.schemaVersion = schema.version;
527
+ if (previous !== null && previous !== schema.version) {
528
+ this.config.onSchemaVersionChange?.({ previous, next: schema.version });
529
+ }
500
530
  }
501
531
  scheduleRegeneration() {
502
532
  if (this.debounceTimer) {
@@ -581,6 +611,7 @@ var devCommand = defineCommand3({
581
611
  if (!projectRoot) {
582
612
  throw new InvalidProjectError(process.cwd());
583
613
  }
614
+ loadProjectEnv(projectRoot);
584
615
  const config = await loadKoraConfig(projectRoot);
585
616
  const vitePort = typeof args.port === "string" ? args.port : String(config?.dev?.port ?? 5173);
586
617
  const syncPortFromConfig = typeof config?.dev?.sync === "object" && typeof config.dev.sync.port === "number" ? config.dev.sync.port : 3001;
@@ -682,7 +713,9 @@ var devCommand = defineCommand3({
682
713
  logger.step(" Schema watcher disabled (schema.ts not found)");
683
714
  }
684
715
  logger.blank();
685
- logger.step(" Kora DevTools overlay: Ctrl+Shift+K (Cmd+Shift+K on macOS) when devtools: true");
716
+ logger.step(
717
+ " Kora DevTools overlay: Ctrl+Shift+K (Cmd+Shift+K on macOS) when devtools is enabled"
718
+ );
686
719
  processManager.spawn({
687
720
  label: "vite",
688
721
  command: process.execPath,
@@ -693,33 +726,31 @@ var devCommand = defineCommand3({
693
726
  },
694
727
  onExit: onManagedProcessExit
695
728
  });
696
- if (shouldStartSync && hasTsx && syncServerFile) {
697
- processManager.spawn({
698
- label: "sync",
699
- command: process.execPath,
700
- args: ["--import", "tsx", syncServerFile],
701
- cwd: projectRoot,
702
- env: {
703
- PORT: String(syncPort),
704
- KORA_SYNC_PORT: String(syncPort)
705
- },
706
- onExit: onManagedProcessExit
707
- });
708
- }
709
- if (shouldStartSync && syncServerFile === null && managedSyncStore !== null) {
710
- processManager.spawn({
711
- label: "sync",
712
- command: process.execPath,
713
- args: ["--input-type=module", "--eval", MANAGED_SYNC_BOOTSTRAP_SCRIPT],
714
- cwd: projectRoot,
715
- env: {
716
- KORA_DEV_SYNC_CONFIG: JSON.stringify({
717
- port: Number(syncPort),
718
- store: managedSyncStore
719
- })
720
- },
721
- onExit: onManagedProcessExit
722
- });
729
+ const syncProcessConfig = shouldStartSync && hasTsx && syncServerFile ? {
730
+ label: "sync",
731
+ command: process.execPath,
732
+ args: ["--import", "tsx", syncServerFile],
733
+ cwd: projectRoot,
734
+ env: {
735
+ PORT: String(syncPort),
736
+ KORA_SYNC_PORT: String(syncPort)
737
+ },
738
+ onExit: onManagedProcessExit
739
+ } : shouldStartSync && syncServerFile === null && managedSyncStore !== null ? {
740
+ label: "sync",
741
+ command: process.execPath,
742
+ args: ["--input-type=module", "--eval", MANAGED_SYNC_BOOTSTRAP_SCRIPT],
743
+ cwd: projectRoot,
744
+ env: {
745
+ KORA_DEV_SYNC_CONFIG: JSON.stringify({
746
+ port: Number(syncPort),
747
+ store: managedSyncStore
748
+ })
749
+ },
750
+ onExit: onManagedProcessExit
751
+ } : null;
752
+ if (syncProcessConfig) {
753
+ processManager.spawn(syncProcessConfig);
723
754
  }
724
755
  if (watchEnabled && schemaPath) {
725
756
  schemaWatcher = new SchemaWatcher({
@@ -729,6 +760,16 @@ var devCommand = defineCommand3({
729
760
  onRegenerate: () => {
730
761
  logger.success("Regenerated types from schema changes");
731
762
  },
763
+ onSchemaVersionChange: ({ previous, next }) => {
764
+ if (!syncProcessConfig) {
765
+ logger.warn(
766
+ `Schema version changed from ${previous} to ${next}; restart your sync server before clients can sync.`
767
+ );
768
+ return;
769
+ }
770
+ logger.warn(`Schema version changed from ${previous} to ${next}; restarting sync server.`);
771
+ void processManager.restart(syncProcessConfig);
772
+ },
732
773
  onError: (error) => {
733
774
  logger.error(`Schema watcher error: ${error.message}`);
734
775
  }
@@ -759,6 +800,43 @@ async function fileExists(path) {
759
800
  return false;
760
801
  }
761
802
  }
803
+ function loadProjectEnv(projectRoot, mode = "development") {
804
+ const files = [".env", ".env.local", `.env.${mode}`, `.env.${mode}.local`];
805
+ const existingKeys = new Set(Object.keys(process.env));
806
+ for (const file of files) {
807
+ const path = join4(projectRoot, file);
808
+ if (!existsSync(path)) continue;
809
+ const parsed = parseEnvFile(readFileSync(path, "utf8"));
810
+ for (const [key, value] of Object.entries(parsed)) {
811
+ if (!existingKeys.has(key)) {
812
+ process.env[key] = value;
813
+ }
814
+ }
815
+ }
816
+ }
817
+ function parseEnvFile(contents) {
818
+ const env = {};
819
+ for (const rawLine of contents.split(/\r?\n/)) {
820
+ const line = rawLine.trim();
821
+ if (!line || line.startsWith("#")) continue;
822
+ const normalized = line.startsWith("export ") ? line.slice("export ".length).trim() : line;
823
+ const equalsIndex = normalized.indexOf("=");
824
+ if (equalsIndex <= 0) continue;
825
+ const key = normalized.slice(0, equalsIndex).trim();
826
+ if (!/^[A-Za-z_][A-Za-z0-9_]*$/.test(key)) continue;
827
+ env[key] = parseEnvValue(normalized.slice(equalsIndex + 1).trim());
828
+ }
829
+ return env;
830
+ }
831
+ function parseEnvValue(value) {
832
+ const quote = value[0];
833
+ if ((quote === '"' || quote === "'") && value[value.length - 1] === quote) {
834
+ const inner = value.slice(1, -1);
835
+ return quote === '"' ? inner.replace(/\\n/g, "\n").replace(/\\r/g, "\r") : inner;
836
+ }
837
+ const commentIndex = value.search(/\s#/);
838
+ return (commentIndex >= 0 ? value.slice(0, commentIndex) : value).trim();
839
+ }
762
840
  function normalizeManagedSyncStore(config, projectRoot) {
763
841
  const sync = config?.dev?.sync;
764
842
  if (typeof sync !== "object" || sync === null) return null;
@@ -1793,6 +1871,14 @@ function mapFieldType(descriptor) {
1793
1871
  return "INTEGER";
1794
1872
  case "array":
1795
1873
  return "TEXT";
1874
+ case "object":
1875
+ return "TEXT";
1876
+ case "json":
1877
+ return "TEXT";
1878
+ case "blob":
1879
+ return "TEXT";
1880
+ case "secret":
1881
+ return "TEXT";
1796
1882
  case "richtext":
1797
1883
  return "BLOB";
1798
1884
  }
@@ -1808,7 +1894,7 @@ function quoteIdentifier(identifier) {
1808
1894
  if (!/^[a-zA-Z_][a-zA-Z0-9_]*$/.test(identifier)) {
1809
1895
  throw new Error(`Invalid SQL identifier: ${identifier}`);
1810
1896
  }
1811
- return identifier;
1897
+ return `"${identifier}"`;
1812
1898
  }
1813
1899
  function formatChange(change) {
1814
1900
  switch (change.type) {
@@ -2503,7 +2589,7 @@ function printStatus(status, url, logger) {
2503
2589
  }
2504
2590
 
2505
2591
  // src/commands/studio/studio-command.ts
2506
- import { existsSync } from "fs";
2592
+ import { existsSync as existsSync2 } from "fs";
2507
2593
  import { resolve as resolve6 } from "path";
2508
2594
  import { defineCommand as defineCommand9 } from "citty";
2509
2595
  var studioCommand = defineCommand9({
@@ -2608,7 +2694,7 @@ var studioCommand = defineCommand9({
2608
2694
  );
2609
2695
  }
2610
2696
  const dbPath = resolve6(process.cwd(), args.db);
2611
- if (!existsSync(dbPath)) {
2697
+ if (!existsSync2(dbPath)) {
2612
2698
  throw new Error(`Database file not found: ${dbPath}`);
2613
2699
  }
2614
2700
  const server = await startStudioServer({ port, dbPath });
@@ -2629,9 +2715,10 @@ var studioCommand = defineCommand9({
2629
2715
  var main = defineCommand10({
2630
2716
  meta: {
2631
2717
  name: "kora",
2632
- description: "Kora.js \u2014 Offline-first application framework"
2718
+ description: "Kora.js, the offline-first application framework"
2633
2719
  },
2634
2720
  subCommands: {
2721
+ "agents-md": agentsCommand,
2635
2722
  backup: backupCommand,
2636
2723
  compact: compactCommand,
2637
2724
  create: createCommand,