syncorejs 0.2.0 → 0.2.2

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 (135) hide show
  1. package/README.md +2 -1
  2. package/dist/_vendor/cli/app.d.mts.map +1 -1
  3. package/dist/_vendor/cli/app.mjs +323 -42
  4. package/dist/_vendor/cli/app.mjs.map +1 -1
  5. package/dist/_vendor/cli/context.mjs +27 -9
  6. package/dist/_vendor/cli/context.mjs.map +1 -1
  7. package/dist/_vendor/cli/doctor.mjs +513 -46
  8. package/dist/_vendor/cli/doctor.mjs.map +1 -1
  9. package/dist/_vendor/cli/messages.mjs +5 -4
  10. package/dist/_vendor/cli/messages.mjs.map +1 -1
  11. package/dist/_vendor/cli/project.mjs +110 -12
  12. package/dist/_vendor/cli/project.mjs.map +1 -1
  13. package/dist/_vendor/cli/render.mjs +57 -9
  14. package/dist/_vendor/cli/render.mjs.map +1 -1
  15. package/dist/_vendor/cli/targets.mjs +4 -3
  16. package/dist/_vendor/cli/targets.mjs.map +1 -1
  17. package/dist/_vendor/core/cli.d.mts +13 -3
  18. package/dist/_vendor/core/cli.d.mts.map +1 -1
  19. package/dist/_vendor/core/cli.mjs +242 -91
  20. package/dist/_vendor/core/cli.mjs.map +1 -1
  21. package/dist/_vendor/core/devtools-auth.mjs +60 -0
  22. package/dist/_vendor/core/devtools-auth.mjs.map +1 -0
  23. package/dist/_vendor/core/index.d.mts +5 -3
  24. package/dist/_vendor/core/index.mjs +22 -2
  25. package/dist/_vendor/core/index.mjs.map +1 -1
  26. package/dist/_vendor/core/runtime/components.d.mts +111 -0
  27. package/dist/_vendor/core/runtime/components.d.mts.map +1 -0
  28. package/dist/_vendor/core/runtime/components.mjs +186 -0
  29. package/dist/_vendor/core/runtime/components.mjs.map +1 -0
  30. package/dist/_vendor/core/runtime/devtools.d.mts +4 -4
  31. package/dist/_vendor/core/runtime/devtools.d.mts.map +1 -1
  32. package/dist/_vendor/core/runtime/devtools.mjs +52 -41
  33. package/dist/_vendor/core/runtime/devtools.mjs.map +1 -1
  34. package/dist/_vendor/core/runtime/functions.d.mts +10 -10
  35. package/dist/_vendor/core/runtime/functions.d.mts.map +1 -1
  36. package/dist/_vendor/core/runtime/functions.mjs +2 -2
  37. package/dist/_vendor/core/runtime/functions.mjs.map +1 -1
  38. package/dist/_vendor/core/runtime/internal/engines/devtoolsEngine.mjs +77 -0
  39. package/dist/_vendor/core/runtime/internal/engines/devtoolsEngine.mjs.map +1 -0
  40. package/dist/_vendor/core/runtime/internal/engines/executionEngine.mjs +617 -0
  41. package/dist/_vendor/core/runtime/internal/engines/executionEngine.mjs.map +1 -0
  42. package/dist/_vendor/core/runtime/internal/engines/reactivityEngine.mjs +186 -0
  43. package/dist/_vendor/core/runtime/internal/engines/reactivityEngine.mjs.map +1 -0
  44. package/dist/_vendor/core/runtime/internal/engines/schedulerEngine.mjs +220 -0
  45. package/dist/_vendor/core/runtime/internal/engines/schedulerEngine.mjs.map +1 -0
  46. package/dist/_vendor/core/runtime/internal/engines/schemaEngine.mjs +203 -0
  47. package/dist/_vendor/core/runtime/internal/engines/schemaEngine.mjs.map +1 -0
  48. package/dist/_vendor/core/runtime/internal/engines/shared.mjs +177 -0
  49. package/dist/_vendor/core/runtime/internal/engines/shared.mjs.map +1 -0
  50. package/dist/_vendor/core/runtime/internal/engines/storageEngine.mjs +144 -0
  51. package/dist/_vendor/core/runtime/internal/engines/storageEngine.mjs.map +1 -0
  52. package/dist/_vendor/core/runtime/internal/runtimeKernel.mjs +220 -0
  53. package/dist/_vendor/core/runtime/internal/runtimeKernel.mjs.map +1 -0
  54. package/dist/_vendor/core/runtime/internal/runtimeStatus.mjs +32 -0
  55. package/dist/_vendor/core/runtime/internal/runtimeStatus.mjs.map +1 -0
  56. package/dist/_vendor/core/runtime/internal/systemMeta.mjs +61 -0
  57. package/dist/_vendor/core/runtime/internal/systemMeta.mjs.map +1 -0
  58. package/dist/_vendor/core/runtime/internal/transactionCoordinator.mjs +37 -0
  59. package/dist/_vendor/core/runtime/internal/transactionCoordinator.mjs.map +1 -0
  60. package/dist/_vendor/core/runtime/runtime.d.mts +159 -205
  61. package/dist/_vendor/core/runtime/runtime.d.mts.map +1 -1
  62. package/dist/_vendor/core/runtime/runtime.mjs +16 -1371
  63. package/dist/_vendor/core/runtime/runtime.mjs.map +1 -1
  64. package/dist/_vendor/core/transport.d.mts +111 -0
  65. package/dist/_vendor/core/transport.d.mts.map +1 -0
  66. package/dist/_vendor/core/transport.mjs +419 -0
  67. package/dist/_vendor/core/transport.mjs.map +1 -0
  68. package/dist/_vendor/devtools-protocol/index.d.ts +39 -1
  69. package/dist/_vendor/devtools-protocol/index.d.ts.map +1 -1
  70. package/dist/_vendor/devtools-protocol/index.js +25 -9
  71. package/dist/_vendor/devtools-protocol/index.js.map +1 -1
  72. package/dist/_vendor/next/index.d.ts +1 -1
  73. package/dist/_vendor/next/index.d.ts.map +1 -1
  74. package/dist/_vendor/next/index.js +31 -13
  75. package/dist/_vendor/next/index.js.map +1 -1
  76. package/dist/_vendor/platform-expo/index.d.ts +12 -12
  77. package/dist/_vendor/platform-expo/index.d.ts.map +1 -1
  78. package/dist/_vendor/platform-expo/index.js +4 -2
  79. package/dist/_vendor/platform-expo/index.js.map +1 -1
  80. package/dist/_vendor/platform-expo/react.d.ts.map +1 -1
  81. package/dist/_vendor/platform-expo/react.js +11 -10
  82. package/dist/_vendor/platform-expo/react.js.map +1 -1
  83. package/dist/_vendor/platform-node/index.d.mts +23 -19
  84. package/dist/_vendor/platform-node/index.d.mts.map +1 -1
  85. package/dist/_vendor/platform-node/index.mjs +13 -5
  86. package/dist/_vendor/platform-node/index.mjs.map +1 -1
  87. package/dist/_vendor/platform-node/ipc-react.d.mts.map +1 -1
  88. package/dist/_vendor/platform-node/ipc-react.mjs +15 -2
  89. package/dist/_vendor/platform-node/ipc-react.mjs.map +1 -1
  90. package/dist/_vendor/platform-node/ipc.d.mts +11 -35
  91. package/dist/_vendor/platform-node/ipc.d.mts.map +1 -1
  92. package/dist/_vendor/platform-node/ipc.mjs +3 -273
  93. package/dist/_vendor/platform-node/ipc.mjs.map +1 -1
  94. package/dist/_vendor/platform-web/external-change.d.ts +2 -1
  95. package/dist/_vendor/platform-web/external-change.d.ts.map +1 -1
  96. package/dist/_vendor/platform-web/external-change.js +2 -1
  97. package/dist/_vendor/platform-web/external-change.js.map +1 -1
  98. package/dist/_vendor/platform-web/index.d.ts +21 -21
  99. package/dist/_vendor/platform-web/index.d.ts.map +1 -1
  100. package/dist/_vendor/platform-web/index.js +44 -7
  101. package/dist/_vendor/platform-web/index.js.map +1 -1
  102. package/dist/_vendor/platform-web/react.d.ts.map +1 -1
  103. package/dist/_vendor/platform-web/react.js +29 -13
  104. package/dist/_vendor/platform-web/react.js.map +1 -1
  105. package/dist/_vendor/platform-web/worker.d.ts +11 -35
  106. package/dist/_vendor/platform-web/worker.d.ts.map +1 -1
  107. package/dist/_vendor/platform-web/worker.js +3 -267
  108. package/dist/_vendor/platform-web/worker.js.map +1 -1
  109. package/dist/_vendor/react/index.d.ts +36 -20
  110. package/dist/_vendor/react/index.d.ts.map +1 -1
  111. package/dist/_vendor/react/index.js +279 -57
  112. package/dist/_vendor/react/index.js.map +1 -1
  113. package/dist/_vendor/schema/definition.d.ts +48 -63
  114. package/dist/_vendor/schema/definition.d.ts.map +1 -1
  115. package/dist/_vendor/schema/definition.js +22 -39
  116. package/dist/_vendor/schema/definition.js.map +1 -1
  117. package/dist/_vendor/schema/index.d.ts +4 -4
  118. package/dist/_vendor/schema/index.js +2 -2
  119. package/dist/_vendor/schema/planner.d.ts +19 -2
  120. package/dist/_vendor/schema/planner.d.ts.map +1 -1
  121. package/dist/_vendor/schema/planner.js +79 -3
  122. package/dist/_vendor/schema/planner.js.map +1 -1
  123. package/dist/_vendor/schema/validators.d.ts +141 -121
  124. package/dist/_vendor/schema/validators.d.ts.map +1 -1
  125. package/dist/_vendor/schema/validators.js +300 -42
  126. package/dist/_vendor/schema/validators.js.map +1 -1
  127. package/dist/_vendor/svelte/index.d.ts +47 -19
  128. package/dist/_vendor/svelte/index.d.ts.map +1 -1
  129. package/dist/_vendor/svelte/index.js +250 -20
  130. package/dist/_vendor/svelte/index.js.map +1 -1
  131. package/dist/components.d.ts +2 -0
  132. package/dist/components.js +2 -0
  133. package/dist/index.d.ts +3 -2
  134. package/dist/index.js +2 -1
  135. package/package.json +8 -3
@@ -3,6 +3,7 @@ import { generateId } from "./runtime/id.mjs";
3
3
  import { SyncoreRuntime } from "./runtime/runtime.mjs";
4
4
  import { createDevtoolsCommandHandler, createDevtoolsSubscriptionHost } from "./runtime/devtools.mjs";
5
5
  import { src_exports } from "./index.mjs";
6
+ import { generateDevtoolsToken, isAllowedDashboardOrigin, isAuthorizedDashboardRequest, sanitizeDevtoolsToken } from "./devtools-auth.mjs";
6
7
  import { appendFile, mkdir, readFile, readdir, rm, stat, writeFile } from "node:fs/promises";
7
8
  import { createServer } from "node:http";
8
9
  import { connect } from "node:net";
@@ -12,11 +13,15 @@ import { DatabaseSync } from "node:sqlite";
12
13
  import { Command } from "commander";
13
14
  import { tsImport } from "tsx/esm/api";
14
15
  import WebSocket, { WebSocketServer } from "ws";
15
- import { createPublicRuntimeId, createPublicTargetId } from "../devtools-protocol/index.js";
16
+ import { SYNCORE_DEVTOOLS_MAX_SUPPORTED_PROTOCOL_VERSION, SYNCORE_DEVTOOLS_MIN_SUPPORTED_PROTOCOL_VERSION, SYNCORE_DEVTOOLS_PROTOCOL_VERSION, createPublicRuntimeId, createPublicTargetId } from "../devtools-protocol/index.js";
16
17
  //#region src/cli.ts
18
+ function templateUsesConnectedClients(template) {
19
+ return template === "react-web" || template === "expo" || template === "next";
20
+ }
17
21
  const COMBINED_DEV_COMMAND = "concurrently --kill-others-on-fail --names syncore,app --prefix-colors yellow,cyan \"bun run syncorejs:dev\" \"bun run dev:app\"";
18
22
  const program = new Command();
19
23
  const CORE_PACKAGE_ROOT = path.resolve(path.dirname(fileURLToPath(import.meta.url)), "..");
24
+ const DEVTOOLS_SESSION_FILE = path.join(".syncore", "devtools-session.json");
20
25
  const SYNCORE_MIGRATION_SNAPSHOT_FILE_NAME = "_schema_snapshot.json";
21
26
  const VALID_SYNCORE_TEMPLATES = [
22
27
  "minimal",
@@ -123,8 +128,10 @@ if (isCliEntryPoint()) await runSyncoreCli();
123
128
  async function runCodegen(cwd) {
124
129
  const functionsDir = path.join(cwd, "syncore", "functions");
125
130
  const generatedDir = path.join(cwd, "syncore", "_generated");
131
+ const componentsManifestPath = path.join(cwd, "syncore", "components.ts");
126
132
  await mkdir(generatedDir, { recursive: true });
127
133
  const functionImportExtension = await resolveFunctionImportExtension(cwd);
134
+ const hasComponentsManifest = await fileExists(componentsManifestPath);
128
135
  const files = await listTypeScriptFiles(functionsDir);
129
136
  const functionEntries = [];
130
137
  for (const file of files) {
@@ -148,6 +155,8 @@ async function runCodegen(cwd) {
148
155
  ``,
149
156
  `import { createFunctionReferenceFor } from "syncorejs";`,
150
157
  `import type { FunctionReferenceFor } from "syncorejs";`,
158
+ `export { components } from "./components${functionImportExtension}";`,
159
+ ``,
151
160
  ...renderFunctionTypeImports(functionEntries, functionImportExtension),
152
161
  ``,
153
162
  ...renderGeneratedApiInterfaces(functionEntries),
@@ -174,9 +183,12 @@ async function runCodegen(cwd) {
174
183
  ` */`,
175
184
  ``,
176
185
  `import type { SyncoreFunctionRegistry } from "syncorejs";`,
177
- ``,
186
+ `import { composeProjectFunctionRegistry } from "syncorejs";`,
187
+ ...renderGeneratedManifestImportLines(hasComponentsManifest, functionImportExtension),
178
188
  ...renderFunctionImports(functionEntries, functionImportExtension),
179
189
  ``,
190
+ ...renderGeneratedManifestDeclarationLines(hasComponentsManifest),
191
+ ``,
180
192
  ...renderGeneratedFunctionsInterface(functionEntries),
181
193
  ``,
182
194
  `/**`,
@@ -184,9 +196,54 @@ async function runCodegen(cwd) {
184
196
  ` *`,
185
197
  ` * Most application code should import from \`./api\` instead of using this map directly.`,
186
198
  ` */`,
187
- `export const functions: SyncoreFunctionsRegistry = {`,
199
+ `const rootFunctions: SyncoreRootFunctionsRegistry = {`,
188
200
  ...functionEntries.map((entry) => ` ${JSON.stringify(`${entry.pathParts.join("/")}/${entry.exportName}`)}: ${renderFunctionImportName(entry)},`),
189
201
  `} as const;`,
202
+ ``,
203
+ `export const functions: SyncoreFunctionRegistry = composeProjectFunctionRegistry(rootFunctions, componentsManifest);`,
204
+ ``
205
+ ].join("\n");
206
+ const schemaSource = [
207
+ `/**`,
208
+ ` * Generated composed Syncore schema including installed components.`,
209
+ ` *`,
210
+ ` * THIS CODE IS AUTOMATICALLY GENERATED.`,
211
+ ` *`,
212
+ ` * To regenerate, run \`npx syncorejs dev\` or \`npx syncorejs codegen\`.`,
213
+ ` * @module`,
214
+ ` */`,
215
+ ``,
216
+ `import { composeProjectSchema } from "syncorejs";`,
217
+ `import rootSchema from "../schema${functionImportExtension}";`,
218
+ ...renderGeneratedManifestImportLines(hasComponentsManifest, functionImportExtension),
219
+ ``,
220
+ ...renderGeneratedManifestDeclarationLines(hasComponentsManifest),
221
+ ``,
222
+ `const schema = composeProjectSchema(rootSchema, componentsManifest);`,
223
+ ``,
224
+ `export default schema;`,
225
+ ``
226
+ ].join("\n");
227
+ const componentsSource = [
228
+ `/**`,
229
+ ` * Generated installed-component helpers for this Syncore app.`,
230
+ ` *`,
231
+ ` * THIS CODE IS AUTOMATICALLY GENERATED.`,
232
+ ` *`,
233
+ ` * To regenerate, run \`npx syncorejs dev\` or \`npx syncorejs codegen\`.`,
234
+ ` * @module`,
235
+ ` */`,
236
+ ``,
237
+ `import { createInstalledComponentsApi, resolveComponentsManifest } from "syncorejs";`,
238
+ ...renderGeneratedManifestImportLines(hasComponentsManifest, functionImportExtension),
239
+ ``,
240
+ ...renderGeneratedManifestDeclarationLines(hasComponentsManifest),
241
+ ``,
242
+ `export const components = createInstalledComponentsApi(componentsManifest);`,
243
+ ``,
244
+ `export const resolvedComponents = resolveComponentsManifest(componentsManifest);`,
245
+ ``,
246
+ `export default resolvedComponents;`,
190
247
  ``
191
248
  ].join("\n");
192
249
  const serverSource = [
@@ -213,7 +270,7 @@ async function runCodegen(cwd) {
213
270
  ` ValidatorMap`,
214
271
  `} from "syncorejs";`,
215
272
  ``,
216
- `export { createFunctionReference, createFunctionReferenceFor, v } from "syncorejs";`,
273
+ `export { createFunctionReference, createFunctionReferenceFor, s } from "syncorejs";`,
217
274
  ``,
218
275
  `/**`,
219
276
  ` * The context object available inside Syncore query handlers in this app.`,
@@ -240,22 +297,14 @@ async function runCodegen(cwd) {
240
297
  ` * @param config - The query definition, including args and a handler.`,
241
298
  ` * @returns The wrapped query. Export it from \`syncore/functions\` to add it to the generated API.`,
242
299
  ` */`,
243
- `export function query<TValidator extends Validator<unknown>, TResult>(`,
244
- ` config: FunctionConfig<QueryCtx, Infer<TValidator>, TResult> & { args: TValidator }`,
245
- `): SyncoreFunctionDefinition<"query", QueryCtx, Infer<TValidator>, TResult>;`,
246
- `export function query<TArgsShape extends ValidatorMap, TResult>(`,
247
- ` config: FunctionConfig<QueryCtx, InferArgs<TArgsShape>, TResult> & { args: TArgsShape }`,
248
- `): SyncoreFunctionDefinition<"query", QueryCtx, InferArgs<TArgsShape>, TResult>;`,
249
- `export function query<TArgsShape extends Validator<unknown> | ValidatorMap, TResult>(`,
250
- ` config: FunctionConfig<QueryCtx, InferArgs<TArgsShape>, TResult> & { args: TArgsShape }`,
251
- `) {`,
252
- ` return baseQuery(config as never) as SyncoreFunctionDefinition<`,
253
- ` "query",`,
254
- ` QueryCtx,`,
255
- ` InferArgs<TArgsShape>,`,
256
- ` TResult`,
257
- ` >;`,
258
- `}`,
300
+ `export const query = baseQuery as {`,
301
+ ` <TValidator extends Validator<unknown, unknown, string>, TResult>(`,
302
+ ` config: FunctionConfig<QueryCtx, Infer<TValidator>, TResult> & { args: TValidator }`,
303
+ ` ): SyncoreFunctionDefinition<"query", QueryCtx, Infer<TValidator>, TResult>;`,
304
+ ` <TArgsShape extends ValidatorMap, TResult>(`,
305
+ ` config: FunctionConfig<QueryCtx, InferArgs<TArgsShape>, TResult> & { args: TArgsShape }`,
306
+ ` ): SyncoreFunctionDefinition<"query", QueryCtx, InferArgs<TArgsShape>, TResult>;`,
307
+ `};`,
259
308
  ``,
260
309
  `/**`,
261
310
  ` * Define a mutation in this Syncore app's public API.`,
@@ -265,22 +314,14 @@ async function runCodegen(cwd) {
265
314
  ` * @param config - The mutation definition, including args and a handler.`,
266
315
  ` * @returns The wrapped mutation. Export it from \`syncore/functions\` to add it to the generated API.`,
267
316
  ` */`,
268
- `export function mutation<TValidator extends Validator<unknown>, TResult>(`,
269
- ` config: FunctionConfig<MutationCtx, Infer<TValidator>, TResult> & { args: TValidator }`,
270
- `): SyncoreFunctionDefinition<"mutation", MutationCtx, Infer<TValidator>, TResult>;`,
271
- `export function mutation<TArgsShape extends ValidatorMap, TResult>(`,
272
- ` config: FunctionConfig<MutationCtx, InferArgs<TArgsShape>, TResult> & { args: TArgsShape }`,
273
- `): SyncoreFunctionDefinition<"mutation", MutationCtx, InferArgs<TArgsShape>, TResult>;`,
274
- `export function mutation<TArgsShape extends Validator<unknown> | ValidatorMap, TResult>(`,
275
- ` config: FunctionConfig<MutationCtx, InferArgs<TArgsShape>, TResult> & { args: TArgsShape }`,
276
- `) {`,
277
- ` return baseMutation(config as never) as SyncoreFunctionDefinition<`,
278
- ` "mutation",`,
279
- ` MutationCtx,`,
280
- ` InferArgs<TArgsShape>,`,
281
- ` TResult`,
282
- ` >;`,
283
- `}`,
317
+ `export const mutation = baseMutation as {`,
318
+ ` <TValidator extends Validator<unknown, unknown, string>, TResult>(`,
319
+ ` config: FunctionConfig<MutationCtx, Infer<TValidator>, TResult> & { args: TValidator }`,
320
+ ` ): SyncoreFunctionDefinition<"mutation", MutationCtx, Infer<TValidator>, TResult>;`,
321
+ ` <TArgsShape extends ValidatorMap, TResult>(`,
322
+ ` config: FunctionConfig<MutationCtx, InferArgs<TArgsShape>, TResult> & { args: TArgsShape }`,
323
+ ` ): SyncoreFunctionDefinition<"mutation", MutationCtx, InferArgs<TArgsShape>, TResult>;`,
324
+ `};`,
284
325
  ``,
285
326
  `/**`,
286
327
  ` * Define an action in this Syncore app's public API.`,
@@ -290,26 +331,20 @@ async function runCodegen(cwd) {
290
331
  ` * @param config - The action definition, including args and a handler.`,
291
332
  ` * @returns The wrapped action. Export it from \`syncore/functions\` to add it to the generated API.`,
292
333
  ` */`,
293
- `export function action<TValidator extends Validator<unknown>, TResult>(`,
294
- ` config: FunctionConfig<ActionCtx, Infer<TValidator>, TResult> & { args: TValidator }`,
295
- `): SyncoreFunctionDefinition<"action", ActionCtx, Infer<TValidator>, TResult>;`,
296
- `export function action<TArgsShape extends ValidatorMap, TResult>(`,
297
- ` config: FunctionConfig<ActionCtx, InferArgs<TArgsShape>, TResult> & { args: TArgsShape }`,
298
- `): SyncoreFunctionDefinition<"action", ActionCtx, InferArgs<TArgsShape>, TResult>;`,
299
- `export function action<TArgsShape extends Validator<unknown> | ValidatorMap, TResult>(`,
300
- ` config: FunctionConfig<ActionCtx, InferArgs<TArgsShape>, TResult> & { args: TArgsShape }`,
301
- `) {`,
302
- ` return baseAction(config as never) as SyncoreFunctionDefinition<`,
303
- ` "action",`,
304
- ` ActionCtx,`,
305
- ` InferArgs<TArgsShape>,`,
306
- ` TResult`,
307
- ` >;`,
308
- `}`,
334
+ `export const action = baseAction as {`,
335
+ ` <TValidator extends Validator<unknown, unknown, string>, TResult>(`,
336
+ ` config: FunctionConfig<ActionCtx, Infer<TValidator>, TResult> & { args: TValidator }`,
337
+ ` ): SyncoreFunctionDefinition<"action", ActionCtx, Infer<TValidator>, TResult>;`,
338
+ ` <TArgsShape extends ValidatorMap, TResult>(`,
339
+ ` config: FunctionConfig<ActionCtx, InferArgs<TArgsShape>, TResult> & { args: TArgsShape }`,
340
+ ` ): SyncoreFunctionDefinition<"action", ActionCtx, InferArgs<TArgsShape>, TResult>;`,
341
+ `};`,
309
342
  ``
310
343
  ].join("\n");
311
344
  await writeFile(path.join(generatedDir, "api.ts"), apiSource);
345
+ await writeFile(path.join(generatedDir, "components.ts"), componentsSource);
312
346
  await writeFile(path.join(generatedDir, "functions.ts"), functionsSource);
347
+ await writeFile(path.join(generatedDir, "schema.ts"), schemaSource);
313
348
  await writeFile(path.join(generatedDir, "server.ts"), serverSource);
314
349
  }
315
350
  async function scaffoldProject(cwd, options) {
@@ -345,19 +380,26 @@ function buildTemplateFiles(template) {
345
380
  },
346
381
  {
347
382
  path: path.join("syncore", "schema.ts"),
348
- content: `import { defineSchema, defineTable, v } from "syncorejs";
383
+ content: `import { defineSchema, defineTable, s } from "syncorejs";
349
384
 
350
385
  export default defineSchema({
351
386
  tasks: defineTable({
352
- text: v.string(),
353
- done: v.boolean()
387
+ text: s.string(),
388
+ done: s.boolean()
354
389
  }).index("by_done", ["done"])
355
390
  });
391
+ `
392
+ },
393
+ {
394
+ path: path.join("syncore", "components.ts"),
395
+ content: `import { defineComponents } from "syncorejs";
396
+
397
+ export default defineComponents({});
356
398
  `
357
399
  },
358
400
  {
359
401
  path: path.join("syncore", "functions", "tasks.ts"),
360
- content: `import { mutation, query, v } from "../_generated/server";
402
+ content: `import { mutation, query, s } from "../_generated/server";
361
403
 
362
404
  export const list = query({
363
405
  args: {},
@@ -366,7 +408,7 @@ export const list = query({
366
408
  });
367
409
 
368
410
  export const create = mutation({
369
- args: { text: v.string() },
411
+ args: { text: s.string() },
370
412
  handler: async (ctx, args) =>
371
413
  ctx.db.insert("tasks", { text: args.text, done: false })
372
414
  });
@@ -380,13 +422,15 @@ export const create = mutation({
380
422
  content: `/// <reference lib="webworker" />
381
423
 
382
424
  import { createBrowserWorkerRuntime } from "syncorejs/browser";
383
- import schema from "../syncore/schema";
425
+ import schema from "../syncore/_generated/schema";
426
+ import { resolvedComponents } from "../syncore/_generated/components";
384
427
  import { functions } from "../syncore/_generated/functions";
385
428
 
386
429
  void createBrowserWorkerRuntime({
387
430
  endpoint: self,
388
431
  schema,
389
432
  functions,
433
+ components: resolvedComponents,
390
434
  databaseName: "syncore-app",
391
435
  persistenceMode: "opfs"
392
436
  });
@@ -410,12 +454,14 @@ export function AppSyncoreProvider({ children }: { children: ReactNode }) {
410
454
  files.push({
411
455
  path: path.join("lib", "syncore.ts"),
412
456
  content: `import { createExpoSyncoreBootstrap } from "syncorejs/expo";
413
- import schema from "../syncore/schema";
457
+ import schema from "../syncore/_generated/schema";
458
+ import { resolvedComponents } from "../syncore/_generated/components";
414
459
  import { functions } from "../syncore/_generated/functions";
415
460
 
416
461
  export const syncore = createExpoSyncoreBootstrap({
417
462
  schema,
418
463
  functions,
464
+ components: resolvedComponents,
419
465
  databaseName: "syncore-app.db",
420
466
  storageDirectoryName: "syncore-app-storage"
421
467
  });
@@ -428,13 +474,15 @@ export const syncore = createExpoSyncoreBootstrap({
428
474
  content: `/* eslint-disable */
429
475
 
430
476
  import { createBrowserWorkerRuntime } from "syncorejs/browser";
431
- import schema from "../syncore/schema";
477
+ import schema from "../syncore/_generated/schema";
478
+ import { resolvedComponents } from "../syncore/_generated/components";
432
479
  import { functions } from "../syncore/_generated/functions";
433
480
 
434
481
  void createBrowserWorkerRuntime({
435
482
  endpoint: self,
436
483
  schema,
437
484
  functions,
485
+ components: resolvedComponents,
438
486
  databaseName: "syncore-app",
439
487
  persistenceDatabaseName: "syncore-app",
440
488
  locateFile: () => "/sql-wasm.wasm",
@@ -469,7 +517,8 @@ export function AppSyncoreProvider({ children }: { children: ReactNode }) {
469
517
  content: `import path from "node:path";
470
518
  import { withNodeSyncoreClient } from "syncorejs/node";
471
519
  import { api } from "./syncore/_generated/api.ts";
472
- import schema from "./syncore/schema.ts";
520
+ import schema from "./syncore/_generated/schema.ts";
521
+ import { resolvedComponents } from "./syncore/_generated/components.ts";
473
522
  import { functions } from "./syncore/_generated/functions.ts";
474
523
 
475
524
  await withNodeSyncoreClient(
@@ -477,7 +526,8 @@ await withNodeSyncoreClient(
477
526
  databasePath: path.join(process.cwd(), ".syncore", "syncore.db"),
478
527
  storageDirectory: path.join(process.cwd(), ".syncore", "storage"),
479
528
  schema,
480
- functions
529
+ functions,
530
+ components: resolvedComponents
481
531
  },
482
532
  async (client) => {
483
533
  await client.mutation(api.tasks.create, { text: "Run locally" });
@@ -493,7 +543,8 @@ await withNodeSyncoreClient(
493
543
  content: `import path from "node:path";
494
544
  import { app } from "electron";
495
545
  import { createNodeSyncoreRuntime } from "syncorejs/node";
496
- import schema from "../syncore/schema.js";
546
+ import schema from "../syncore/_generated/schema.js";
547
+ import { resolvedComponents } from "../syncore/_generated/components.js";
497
548
  import { functions } from "../syncore/_generated/functions.js";
498
549
 
499
550
  export function createAppSyncoreRuntime() {
@@ -503,6 +554,7 @@ export function createAppSyncoreRuntime() {
503
554
  storageDirectory: path.join(userDataDirectory, "storage"),
504
555
  schema,
505
556
  functions,
557
+ components: resolvedComponents,
506
558
  platform: "electron-main"
507
559
  });
508
560
  }
@@ -768,12 +820,19 @@ function renderGeneratedFunctionsInterface(functionEntries) {
768
820
  `/**`,
769
821
  ` * Type-safe runtime definitions for every function exported from \`syncore/functions\`.`,
770
822
  ` */`,
771
- `export interface SyncoreFunctionsRegistry extends SyncoreFunctionRegistry {`
823
+ `export interface SyncoreRootFunctionsRegistry extends SyncoreFunctionRegistry {`
772
824
  ];
773
825
  for (const entry of functionEntries.slice().sort((left, right) => `${left.pathParts.join("/")}/${left.exportName}`.localeCompare(`${right.pathParts.join("/")}/${right.exportName}`))) lines.push(` /**`, ` * Runtime definition for the public Syncore ${entry.kind} \`${entry.pathParts.join("/")}/${entry.exportName}\`.`, ` */`, ` readonly ${JSON.stringify(`${entry.pathParts.join("/")}/${entry.exportName}`)}: typeof ${renderFunctionImportName(entry)};`);
774
826
  lines.push(`}`);
775
827
  return [lines.join("\n")];
776
828
  }
829
+ function renderGeneratedManifestImportLines(hasComponentsManifest, extension) {
830
+ if (!hasComponentsManifest) return [];
831
+ return [`import componentsManifest from "../components${extension}";`];
832
+ }
833
+ function renderGeneratedManifestDeclarationLines(hasComponentsManifest) {
834
+ return hasComponentsManifest ? [] : [`const componentsManifest = {} as const;`];
835
+ }
777
836
  function renderApiInterfaceName(node) {
778
837
  if (node.pathParts.length === 0) return "SyncoreApi";
779
838
  return `SyncoreApi__${node.pathParts.map(toTypeNamePart).join("__")}`;
@@ -831,11 +890,25 @@ function requireProjectTargetConfig(config) {
831
890
  if (!projectTarget) throw new Error("This Syncore project does not define a projectTarget. Use a connected client target instead.");
832
891
  return projectTarget;
833
892
  }
834
- async function loadProjectSchema(cwd) {
893
+ async function loadProjectRootSchema(cwd) {
835
894
  const schema = await loadDefaultExport(path.join(cwd, "syncore", "schema.ts"));
836
895
  if (!schema || typeof schema !== "object" || typeof schema.tableNames !== "function") throw new Error("syncore/schema.ts must default export defineSchema(...).");
837
896
  return schema;
838
897
  }
898
+ async function loadProjectComponentsManifest(cwd) {
899
+ const filePath = path.join(cwd, "syncore", "components.ts");
900
+ if (!await fileExists(filePath)) return {};
901
+ const manifest = await loadDefaultExport(filePath);
902
+ if (!manifest || typeof manifest !== "object" || Array.isArray(manifest)) throw new Error("syncore/components.ts must default export defineComponents({...}).");
903
+ return manifest;
904
+ }
905
+ async function loadProjectSchema(cwd) {
906
+ const filePath = path.join(cwd, "syncore", "_generated", "schema.ts");
907
+ if (!await fileExists(filePath)) await runCodegen(cwd);
908
+ const schema = await loadDefaultExport(filePath);
909
+ if (!schema || typeof schema !== "object" || typeof schema.tableNames !== "function") throw new Error("syncore/_generated/schema.ts must default export a composed Syncore schema.");
910
+ return schema;
911
+ }
839
912
  async function loadDefaultExport(filePath) {
840
913
  if (!await fileExists(filePath)) throw new Error(`Missing file: ${path.relative(process.cwd(), filePath)}`);
841
914
  const moduleUrl = pathToFileURL(filePath).href;
@@ -856,10 +929,19 @@ async function loadNamedExport(filePath, exportName) {
856
929
  return resolvedValue;
857
930
  }
858
931
  async function loadProjectFunctions(cwd) {
859
- const functions = await loadNamedExport(path.join(cwd, "syncore", "_generated", "functions.ts"), "functions");
932
+ const filePath = path.join(cwd, "syncore", "_generated", "functions.ts");
933
+ if (!await fileExists(filePath)) await runCodegen(cwd);
934
+ const functions = await loadNamedExport(filePath, "functions");
860
935
  if (!functions || typeof functions !== "object") throw new Error("syncore/_generated/functions.ts must export a functions registry.");
861
936
  return functions;
862
937
  }
938
+ async function loadProjectResolvedComponents(cwd) {
939
+ const filePath = path.join(cwd, "syncore", "_generated", "components.ts");
940
+ if (!await fileExists(filePath)) await runCodegen(cwd);
941
+ const components = await loadNamedExport(filePath, "resolvedComponents");
942
+ if (!Array.isArray(components)) throw new Error("syncore/_generated/components.ts must export resolvedComponents.");
943
+ return components;
944
+ }
863
945
  var HubSqliteDriver = class {
864
946
  database;
865
947
  transactionDepth = 0;
@@ -1033,8 +1115,11 @@ const hubDevtoolsSqlSupport = {
1033
1115
  async function createProjectTargetBackend(cwd) {
1034
1116
  const projectTarget = resolveProjectTargetConfig(await loadProjectConfig(cwd));
1035
1117
  if (!projectTarget) return null;
1036
- const schema = await loadProjectSchema(cwd);
1037
- const functions = await loadProjectFunctions(cwd);
1118
+ const [schema, functions, components] = await Promise.all([
1119
+ loadProjectSchema(cwd),
1120
+ loadProjectFunctions(cwd),
1121
+ loadProjectResolvedComponents(cwd)
1122
+ ]);
1038
1123
  const databasePath = path.resolve(cwd, projectTarget.databasePath);
1039
1124
  const storageDirectory = path.resolve(cwd, projectTarget.storageDirectory);
1040
1125
  await mkdir(path.dirname(databasePath), { recursive: true });
@@ -1043,6 +1128,7 @@ async function createProjectTargetBackend(cwd) {
1043
1128
  const runtime = new SyncoreRuntime({
1044
1129
  schema,
1045
1130
  functions,
1131
+ components,
1046
1132
  driver,
1047
1133
  storage: new HubFileStorageAdapter(storageDirectory),
1048
1134
  platform: "project"
@@ -1052,19 +1138,22 @@ async function createProjectTargetBackend(cwd) {
1052
1138
  driver,
1053
1139
  schema,
1054
1140
  functions,
1055
- runtime,
1141
+ admin: runtime.getAdmin(),
1056
1142
  sql: hubDevtoolsSqlSupport
1057
1143
  });
1058
1144
  const subscriptionHost = createDevtoolsSubscriptionHost({
1059
1145
  driver,
1060
1146
  schema,
1061
1147
  functions,
1062
- runtime,
1148
+ admin: runtime.getAdmin(),
1063
1149
  sql: hubDevtoolsSqlSupport
1064
1150
  });
1065
1151
  return {
1066
1152
  hello: {
1067
1153
  type: "hello",
1154
+ protocolVersion: SYNCORE_DEVTOOLS_PROTOCOL_VERSION,
1155
+ minSupportedProtocolVersion: SYNCORE_DEVTOOLS_MIN_SUPPORTED_PROTOCOL_VERSION,
1156
+ maxSupportedProtocolVersion: SYNCORE_DEVTOOLS_MAX_SUPPORTED_PROTOCOL_VERSION,
1068
1157
  runtimeId: PROJECT_TARGET_RUNTIME_ID,
1069
1158
  platform: "project",
1070
1159
  sessionLabel: "Project Target",
@@ -1239,16 +1328,26 @@ function applyMigrationSql(database, sql, fileName) {
1239
1328
  async function startDevHub(options) {
1240
1329
  const dashboardPort = resolvePortFromEnv("SYNCORE_DASHBOARD_PORT", 4310);
1241
1330
  const devtoolsPort = resolvePortFromEnv("SYNCORE_DEVTOOLS_PORT", 4311);
1331
+ const dashboardUrl = `http://localhost:${dashboardPort}`;
1332
+ const devtoolsUrl = `ws://127.0.0.1:${devtoolsPort}`;
1242
1333
  const logsDirectory = path.join(options.cwd, ".syncore", "logs");
1243
1334
  const logFilePath = path.join(logsDirectory, "runtime.jsonl");
1335
+ const hubAccessToken = sanitizeDevtoolsToken(process.env.SYNCORE_DEVTOOLS_TOKEN) ?? generateDevtoolsToken();
1336
+ const sessionState = {
1337
+ dashboardUrl,
1338
+ authenticatedDashboardUrl: `${dashboardUrl}/?token=${hubAccessToken}`,
1339
+ devtoolsUrl,
1340
+ token: hubAccessToken
1341
+ };
1244
1342
  await mkdir(logsDirectory, { recursive: true });
1245
1343
  await writeFile(logFilePath, "");
1246
1344
  await runDevProjectBootstrap(options.cwd, options.template);
1247
1345
  await setupDevProjectWatch(options.cwd, options.template);
1248
1346
  if (await isLocalPortInUse(devtoolsPort)) {
1249
1347
  console.log(`Syncore devtools hub already running at ws://localhost:${devtoolsPort}. Reusing existing hub/dashboard.`);
1250
- return;
1348
+ return await readDevtoolsSessionState(options.cwd) ?? sessionState;
1251
1349
  }
1350
+ await writeDevtoolsSessionState(options.cwd, sessionState);
1252
1351
  let projectTargetBackend = null;
1253
1352
  try {
1254
1353
  projectTargetBackend = await createProjectTargetBackend(options.cwd);
@@ -1271,6 +1370,9 @@ async function startDevHub(options) {
1271
1370
  const dashboardSubscriptions = /* @__PURE__ */ new Map();
1272
1371
  const hello = {
1273
1372
  type: "hello",
1373
+ protocolVersion: SYNCORE_DEVTOOLS_PROTOCOL_VERSION,
1374
+ minSupportedProtocolVersion: SYNCORE_DEVTOOLS_MIN_SUPPORTED_PROTOCOL_VERSION,
1375
+ maxSupportedProtocolVersion: SYNCORE_DEVTOOLS_MAX_SUPPORTED_PROTOCOL_VERSION,
1274
1376
  runtimeId: "syncore-dev-hub",
1275
1377
  platform: "dev"
1276
1378
  };
@@ -1300,7 +1402,18 @@ async function startDevHub(options) {
1300
1402
  event
1301
1403
  })}\n`);
1302
1404
  };
1303
- websocketServer.on("connection", (socket) => {
1405
+ websocketServer.on("connection", (socket, request) => {
1406
+ const isBrowserDashboardClient = isAllowedDashboardOrigin(request.headers.origin, dashboardPort);
1407
+ const isAuthorizedDashboardClient = !isBrowserDashboardClient || isAuthorizedDashboardRequest({
1408
+ requestUrl: request.url,
1409
+ originHeader: request.headers.origin,
1410
+ dashboardPort,
1411
+ expectedToken: hubAccessToken
1412
+ });
1413
+ if (isBrowserDashboardClient && !isAuthorizedDashboardClient) {
1414
+ socket.close(1008, "Unauthorized devtools client");
1415
+ return;
1416
+ }
1304
1417
  dashboardSockets.add(socket);
1305
1418
  socket.send(JSON.stringify(hello));
1306
1419
  for (const runtimeHello of runtimeHellos.values()) socket.send(JSON.stringify(runtimeHello));
@@ -1318,10 +1431,15 @@ async function startDevHub(options) {
1318
1431
  if (rawPayload.length === 0) return;
1319
1432
  const message = JSON.parse(rawPayload);
1320
1433
  if (message.type === "ping") {
1434
+ if (!isAuthorizedDashboardClient) {
1435
+ socket.close(1008, "Unauthorized devtools client");
1436
+ return;
1437
+ }
1321
1438
  socket.send(JSON.stringify({ type: "pong" }));
1322
1439
  return;
1323
1440
  }
1324
1441
  if (message.type === "command") {
1442
+ if (!isAuthorizedDashboardClient) return;
1325
1443
  const targetRuntimeId = message.targetRuntimeId;
1326
1444
  if (!targetRuntimeId) return;
1327
1445
  if (targetRuntimeId === PROJECT_TARGET_RUNTIME_ID && projectTargetBackend) {
@@ -1342,6 +1460,7 @@ async function startDevHub(options) {
1342
1460
  return;
1343
1461
  }
1344
1462
  if (message.type === "subscribe") {
1463
+ if (!isAuthorizedDashboardClient) return;
1345
1464
  const targetRuntimeId = message.targetRuntimeId;
1346
1465
  if (!targetRuntimeId) return;
1347
1466
  const subscriptions = dashboardSubscriptions.get(socket) ?? /* @__PURE__ */ new Map();
@@ -1375,6 +1494,7 @@ async function startDevHub(options) {
1375
1494
  return;
1376
1495
  }
1377
1496
  if (message.type === "unsubscribe") {
1497
+ if (!isAuthorizedDashboardClient) return;
1378
1498
  const subscriptions = dashboardSubscriptions.get(socket);
1379
1499
  const subscription = subscriptions?.get(message.subscriptionId);
1380
1500
  if (!subscription) return;
@@ -1481,25 +1601,29 @@ async function startDevHub(options) {
1481
1601
  console.error(`Syncore devtools hub failed: ${formatError(error)}`);
1482
1602
  process.exit(1);
1483
1603
  });
1484
- httpServer.listen(devtoolsPort, "127.0.0.1", () => {
1485
- (async () => {
1486
- console.log(`Syncore devtools hub: ws://localhost:${devtoolsPort}`);
1487
- console.log(`Electron/Node runtimes: set devtoolsUrl to ws://localhost:${devtoolsPort}.`);
1488
- console.log(`Web/Next apps: connect the dashboard or worker bridge to ws://localhost:${devtoolsPort}.`);
1489
- console.log("Expo apps: use the same hub URL through LAN or adb reverse while developing.");
1490
- const dashboardRoot = path.resolve(CORE_PACKAGE_ROOT, "..", "..", "apps", "dashboard");
1491
- if (await fileExists(path.join(dashboardRoot, "vite.config.ts"))) try {
1492
- await (await (await import("vite")).createServer({
1493
- configFile: path.join(dashboardRoot, "vite.config.ts"),
1494
- root: dashboardRoot,
1495
- server: { port: dashboardPort }
1496
- })).listen();
1497
- console.log(`Dashboard shell: http://localhost:${dashboardPort}`);
1498
- } catch (error) {
1499
- console.log(`Dashboard source not started automatically: ${formatError(error)}`);
1500
- }
1501
- })();
1604
+ await new Promise((resolve, reject) => {
1605
+ httpServer.once("error", reject);
1606
+ httpServer.listen(devtoolsPort, "127.0.0.1", () => {
1607
+ httpServer.off("error", reject);
1608
+ resolve();
1609
+ });
1502
1610
  });
1611
+ console.log(`Syncore devtools hub: ws://localhost:${devtoolsPort}`);
1612
+ console.log(`Devtools dashboard token: ${hubAccessToken}`);
1613
+ console.log(`Electron/Node runtimes: set devtoolsUrl to ws://localhost:${devtoolsPort}.`);
1614
+ console.log(`Web/Next apps: connect the dashboard or worker bridge to ws://localhost:${devtoolsPort}.`);
1615
+ console.log("Expo apps: use the same hub URL through LAN or adb reverse while developing.");
1616
+ const dashboardRoot = path.resolve(CORE_PACKAGE_ROOT, "..", "..", "apps", "dashboard");
1617
+ if (await fileExists(path.join(dashboardRoot, "vite.config.ts"))) try {
1618
+ await (await (await import("vite")).createServer({
1619
+ configFile: path.join(dashboardRoot, "vite.config.ts"),
1620
+ root: dashboardRoot,
1621
+ server: { port: dashboardPort }
1622
+ })).listen();
1623
+ console.log(`Dashboard shell: ${sessionState.authenticatedDashboardUrl}`);
1624
+ } catch (error) {
1625
+ console.log(`Dashboard source not started automatically: ${formatError(error)}`);
1626
+ }
1503
1627
  const close = () => {
1504
1628
  projectTargetBackend?.dispose();
1505
1629
  websocketServer.close();
@@ -1508,6 +1632,29 @@ async function startDevHub(options) {
1508
1632
  };
1509
1633
  process.on("SIGINT", close);
1510
1634
  process.on("SIGTERM", close);
1635
+ return sessionState;
1636
+ }
1637
+ async function writeDevtoolsSessionState(cwd, state) {
1638
+ const sessionPath = path.join(cwd, DEVTOOLS_SESSION_FILE);
1639
+ await mkdir(path.dirname(sessionPath), { recursive: true });
1640
+ await writeFile(sessionPath, `${JSON.stringify(state, null, 2)}\n`);
1641
+ }
1642
+ async function readDevtoolsSessionState(cwd) {
1643
+ const sessionPath = path.join(cwd, DEVTOOLS_SESSION_FILE);
1644
+ if (!await fileExists(sessionPath)) return null;
1645
+ try {
1646
+ const source = await readFile(sessionPath, "utf8");
1647
+ const parsed = JSON.parse(source);
1648
+ if (typeof parsed.dashboardUrl !== "string" || typeof parsed.authenticatedDashboardUrl !== "string" || typeof parsed.devtoolsUrl !== "string" || typeof parsed.token !== "string") return null;
1649
+ return {
1650
+ dashboardUrl: parsed.dashboardUrl,
1651
+ authenticatedDashboardUrl: parsed.authenticatedDashboardUrl,
1652
+ devtoolsUrl: parsed.devtoolsUrl,
1653
+ token: parsed.token
1654
+ };
1655
+ } catch {
1656
+ return null;
1657
+ }
1511
1658
  }
1512
1659
  async function setupDevProjectWatch(cwd, template) {
1513
1660
  const snapshot = await createDevWatchSnapshot(cwd);
@@ -1558,6 +1705,10 @@ async function runDevProjectBootstrap(cwd, template) {
1558
1705
  else console.log("Schema snapshot updated.");
1559
1706
  }
1560
1707
  for (const warning of plan.warnings) console.warn(`Syncore dev warning: ${warning}`);
1708
+ if (templateUsesConnectedClients(template)) {
1709
+ console.log("Syncore dev is ready. Codegen refreshed; waiting for a connected client runtime to apply schema locally.");
1710
+ return;
1711
+ }
1561
1712
  const appliedCount = await applyProjectMigrations(cwd);
1562
1713
  console.log(`Syncore dev is ready. Codegen refreshed; ${appliedCount} migration(s) applied.`);
1563
1714
  } catch (error) {
@@ -1644,6 +1795,6 @@ function toSearchValue(value) {
1644
1795
  return stableStringify(value);
1645
1796
  }
1646
1797
  //#endregion
1647
- export { SYNCORE_MIGRATION_SNAPSHOT_FILE_NAME, VALID_SYNCORE_TEMPLATES, applyProjectMigrations, detectProjectTemplate, fileExists, formatError, getNextMigrationNumber, hasSyncoreProject, importJsonlIntoProject, isLocalPortInUse, loadProjectConfig, loadProjectFunctions, loadProjectSchema, logScaffoldResult, readPackageJson, readStoredSnapshot, resolveDefaultSeedFile, resolvePortFromEnv, resolveProjectTargetConfig, resolveRequestedTemplate, runCodegen, runDevProjectBootstrap, runSyncoreCli, scaffoldProject, slugify, startDevHub, writeStoredSnapshot };
1798
+ export { SYNCORE_MIGRATION_SNAPSHOT_FILE_NAME, VALID_SYNCORE_TEMPLATES, applyProjectMigrations, detectProjectTemplate, fileExists, formatError, getNextMigrationNumber, hasSyncoreProject, importJsonlIntoProject, isLocalPortInUse, loadProjectComponentsManifest, loadProjectConfig, loadProjectFunctions, loadProjectResolvedComponents, loadProjectRootSchema, loadProjectSchema, logScaffoldResult, readPackageJson, readStoredSnapshot, resolveDefaultSeedFile, resolvePortFromEnv, resolveProjectTargetConfig, resolveRequestedTemplate, runCodegen, runDevProjectBootstrap, runSyncoreCli, scaffoldProject, slugify, startDevHub, templateUsesConnectedClients, writeStoredSnapshot };
1648
1799
 
1649
1800
  //# sourceMappingURL=cli.mjs.map