@tinyrack/dotweave 0.42.13 → 0.42.21

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 (234) hide show
  1. package/README.md +6 -2
  2. package/dist/application.d.ts +0 -3
  3. package/dist/application.d.ts.map +1 -1
  4. package/dist/application.js +23 -22
  5. package/dist/application.js.map +1 -1
  6. package/dist/cli/autocomplete.d.ts +5 -4
  7. package/dist/cli/autocomplete.d.ts.map +1 -1
  8. package/dist/cli/autocomplete.js +33 -28
  9. package/dist/cli/autocomplete.js.map +1 -1
  10. package/dist/cli/cd.d.ts +2 -2
  11. package/dist/cli/cd.d.ts.map +1 -1
  12. package/dist/cli/cd.js +1 -4
  13. package/dist/cli/cd.js.map +1 -1
  14. package/dist/cli/doctor.d.ts +2 -2
  15. package/dist/cli/doctor.d.ts.map +1 -1
  16. package/dist/cli/doctor.js +19 -28
  17. package/dist/cli/doctor.js.map +1 -1
  18. package/dist/cli/index.d.ts +1 -3
  19. package/dist/cli/index.d.ts.map +1 -1
  20. package/dist/cli/index.js +5 -5
  21. package/dist/cli/index.js.map +1 -1
  22. package/dist/cli/init.d.ts +2 -2
  23. package/dist/cli/init.d.ts.map +1 -1
  24. package/dist/cli/init.js +9 -15
  25. package/dist/cli/init.js.map +1 -1
  26. package/dist/cli/profile/add.d.ts +4 -0
  27. package/dist/cli/profile/add.d.ts.map +1 -0
  28. package/dist/cli/profile/add.js +29 -0
  29. package/dist/cli/profile/add.js.map +1 -0
  30. package/dist/cli/profile/index.d.ts +1 -1
  31. package/dist/cli/profile/index.d.ts.map +1 -1
  32. package/dist/cli/profile/index.js +5 -1
  33. package/dist/cli/profile/index.js.map +1 -1
  34. package/dist/cli/profile/list.d.ts +2 -2
  35. package/dist/cli/profile/list.d.ts.map +1 -1
  36. package/dist/cli/profile/list.js +8 -26
  37. package/dist/cli/profile/list.js.map +1 -1
  38. package/dist/cli/profile/remove.d.ts +4 -0
  39. package/dist/cli/profile/remove.d.ts.map +1 -0
  40. package/dist/cli/profile/remove.js +29 -0
  41. package/dist/cli/profile/remove.js.map +1 -0
  42. package/dist/cli/profile/use.d.ts +2 -2
  43. package/dist/cli/profile/use.d.ts.map +1 -1
  44. package/dist/cli/profile/use.js +5 -14
  45. package/dist/cli/profile/use.js.map +1 -1
  46. package/dist/cli/pull.d.ts +2 -2
  47. package/dist/cli/pull.d.ts.map +1 -1
  48. package/dist/cli/pull.js +22 -41
  49. package/dist/cli/pull.js.map +1 -1
  50. package/dist/cli/push.d.ts +2 -2
  51. package/dist/cli/push.d.ts.map +1 -1
  52. package/dist/cli/push.js +17 -23
  53. package/dist/cli/push.js.map +1 -1
  54. package/dist/cli/root-commands.d.ts +9 -10
  55. package/dist/cli/root-commands.d.ts.map +1 -1
  56. package/dist/cli/root-commands.js +0 -4
  57. package/dist/cli/root-commands.js.map +1 -1
  58. package/dist/cli/shared-flags.d.ts +9 -0
  59. package/dist/cli/shared-flags.d.ts.map +1 -0
  60. package/dist/cli/shared-flags.js +8 -0
  61. package/dist/cli/shared-flags.js.map +1 -0
  62. package/dist/cli/status.d.ts +2 -2
  63. package/dist/cli/status.d.ts.map +1 -1
  64. package/dist/cli/status.js +26 -55
  65. package/dist/cli/status.js.map +1 -1
  66. package/dist/cli/track.d.ts +2 -2
  67. package/dist/cli/track.d.ts.map +1 -1
  68. package/dist/cli/track.js +19 -35
  69. package/dist/cli/track.js.map +1 -1
  70. package/dist/cli/untrack.d.ts +2 -2
  71. package/dist/cli/untrack.d.ts.map +1 -1
  72. package/dist/cli/untrack.js +5 -14
  73. package/dist/cli/untrack.js.map +1 -1
  74. package/dist/config/constants.d.ts +2 -2
  75. package/dist/config/constants.d.ts.map +1 -1
  76. package/dist/config/constants.js +2 -2
  77. package/dist/config/constants.js.map +1 -1
  78. package/dist/config/global-config.d.ts +3 -3
  79. package/dist/config/global-config.d.ts.map +1 -1
  80. package/dist/config/global-config.js +7 -8
  81. package/dist/config/global-config.js.map +1 -1
  82. package/dist/config/identity-file.d.ts +0 -7
  83. package/dist/config/identity-file.d.ts.map +1 -1
  84. package/dist/config/identity-file.js +2 -44
  85. package/dist/config/identity-file.js.map +1 -1
  86. package/dist/config/migration.d.ts +6 -0
  87. package/dist/config/migration.d.ts.map +1 -1
  88. package/dist/config/migration.js +35 -13
  89. package/dist/config/migration.js.map +1 -1
  90. package/dist/config/runtime-env.d.ts.map +1 -1
  91. package/dist/config/runtime-env.js +2 -7
  92. package/dist/config/runtime-env.js.map +1 -1
  93. package/dist/config/{sync-entry.d.ts → sync-queries.d.ts} +5 -3
  94. package/dist/config/sync-queries.d.ts.map +1 -0
  95. package/dist/config/{sync-entry.js → sync-queries.js} +15 -6
  96. package/dist/config/sync-queries.js.map +1 -0
  97. package/dist/config/sync-schema.d.ts +13 -8
  98. package/dist/config/sync-schema.d.ts.map +1 -1
  99. package/dist/config/sync-schema.js +138 -18
  100. package/dist/config/sync-schema.js.map +1 -1
  101. package/dist/config/xdg.d.ts.map +1 -1
  102. package/dist/config/xdg.js +15 -34
  103. package/dist/config/xdg.js.map +1 -1
  104. package/dist/lib/error.js +1 -1
  105. package/dist/lib/error.js.map +1 -1
  106. package/dist/lib/git.d.ts +3 -4
  107. package/dist/lib/git.d.ts.map +1 -1
  108. package/dist/lib/git.js +7 -48
  109. package/dist/lib/git.js.map +1 -1
  110. package/dist/lib/jsonc.d.ts +1 -1
  111. package/dist/lib/jsonc.d.ts.map +1 -1
  112. package/dist/lib/jsonc.js +1 -1
  113. package/dist/lib/jsonc.js.map +1 -1
  114. package/dist/lib/path.d.ts +3 -16
  115. package/dist/lib/path.d.ts.map +1 -1
  116. package/dist/lib/path.js +36 -19
  117. package/dist/lib/path.js.map +1 -1
  118. package/dist/lib/string.d.ts +1 -4
  119. package/dist/lib/string.d.ts.map +1 -1
  120. package/dist/lib/string.js +6 -4
  121. package/dist/lib/string.js.map +1 -1
  122. package/dist/lib/version.d.ts.map +1 -1
  123. package/dist/lib/version.js +2 -2
  124. package/dist/lib/version.js.map +1 -1
  125. package/dist/migrations/sync-v8.d.ts +3 -0
  126. package/dist/migrations/sync-v8.d.ts.map +1 -0
  127. package/dist/migrations/sync-v8.js +66 -0
  128. package/dist/migrations/sync-v8.js.map +1 -0
  129. package/dist/services/autocomplete.js +13 -13
  130. package/dist/services/autocomplete.js.map +1 -1
  131. package/dist/services/config-file.d.ts +6 -5
  132. package/dist/services/config-file.d.ts.map +1 -1
  133. package/dist/services/config-file.js +9 -8
  134. package/dist/services/config-file.js.map +1 -1
  135. package/dist/services/doctor.d.ts +1 -4
  136. package/dist/services/doctor.d.ts.map +1 -1
  137. package/dist/services/doctor.js +10 -37
  138. package/dist/services/doctor.js.map +1 -1
  139. package/dist/services/init.d.ts +1 -5
  140. package/dist/services/init.d.ts.map +1 -1
  141. package/dist/services/init.js +25 -59
  142. package/dist/services/init.js.map +1 -1
  143. package/dist/services/local-snapshot.d.ts +2 -7
  144. package/dist/services/local-snapshot.d.ts.map +1 -1
  145. package/dist/services/local-snapshot.js +12 -35
  146. package/dist/services/local-snapshot.js.map +1 -1
  147. package/dist/services/profile.d.ts +8 -4
  148. package/dist/services/profile.d.ts.map +1 -1
  149. package/dist/services/profile.js +110 -34
  150. package/dist/services/profile.js.map +1 -1
  151. package/dist/services/pull-apply.d.ts +30 -0
  152. package/dist/services/pull-apply.d.ts.map +1 -0
  153. package/dist/services/{local-materialization.js → pull-apply.js} +150 -210
  154. package/dist/services/pull-apply.js.map +1 -0
  155. package/dist/services/pull.d.ts +7 -10
  156. package/dist/services/pull.d.ts.map +1 -1
  157. package/dist/services/pull.js +19 -30
  158. package/dist/services/pull.js.map +1 -1
  159. package/dist/services/push.d.ts +4 -7
  160. package/dist/services/push.d.ts.map +1 -1
  161. package/dist/services/push.js +15 -38
  162. package/dist/services/push.js.map +1 -1
  163. package/dist/services/repo-artifacts.d.ts +5 -6
  164. package/dist/services/repo-artifacts.d.ts.map +1 -1
  165. package/dist/services/repo-artifacts.js +21 -60
  166. package/dist/services/repo-artifacts.js.map +1 -1
  167. package/dist/services/repo-snapshot.d.ts +2 -3
  168. package/dist/services/repo-snapshot.d.ts.map +1 -1
  169. package/dist/services/repo-snapshot.js +14 -26
  170. package/dist/services/repo-snapshot.js.map +1 -1
  171. package/dist/services/status.d.ts +1 -5
  172. package/dist/services/status.d.ts.map +1 -1
  173. package/dist/services/status.js +7 -17
  174. package/dist/services/status.js.map +1 -1
  175. package/dist/services/{runtime.d.ts → sync-context.d.ts} +9 -3
  176. package/dist/services/sync-context.d.ts.map +1 -0
  177. package/dist/services/{runtime.js → sync-context.js} +24 -8
  178. package/dist/services/sync-context.js.map +1 -0
  179. package/dist/services/{set.d.ts → sync-mode.d.ts} +7 -9
  180. package/dist/services/sync-mode.d.ts.map +1 -0
  181. package/dist/services/{set.js → sync-mode.js} +9 -23
  182. package/dist/services/sync-mode.js.map +1 -0
  183. package/dist/services/{paths.d.ts → sync-paths.d.ts} +2 -2
  184. package/dist/services/sync-paths.d.ts.map +1 -0
  185. package/dist/services/{paths.js → sync-paths.js} +4 -6
  186. package/dist/services/sync-paths.js.map +1 -0
  187. package/dist/services/terminal/logger.d.ts +30 -5
  188. package/dist/services/terminal/logger.d.ts.map +1 -1
  189. package/dist/services/terminal/logger.js +61 -14
  190. package/dist/services/terminal/logger.js.map +1 -1
  191. package/dist/services/terminal/path-completion.d.ts +2 -2
  192. package/dist/services/terminal/path-completion.d.ts.map +1 -1
  193. package/dist/services/terminal/path-completion.js +16 -13
  194. package/dist/services/terminal/path-completion.js.map +1 -1
  195. package/dist/services/terminal/shell.d.ts +1 -12
  196. package/dist/services/terminal/shell.d.ts.map +1 -1
  197. package/dist/services/terminal/shell.js +7 -160
  198. package/dist/services/terminal/shell.js.map +1 -1
  199. package/dist/services/terminal/spinner.d.ts +10 -0
  200. package/dist/services/terminal/spinner.d.ts.map +1 -0
  201. package/dist/services/terminal/spinner.js +61 -0
  202. package/dist/services/terminal/spinner.js.map +1 -0
  203. package/dist/services/terminal/theme.d.ts +31 -0
  204. package/dist/services/terminal/theme.d.ts.map +1 -0
  205. package/dist/services/terminal/theme.js +32 -0
  206. package/dist/services/terminal/theme.js.map +1 -0
  207. package/dist/services/track.d.ts +1 -3
  208. package/dist/services/track.d.ts.map +1 -1
  209. package/dist/services/track.js +27 -23
  210. package/dist/services/track.js.map +1 -1
  211. package/dist/services/untrack.d.ts +0 -2
  212. package/dist/services/untrack.d.ts.map +1 -1
  213. package/dist/services/untrack.js +4 -11
  214. package/dist/services/untrack.js.map +1 -1
  215. package/package.json +1 -2
  216. package/dist/config/sync-entry.d.ts.map +0 -1
  217. package/dist/config/sync-entry.js.map +0 -1
  218. package/dist/config/sync.d.ts +0 -8
  219. package/dist/config/sync.d.ts.map +0 -1
  220. package/dist/config/sync.js +0 -53
  221. package/dist/config/sync.js.map +0 -1
  222. package/dist/services/local-materialization.d.ts +0 -30
  223. package/dist/services/local-materialization.d.ts.map +0 -1
  224. package/dist/services/local-materialization.js.map +0 -1
  225. package/dist/services/paths.d.ts.map +0 -1
  226. package/dist/services/paths.js.map +0 -1
  227. package/dist/services/runtime.d.ts.map +0 -1
  228. package/dist/services/runtime.js.map +0 -1
  229. package/dist/services/set.d.ts.map +0 -1
  230. package/dist/services/set.js.map +0 -1
  231. package/dist/services/terminal/cli-runtime.d.ts +0 -18
  232. package/dist/services/terminal/cli-runtime.d.ts.map +0 -1
  233. package/dist/services/terminal/cli-runtime.js +0 -19
  234. package/dist/services/terminal/cli-runtime.js.map +0 -1
@@ -1,5 +1,11 @@
1
1
  export type ConfigMigrationFn = (config: Record<string, unknown>) => Record<string, unknown>;
2
2
  export type ConfigMigrationRegistry = ReadonlyMap<number, ConfigMigrationFn>;
3
+ export type ConfigMigrationResult = Readonly<{
4
+ config: unknown;
5
+ migrated: boolean;
6
+ originalVersion?: number;
7
+ }>;
8
+ export declare const applyConfigMigrations: (rawConfig: unknown, registry: ConfigMigrationRegistry, targetVersion: number, filePath: string) => ConfigMigrationResult;
3
9
  /**
4
10
  * Applies sequential config migrations from the detected version up to targetVersion.
5
11
  * Creates a backup file before the first migration step, then saves the result.
@@ -1 +1 @@
1
- {"version":3,"file":"migration.d.ts","sourceRoot":"","sources":["../../src/config/migration.ts"],"names":[],"mappings":"AAOA,MAAM,MAAM,iBAAiB,GAAG,CAC9B,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAC5B,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;AAE7B,MAAM,MAAM,uBAAuB,GAAG,WAAW,CAAC,MAAM,EAAE,iBAAiB,CAAC,CAAC;AAE7E;;;;GAIG;AACH,eAAO,MAAM,mBAAmB,GAC9B,WAAW,OAAO,EAClB,UAAU,uBAAuB,EACjC,eAAe,MAAM,EACrB,UAAU,MAAM,KACf,OAAO,CAAC,OAAO,CAgFjB,CAAC"}
1
+ {"version":3,"file":"migration.d.ts","sourceRoot":"","sources":["../../src/config/migration.ts"],"names":[],"mappings":"AAOA,MAAM,MAAM,iBAAiB,GAAG,CAC9B,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAC5B,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;AAE7B,MAAM,MAAM,uBAAuB,GAAG,WAAW,CAAC,MAAM,EAAE,iBAAiB,CAAC,CAAC;AAE7E,MAAM,MAAM,qBAAqB,GAAG,QAAQ,CAAC;IAC3C,MAAM,EAAE,OAAO,CAAC;IAChB,QAAQ,EAAE,OAAO,CAAC;IAClB,eAAe,CAAC,EAAE,MAAM,CAAC;CAC1B,CAAC,CAAC;AAkBH,eAAO,MAAM,qBAAqB,GAChC,WAAW,OAAO,EAClB,UAAU,uBAAuB,EACjC,eAAe,MAAM,EACrB,UAAU,MAAM,KACf,qBAsEF,CAAC;AAEF;;;;GAIG;AACH,eAAO,MAAM,mBAAmB,GAC9B,WAAW,OAAO,EAClB,UAAU,uBAAuB,EACjC,eAAe,MAAM,EACrB,UAAU,MAAM,KACf,OAAO,CAAC,OAAO,CA4BjB,CAAC"}
@@ -3,25 +3,31 @@ import { basename, dirname, join } from "node:path";
3
3
  import { DotweaveError } from "#app/lib/error.ts";
4
4
  import { writeTextFileAtomically } from "#app/lib/filesystem.ts";
5
5
  import { ensureTrailingNewline } from "#app/lib/string.ts";
6
- /**
7
- * Applies sequential config migrations from the detected version up to targetVersion.
8
- * Creates a backup file before the first migration step, then saves the result.
9
- * Returns the migrated config (or the original if no migration was needed).
10
- */
11
- export const runConfigMigrations = async (rawConfig, registry, targetVersion, filePath) => {
6
+ const withMigrationContext = (error, filePath, fromVersion) => {
7
+ return new DotweaveError(error.message, {
8
+ code: error.code,
9
+ details: [
10
+ ...error.details,
11
+ `Config file: ${filePath}`,
12
+ `Migration: ${fromVersion} → ${fromVersion + 1}`,
13
+ ],
14
+ hint: error.hint,
15
+ });
16
+ };
17
+ export const applyConfigMigrations = (rawConfig, registry, targetVersion, filePath) => {
12
18
  if (typeof rawConfig !== "object" ||
13
19
  rawConfig === null ||
14
20
  Array.isArray(rawConfig)) {
15
- return rawConfig;
21
+ return { config: rawConfig, migrated: false };
16
22
  }
17
23
  const configObject = rawConfig;
18
24
  // biome-ignore lint/complexity/useLiteralKeys: noPropertyAccessFromIndexSignature requires bracket notation
19
25
  const version = configObject["version"];
20
26
  if (typeof version !== "number") {
21
- return rawConfig;
27
+ return { config: rawConfig, migrated: false };
22
28
  }
23
29
  if (version === targetVersion) {
24
- return rawConfig;
30
+ return { config: rawConfig, migrated: false, originalVersion: version };
25
31
  }
26
32
  if (version > targetVersion) {
27
33
  throw new DotweaveError(`Config file version ${version} is newer than this CLI supports (max: ${targetVersion}).`, {
@@ -30,8 +36,6 @@ export const runConfigMigrations = async (rawConfig, registry, targetVersion, fi
30
36
  hint: "Upgrade dotweave to the latest version.",
31
37
  });
32
38
  }
33
- const backupPath = join(dirname(filePath), `${basename(filePath)}.v${version}.bak`);
34
- await writeFile(backupPath, ensureTrailingNewline(JSON.stringify(configObject, null, 2)), "utf8");
35
39
  let current = configObject;
36
40
  for (let v = version; v < targetVersion; v++) {
37
41
  const migrateFn = registry.get(v);
@@ -46,16 +50,34 @@ export const runConfigMigrations = async (rawConfig, registry, targetVersion, fi
46
50
  current = migrateFn(current);
47
51
  }
48
52
  catch (error) {
53
+ if (error instanceof DotweaveError) {
54
+ throw withMigrationContext(error, filePath, v);
55
+ }
49
56
  throw new DotweaveError(`Failed to migrate config from version ${v} to ${v + 1}.`, {
50
57
  code: "CONFIG_MIGRATION_FAILED",
51
58
  details: [
52
59
  `Config file: ${filePath}`,
60
+ `Migration: ${v} → ${v + 1}`,
53
61
  ...(error instanceof Error ? [error.message] : []),
54
62
  ],
55
63
  });
56
64
  }
57
65
  }
58
- await writeTextFileAtomically(filePath, ensureTrailingNewline(JSON.stringify(current, null, 2)));
59
- return current;
66
+ return { config: current, migrated: true, originalVersion: version };
67
+ };
68
+ /**
69
+ * Applies sequential config migrations from the detected version up to targetVersion.
70
+ * Creates a backup file before the first migration step, then saves the result.
71
+ * Returns the migrated config (or the original if no migration was needed).
72
+ */
73
+ export const runConfigMigrations = async (rawConfig, registry, targetVersion, filePath) => {
74
+ const { config, migrated, originalVersion } = applyConfigMigrations(rawConfig, registry, targetVersion, filePath);
75
+ if (!migrated || originalVersion === undefined) {
76
+ return config;
77
+ }
78
+ const backupPath = join(dirname(filePath), `${basename(filePath)}.v${originalVersion}.bak`);
79
+ await writeFile(backupPath, ensureTrailingNewline(JSON.stringify(rawConfig, null, 2)), "utf8");
80
+ await writeTextFileAtomically(filePath, ensureTrailingNewline(JSON.stringify(config, null, 2)));
81
+ return config;
60
82
  };
61
83
  //# sourceMappingURL=migration.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"migration.js","sourceRoot":"","sources":["../../src/config/migration.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"migration.js","sourceRoot":"","sources":["../../src/config/migration.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"runtime-env.d.ts","sourceRoot":"","sources":["../../src/config/runtime-env.ts"],"names":[],"mappings":"AAoBA,eAAO,MAAM,YAAY,GAAI,MAAM,MAAM,uBAExC,CAAC;AAEF,eAAO,MAAM,2BAA2B,cAEvC,CAAC;AAEF,eAAO,MAAM,2BAA2B,cAKvC,CAAC;AAEF,eAAO,MAAM,0CAA0C,cAKtD,CAAC;AAEF,eAAO,MAAM,mCAAmC,cAK/C,CAAC;AAEF,eAAO,MAAM,yBAAyB,qDAOrC,CAAC"}
1
+ {"version":3,"file":"runtime-env.d.ts","sourceRoot":"","sources":["../../src/config/runtime-env.ts"],"names":[],"mappings":"AAaA,eAAO,MAAM,YAAY,GAAI,MAAM,MAAM,uBAExC,CAAC;AAEF,eAAO,MAAM,2BAA2B,cAEvC,CAAC;AAEF,eAAO,MAAM,2BAA2B,cAKvC,CAAC;AAEF,eAAO,MAAM,0CAA0C,cAKtD,CAAC;AAEF,eAAO,MAAM,mCAAmC,cAK/C,CAAC;AAEF,eAAO,MAAM,yBAAyB,qDAOrC,CAAC"}
@@ -2,14 +2,9 @@ import { platform, release } from "node:os";
2
2
  import { detectCurrentPlatformKey } from "#app/config/platform.ts";
3
3
  import { resolveDotweaveConfigDirectory, resolveDotweaveGlobalConfigFilePath, resolveDotweaveSyncDirectory, resolveHomeDirectory, resolveXdgConfigHome, } from "#app/config/xdg.ts";
4
4
  import { ENV } from "#app/lib/env.ts";
5
- const trimConfiguredValue = (value) => {
6
- const trimmedValue = value?.trim();
7
- return trimmedValue === undefined || trimmedValue === ""
8
- ? undefined
9
- : trimmedValue;
10
- };
5
+ import { normalizeConfiguredValue } from "#app/lib/string.ts";
11
6
  export const readEnvValue = (name) => {
12
- return trimConfiguredValue(ENV[name]);
7
+ return normalizeConfiguredValue(ENV[name]);
13
8
  };
14
9
  export const resolveHomeDirectoryFromEnv = () => {
15
10
  return resolveHomeDirectory(readEnvValue("HOME"));
@@ -1 +1 @@
1
- {"version":3,"file":"runtime-env.js","sourceRoot":"","sources":["../../src/config/runtime-env.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC;AAE5C,OAAO,EAAE,wBAAwB,EAAE,MAAM,yBAAyB,CAAC;AACnE,OAAO,EACL,8BAA8B,EAC9B,mCAAmC,EACnC,4BAA4B,EAC5B,oBAAoB,EACpB,oBAAoB,GACrB,MAAM,oBAAoB,CAAC;AAC5B,OAAO,EAAE,GAAG,EAAE,MAAM,iBAAiB,CAAC;AAEtC,MAAM,mBAAmB,GAAG,CAAC,KAAyB,EAAE,EAAE;IACxD,MAAM,YAAY,GAAG,KAAK,EAAE,IAAI,EAAE,CAAC;IAEnC,OAAO,YAAY,KAAK,SAAS,IAAI,YAAY,KAAK,EAAE;QACtD,CAAC,CAAC,SAAS;QACX,CAAC,CAAC,YAAY,CAAC;AACnB,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,YAAY,GAAG,CAAC,IAAY,EAAE,EAAE;IAC3C,OAAO,mBAAmB,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC;AACxC,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,2BAA2B,GAAG,GAAG,EAAE;IAC9C,OAAO,oBAAoB,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC,CAAC;AACpD,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,2BAA2B,GAAG,GAAG,EAAE;IAC9C,OAAO,oBAAoB,CACzB,YAAY,CAAC,MAAM,CAAC,EACpB,YAAY,CAAC,iBAAiB,CAAC,CAChC,CAAC;AACJ,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,0CAA0C,GAAG,GAAG,EAAE;IAC7D,MAAM,eAAe,GAAG,8BAA8B,CACpD,2BAA2B,EAAE,CAC9B,CAAC;IACF,OAAO,mCAAmC,CAAC,eAAe,CAAC,CAAC;AAC9D,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,mCAAmC,GAAG,GAAG,EAAE;IACtD,MAAM,eAAe,GAAG,8BAA8B,CACpD,2BAA2B,EAAE,CAC9B,CAAC;IACF,OAAO,4BAA4B,CAAC,eAAe,CAAC,CAAC;AACvD,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,yBAAyB,GAAG,GAAG,EAAE;IAC5C,OAAO,wBAAwB,CAC7B,QAAQ,EAAE,EACV,OAAO,EAAE,EACT,YAAY,CAAC,iBAAiB,CAAC,EAC/B,YAAY,CAAC,aAAa,CAAC,CAC5B,CAAC;AACJ,CAAC,CAAC"}
1
+ {"version":3,"file":"runtime-env.js","sourceRoot":"","sources":["../../src/config/runtime-env.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC;AAE5C,OAAO,EAAE,wBAAwB,EAAE,MAAM,yBAAyB,CAAC;AACnE,OAAO,EACL,8BAA8B,EAC9B,mCAAmC,EACnC,4BAA4B,EAC5B,oBAAoB,EACpB,oBAAoB,GACrB,MAAM,oBAAoB,CAAC;AAC5B,OAAO,EAAE,GAAG,EAAE,MAAM,iBAAiB,CAAC;AACtC,OAAO,EAAE,wBAAwB,EAAE,MAAM,oBAAoB,CAAC;AAE9D,MAAM,CAAC,MAAM,YAAY,GAAG,CAAC,IAAY,EAAE,EAAE;IAC3C,OAAO,wBAAwB,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC;AAC7C,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,2BAA2B,GAAG,GAAG,EAAE;IAC9C,OAAO,oBAAoB,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC,CAAC;AACpD,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,2BAA2B,GAAG,GAAG,EAAE;IAC9C,OAAO,oBAAoB,CACzB,YAAY,CAAC,MAAM,CAAC,EACpB,YAAY,CAAC,iBAAiB,CAAC,CAChC,CAAC;AACJ,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,0CAA0C,GAAG,GAAG,EAAE;IAC7D,MAAM,eAAe,GAAG,8BAA8B,CACpD,2BAA2B,EAAE,CAC9B,CAAC;IACF,OAAO,mCAAmC,CAAC,eAAe,CAAC,CAAC;AAC9D,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,mCAAmC,GAAG,GAAG,EAAE;IACtD,MAAM,eAAe,GAAG,8BAA8B,CACpD,2BAA2B,EAAE,CAC9B,CAAC;IACF,OAAO,4BAA4B,CAAC,eAAe,CAAC,CAAC;AACvD,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,yBAAyB,GAAG,GAAG,EAAE;IAC5C,OAAO,wBAAwB,CAC7B,QAAQ,EAAE,EACV,OAAO,EAAE,EACT,YAAY,CAAC,iBAAiB,CAAC,EAC/B,YAAY,CAAC,aAAa,CAAC,CAC5B,CAAC;AACJ,CAAC,CAAC"}
@@ -1,4 +1,4 @@
1
- import type { ResolvedSyncConfig, ResolvedSyncConfigEntry, SyncMode } from "#app/config/sync-schema.ts";
1
+ import type { PlatformSyncMode, ResolvedSyncConfig, ResolvedSyncConfigEntry, SyncMode } from "#app/config/sync-schema.ts";
2
2
  export declare const findOwningSyncEntry: (config: Pick<ResolvedSyncConfig, "entries">, repoPath: string) => ResolvedSyncConfigEntry | undefined;
3
3
  export declare const collectChildEntryPaths: (config: Pick<ResolvedSyncConfig, "entries">, repoPath: string) => ReadonlySet<string>;
4
4
  export declare const resolveEntryRelativeRepoPath: (entry: Pick<ResolvedSyncConfigEntry, "kind" | "repoPath">, repoPath: string) => string | undefined;
@@ -9,6 +9,8 @@ export declare const resolveSyncRule: (config: ResolvedSyncConfig, repoPath: str
9
9
  export declare const resolveSyncMode: (config: ResolvedSyncConfig, repoPath: string, activeProfile?: string) => SyncMode | undefined;
10
10
  export declare const isIgnoredSyncPath: (config: ResolvedSyncConfig, repoPath: string) => boolean;
11
11
  export declare const isSecretSyncPath: (config: ResolvedSyncConfig, repoPath: string) => boolean;
12
- export declare const resolveManagedSyncMode: (config: ResolvedSyncConfig, repoPath: string, activeProfile?: string, context?: string) => "normal" | "secret" | "ignore";
12
+ export declare const requireManagedSyncMode: (config: ResolvedSyncConfig, repoPath: string, activeProfile?: string, context?: string) => "normal" | "secret" | "ignore";
13
+ export declare const buildDefaultPlatformMode: (mode: SyncMode) => PlatformSyncMode;
14
+ export declare const hasPlatformSpecificModeOverride: (configuredMode: PlatformSyncMode) => boolean;
13
15
  export declare const collectAllProfileNames: (entries: readonly ResolvedSyncConfigEntry[]) => string[];
14
- //# sourceMappingURL=sync-entry.d.ts.map
16
+ //# sourceMappingURL=sync-queries.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sync-queries.d.ts","sourceRoot":"","sources":["../../src/config/sync-queries.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EACV,gBAAgB,EAChB,kBAAkB,EAClB,uBAAuB,EACvB,QAAQ,EACT,MAAM,4BAA4B,CAAC;AAiBpC,eAAO,MAAM,mBAAmB,GAC9B,QAAQ,IAAI,CAAC,kBAAkB,EAAE,SAAS,CAAC,EAC3C,UAAU,MAAM,KACf,uBAAuB,GAAG,SAa5B,CAAC;AAEF,eAAO,MAAM,sBAAsB,GACjC,QAAQ,IAAI,CAAC,kBAAkB,EAAE,SAAS,CAAC,EAC3C,UAAU,MAAM,KACf,WAAW,CAAC,MAAM,CASpB,CAAC;AAEF,eAAO,MAAM,4BAA4B,GACvC,OAAO,IAAI,CAAC,uBAAuB,EAAE,MAAM,GAAG,UAAU,CAAC,EACzD,UAAU,MAAM,uBAejB,CAAC;AAuBF,eAAO,MAAM,eAAe,GAC1B,QAAQ,kBAAkB,EAC1B,UAAU,MAAM,EAChB,gBAAgB,MAAM,KACrB;IAAE,IAAI,EAAE,QAAQ,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAE,GAAG,SAcxC,CAAC;AAEF,eAAO,MAAM,eAAe,GAC1B,QAAQ,kBAAkB,EAC1B,UAAU,MAAM,EAChB,gBAAgB,MAAM,KACrB,QAAQ,GAAG,SAEb,CAAC;AAEF,eAAO,MAAM,iBAAiB,GAC5B,QAAQ,kBAAkB,EAC1B,UAAU,MAAM,YAGjB,CAAC;AAEF,eAAO,MAAM,gBAAgB,GAC3B,QAAQ,kBAAkB,EAC1B,UAAU,MAAM,YAGjB,CAAC;AAEF,eAAO,MAAM,sBAAsB,GACjC,QAAQ,kBAAkB,EAC1B,UAAU,MAAM,EAChB,gBAAgB,MAAM,EACtB,UAAU,MAAM,mCAmBjB,CAAC;AAMF,eAAO,MAAM,wBAAwB,GAAI,MAAM,QAAQ,KAAG,gBAExD,CAAC;AAEH,eAAO,MAAM,+BAA+B,GAC1C,gBAAgB,gBAAgB,YAQjC,CAAC;AAEF,eAAO,MAAM,sBAAsB,GACjC,SAAS,SAAS,uBAAuB,EAAE,KAC1C,MAAM,EAUR,CAAC"}
@@ -1,4 +1,4 @@
1
- import { CONSTANTS } from "#app/config/constants.ts";
1
+ import { AppConstants } from "#app/config/constants.ts";
2
2
  import { DotweaveError } from "#app/lib/error.ts";
3
3
  // ---------------------------------------------------------------------------
4
4
  // Entry lookup
@@ -42,12 +42,12 @@ export const resolveEntryRelativeRepoPath = (entry, repoPath) => {
42
42
  // ---------------------------------------------------------------------------
43
43
  const resolveProfileForEntry = (entry, activeProfile) => {
44
44
  if (entry.profiles.length === 0) {
45
- return CONSTANTS.SYNC.DEFAULT_PROFILE;
45
+ return AppConstants.SYNC.DEFAULT_PROFILE;
46
46
  }
47
47
  const effective = activeProfile !== undefined &&
48
- activeProfile !== CONSTANTS.SYNC.DEFAULT_PROFILE
48
+ activeProfile !== AppConstants.SYNC.DEFAULT_PROFILE
49
49
  ? activeProfile
50
- : CONSTANTS.SYNC.DEFAULT_PROFILE;
50
+ : AppConstants.SYNC.DEFAULT_PROFILE;
51
51
  return entry.profiles.includes(effective) ? effective : undefined;
52
52
  };
53
53
  export const resolveSyncRule = (config, repoPath, activeProfile) => {
@@ -70,7 +70,7 @@ export const isIgnoredSyncPath = (config, repoPath) => {
70
70
  export const isSecretSyncPath = (config, repoPath) => {
71
71
  return resolveSyncMode(config, repoPath) === "secret";
72
72
  };
73
- export const resolveManagedSyncMode = (config, repoPath, activeProfile, context) => {
73
+ export const requireManagedSyncMode = (config, repoPath, activeProfile, context) => {
74
74
  const mode = resolveSyncMode(config, repoPath, activeProfile);
75
75
  if (mode === undefined) {
76
76
  throw new DotweaveError("Repository path is not managed by the current sync configuration.", {
@@ -87,6 +87,15 @@ export const resolveManagedSyncMode = (config, repoPath, activeProfile, context)
87
87
  // ---------------------------------------------------------------------------
88
88
  // Profile collection
89
89
  // ---------------------------------------------------------------------------
90
+ export const buildDefaultPlatformMode = (mode) => ({
91
+ default: mode,
92
+ });
93
+ export const hasPlatformSpecificModeOverride = (configuredMode) => {
94
+ return (configuredMode.win !== undefined ||
95
+ configuredMode.mac !== undefined ||
96
+ configuredMode.linux !== undefined ||
97
+ configuredMode.wsl !== undefined);
98
+ };
90
99
  export const collectAllProfileNames = (entries) => {
91
100
  const profiles = new Set();
92
101
  for (const entry of entries) {
@@ -96,4 +105,4 @@ export const collectAllProfileNames = (entries) => {
96
105
  }
97
106
  return [...profiles].sort((left, right) => left.localeCompare(right));
98
107
  };
99
- //# sourceMappingURL=sync-entry.js.map
108
+ //# sourceMappingURL=sync-queries.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sync-queries.js","sourceRoot":"","sources":["../../src/config/sync-queries.ts"],"names":[],"mappings":"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"}
@@ -1,5 +1,5 @@
1
1
  import { z } from "zod";
2
- import { CONSTANTS } from "#app/config/constants.ts";
2
+ import { AppConstants } from "#app/config/constants.ts";
3
3
  import { type PlatformKey, type PlatformStringValue } from "#app/config/platform.ts";
4
4
  declare const platformSyncModeSchema: z.ZodObject<{
5
5
  default: z.ZodEnum<{
@@ -35,11 +35,12 @@ declare const platformPermissionSchema: z.ZodObject<{
35
35
  linux: z.ZodOptional<z.ZodString>;
36
36
  wsl: z.ZodOptional<z.ZodString>;
37
37
  }, z.core.$strip>;
38
- declare const syncConfigSchema: z.ZodObject<{
39
- version: z.ZodLiteral<7>;
38
+ export declare const syncConfigSchema: z.ZodObject<{
39
+ version: z.ZodUnion<readonly [z.ZodLiteral<7>, z.ZodLiteral<8>]>;
40
40
  age: z.ZodOptional<z.ZodObject<{
41
41
  recipients: z.ZodArray<z.ZodString>;
42
42
  }, z.core.$strip>>;
43
+ profiles: z.ZodDefault<z.ZodArray<z.ZodString>>;
43
44
  entries: z.ZodArray<z.ZodObject<{
44
45
  kind: z.ZodEnum<{
45
46
  file: "file";
@@ -98,11 +99,11 @@ declare const syncConfigSchema: z.ZodObject<{
98
99
  }, z.core.$strip>;
99
100
  declare const syncEntryKinds: readonly ["file", "directory"];
100
101
  export type SyncConfigEntryKind = (typeof syncEntryKinds)[number];
101
- export type SyncMode = (typeof CONSTANTS.SYNC.MODES)[number];
102
+ export type SyncMode = (typeof AppConstants.SYNC.MODES)[number];
102
103
  export type ConfiguredSyncRepoPath = PlatformStringValue;
103
104
  export type PlatformSyncMode = z.infer<typeof platformSyncModeSchema>;
104
105
  export type PlatformPermission = z.infer<typeof platformPermissionSchema>;
105
- export type SyncConfig = z.infer<typeof syncConfigSchema>;
106
+ export type RawSyncConfig = z.infer<typeof syncConfigSchema>;
106
107
  export type SyncConfigResolutionContext = Readonly<{
107
108
  homeDirectory: string;
108
109
  platformKey: PlatformKey;
@@ -130,17 +131,21 @@ export type AgeConfig = Readonly<{
130
131
  export type ResolvedSyncConfig = Readonly<{
131
132
  age?: AgeConfig;
132
133
  entries: readonly ResolvedSyncConfigEntry[];
133
- version: typeof CONSTANTS.SYNC.CONFIG_VERSION;
134
+ profiles?: readonly string[];
135
+ version: 7 | typeof AppConstants.SYNC.CONFIG_VERSION;
134
136
  }>;
135
137
  export declare const normalizeSyncRepoPath: (value: string) => string;
136
138
  export declare const normalizeSyncProfileName: (value: string, description?: string) => string;
137
139
  export declare const hasReservedSyncArtifactSuffixSegment: (value: string) => boolean;
138
140
  export declare const deriveRepoPathFromLocalPath: (localPath: PlatformStringValue, homeDirectory: string) => string;
139
141
  export declare const validateResolvedSyncConfigEntries: (entries: readonly ResolvedSyncConfigEntry[]) => void;
142
+ export declare const validateRawSyncConfigProfileRegistry: (config: Pick<RawSyncConfig, "entries" | "profiles">) => string[];
140
143
  export declare const parseSyncConfig: (input: unknown, context: SyncConfigResolutionContext) => ResolvedSyncConfig;
141
144
  export declare const createInitialSyncConfig: (age: {
142
145
  recipients: string[];
143
- }) => SyncConfig;
144
- export declare const formatSyncConfig: (config: SyncConfig) => string;
146
+ }) => RawSyncConfig;
147
+ export declare const formatSyncConfig: (config: RawSyncConfig) => string;
148
+ export declare const resolveSyncConfigFilePath: (syncDirectory: string) => string;
149
+ export declare const readSyncConfig: (syncDirectory: string, context: SyncConfigResolutionContext) => Promise<ResolvedSyncConfig>;
145
150
  export {};
146
151
  //# sourceMappingURL=sync-schema.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"sync-schema.d.ts","sourceRoot":"","sources":["../../src/config/sync-schema.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"sync-schema.d.ts","sourceRoot":"","sources":["../../src/config/sync-schema.ts"],"names":[],"mappings":"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"}
@@ -1,13 +1,19 @@
1
- import { isAbsolute, posix, relative, sep } from "node:path";
1
+ import { readFile, writeFile } from "node:fs/promises";
2
+ import { basename, dirname, isAbsolute, join, posix, relative, sep, } from "node:path";
2
3
  import { z } from "zod";
3
- import { CONSTANTS } from "#app/config/constants.ts";
4
+ import { AppConstants } from "#app/config/constants.ts";
5
+ import { applyConfigMigrations } from "#app/config/migration.ts";
4
6
  import { resolvePlatformValue, } from "#app/config/platform.ts";
5
7
  import { resolveConfiguredAbsolutePath } from "#app/config/xdg.ts";
6
8
  import { DotweaveError } from "#app/lib/error.ts";
7
9
  import { parsePermissionOctal } from "#app/lib/file-mode.ts";
10
+ import { writeTextFileAtomically } from "#app/lib/filesystem.ts";
11
+ import { parseJsonc, validateJsoncConfigPath } from "#app/lib/jsonc.ts";
8
12
  import { doPathsOverlap } from "#app/lib/path.ts";
9
13
  import { ensureTrailingNewline } from "#app/lib/string.ts";
10
14
  import { formatInputIssues } from "#app/lib/validation.ts";
15
+ import { migrateSyncConfigV7ToV8 } from "#app/migrations/sync-v8.ts";
16
+ const syncConfigMigrationRegistry = new Map([[7, migrateSyncConfigV7ToV8]]);
11
17
  // ---------------------------------------------------------------------------
12
18
  // Zod schemas
13
19
  // ---------------------------------------------------------------------------
@@ -18,6 +24,9 @@ const requiredTrimmedStringSchema = z
18
24
  const syncProfileNameArraySchema = z
19
25
  .array(requiredTrimmedStringSchema)
20
26
  .min(1, "At least one profile must be specified.");
27
+ const syncProfileRegistrySchema = z
28
+ .array(requiredTrimmedStringSchema)
29
+ .default([]);
21
30
  const platformLocalPathSchema = z.object({
22
31
  default: requiredTrimmedStringSchema,
23
32
  win: requiredTrimmedStringSchema.optional(),
@@ -35,11 +44,11 @@ const platformRepoPathSchema = z.object({
35
44
  });
36
45
  const repoPathSchema = platformRepoPathSchema;
37
46
  const platformSyncModeSchema = z.object({
38
- default: z.enum(CONSTANTS.SYNC.MODES),
39
- win: z.enum(CONSTANTS.SYNC.MODES).optional(),
40
- mac: z.enum(CONSTANTS.SYNC.MODES).optional(),
41
- linux: z.enum(CONSTANTS.SYNC.MODES).optional(),
42
- wsl: z.enum(CONSTANTS.SYNC.MODES).optional(),
47
+ default: z.enum(AppConstants.SYNC.MODES),
48
+ win: z.enum(AppConstants.SYNC.MODES).optional(),
49
+ mac: z.enum(AppConstants.SYNC.MODES).optional(),
50
+ linux: z.enum(AppConstants.SYNC.MODES).optional(),
51
+ wsl: z.enum(AppConstants.SYNC.MODES).optional(),
43
52
  });
44
53
  const permissionOctalSchema = z
45
54
  .string()
@@ -65,11 +74,12 @@ const syncConfigAgeSchema = z.object({
65
74
  .min(1, "At least one age recipient is required."),
66
75
  });
67
76
  const syncConfigSchemaV7 = z.object({
68
- version: z.literal(CONSTANTS.SYNC.CONFIG_VERSION),
77
+ version: z.union([z.literal(7), z.literal(AppConstants.SYNC.CONFIG_VERSION)]),
69
78
  age: syncConfigAgeSchema.optional(),
79
+ profiles: syncProfileRegistrySchema,
70
80
  entries: z.array(syncConfigEntrySchema),
71
81
  });
72
- const syncConfigSchema = syncConfigSchemaV7;
82
+ export const syncConfigSchema = syncConfigSchemaV7;
73
83
  // ---------------------------------------------------------------------------
74
84
  // Exported types
75
85
  // ---------------------------------------------------------------------------
@@ -91,7 +101,7 @@ export const normalizeSyncRepoPath = (value) => {
91
101
  });
92
102
  }
93
103
  if (hasReservedSyncArtifactSuffixSegment(normalizedValue)) {
94
- throw new DotweaveError(`Repository path must not use the reserved suffix ${CONSTANTS.SYNC.SECRET_ARTIFACT_SUFFIX}.`, {
104
+ throw new DotweaveError(`Repository path must not use the reserved suffix ${AppConstants.SYNC.SECRET_ARTIFACT_SUFFIX}.`, {
95
105
  code: "RESERVED_SECRET_SUFFIX",
96
106
  details: [`Repository path: ${value}`],
97
107
  hint: "Rename the path so no segment ends with the secret artifact suffix.",
@@ -134,7 +144,7 @@ export const hasReservedSyncArtifactSuffixSegment = (value) => {
134
144
  return value
135
145
  .replaceAll("\\", "/")
136
146
  .split("/")
137
- .some((segment) => segment.endsWith(CONSTANTS.SYNC.SECRET_ARTIFACT_SUFFIX));
147
+ .some((segment) => segment.endsWith(AppConstants.SYNC.SECRET_ARTIFACT_SUFFIX));
138
148
  };
139
149
  export const deriveRepoPathFromLocalPath = (localPath, homeDirectory) => {
140
150
  const resolvedDefaultPath = resolveConfiguredAbsolutePath(localPath.default, homeDirectory, undefined);
@@ -160,8 +170,8 @@ const validatePathOverlaps = (entries, property, description) => {
160
170
  if (currentValue === otherValue) {
161
171
  const isRepoPath = property === "repoPath";
162
172
  throw new DotweaveError(isRepoPath
163
- ? `Multiple entries target the same repository path in ${CONSTANTS.SYNC.CONFIG_FILE_NAME}.`
164
- : `Duplicate ${description.toLowerCase()} paths in ${CONSTANTS.SYNC.CONFIG_FILE_NAME}.`, {
173
+ ? `Multiple entries target the same repository path in ${AppConstants.SYNC.CONFIG_FILE_NAME}.`
174
+ : `Duplicate ${description.toLowerCase()} paths in ${AppConstants.SYNC.CONFIG_FILE_NAME}.`, {
165
175
  code: "DUPLICATE_PATHS",
166
176
  details: isRepoPath
167
177
  ? [
@@ -174,7 +184,7 @@ const validatePathOverlaps = (entries, property, description) => {
174
184
  ],
175
185
  hint: isRepoPath
176
186
  ? "Each entry must use a unique repoPath. Change or remove one of the conflicting entries."
177
- : `Remove the duplicate entry from ${CONSTANTS.SYNC.CONFIG_FILE_NAME}.`,
187
+ : `Remove the duplicate entry from ${AppConstants.SYNC.CONFIG_FILE_NAME}.`,
178
188
  });
179
189
  }
180
190
  const isParentChild = currentValue.startsWith(`${otherValue}/`) ||
@@ -188,7 +198,7 @@ const validatePathOverlaps = (entries, property, description) => {
188
198
  ? false
189
199
  : doPathsOverlap(currentValue, otherValue);
190
200
  if (overlaps) {
191
- throw new DotweaveError(`${description} paths must not overlap in ${CONSTANTS.SYNC.CONFIG_FILE_NAME}.`, {
201
+ throw new DotweaveError(`${description} paths must not overlap in ${AppConstants.SYNC.CONFIG_FILE_NAME}.`, {
192
202
  code: "OVERLAPPING_PATHS",
193
203
  details: [
194
204
  `${currentEntry.repoPath}: ${currentValue}`,
@@ -204,10 +214,76 @@ export const validateResolvedSyncConfigEntries = (entries) => {
204
214
  validatePathOverlaps(entries, "repoPath", "Repository");
205
215
  validatePathOverlaps(entries, "localPath", "Local");
206
216
  };
217
+ const normalizeProfileRegistry = (profiles) => {
218
+ const normalizedProfiles = profiles.map((profile) => normalizeSyncProfileName(profile));
219
+ const seenProfiles = new Set();
220
+ for (const profile of normalizedProfiles) {
221
+ if (profile === AppConstants.SYNC.DEFAULT_PROFILE) {
222
+ throw new DotweaveError(`Profile '${AppConstants.SYNC.DEFAULT_PROFILE}' is implicit and must not be listed in manifest profiles.`, {
223
+ code: "INVALID_PROFILE_REGISTRY",
224
+ hint: `Remove '${AppConstants.SYNC.DEFAULT_PROFILE}' from profiles in ${AppConstants.SYNC.CONFIG_FILE_NAME}.`,
225
+ });
226
+ }
227
+ if (seenProfiles.has(profile)) {
228
+ throw new DotweaveError(`Duplicate profile '${profile}' in manifest.`, {
229
+ code: "DUPLICATE_PROFILE",
230
+ hint: `Remove duplicate profile names from profiles in ${AppConstants.SYNC.CONFIG_FILE_NAME}.`,
231
+ });
232
+ }
233
+ seenProfiles.add(profile);
234
+ }
235
+ return normalizedProfiles;
236
+ };
237
+ const validateProfileReferences = (references, profiles) => {
238
+ const availableProfiles = new Set([
239
+ AppConstants.SYNC.DEFAULT_PROFILE,
240
+ ...profiles,
241
+ ]);
242
+ for (const [entryLabel, entryProfiles] of references) {
243
+ for (const profile of entryProfiles) {
244
+ const normalizedProfile = normalizeSyncProfileName(profile);
245
+ if (!availableProfiles.has(normalizedProfile)) {
246
+ throw new DotweaveError(`Unknown profile '${normalizedProfile}'.`, {
247
+ code: "UNKNOWN_PROFILE",
248
+ details: [`Entry: ${entryLabel}`],
249
+ hint: `Add it with 'dotweave profile add ${normalizedProfile}', or remove it from the entry profiles.`,
250
+ });
251
+ }
252
+ }
253
+ }
254
+ };
255
+ const validateEntryProfileReferences = (entries, profiles) => {
256
+ validateProfileReferences(entries.map((entry) => [entry.repoPath, entry.profiles]), profiles);
257
+ };
258
+ export const validateRawSyncConfigProfileRegistry = (config) => {
259
+ const profiles = normalizeProfileRegistry(config.profiles ?? []);
260
+ validateProfileReferences(config.entries.map((entry, index) => [
261
+ entry.repoPath?.default ?? entry.localPath.default ?? `#${index}`,
262
+ entry.profiles ?? [],
263
+ ]), profiles);
264
+ return profiles;
265
+ };
266
+ const collectLegacyProfileRegistry = (entries) => {
267
+ const profiles = new Set();
268
+ for (const entry of entries) {
269
+ if (entry.profiles === undefined) {
270
+ continue;
271
+ }
272
+ for (const profile of entry.profiles) {
273
+ const normalizedProfile = normalizeSyncProfileName(profile);
274
+ if (normalizedProfile !== AppConstants.SYNC.DEFAULT_PROFILE) {
275
+ profiles.add(normalizedProfile);
276
+ }
277
+ }
278
+ }
279
+ return [...profiles].sort((left, right) => left.localeCompare(right));
280
+ };
207
281
  // ---------------------------------------------------------------------------
208
282
  // Internal parsing helpers
209
283
  // ---------------------------------------------------------------------------
210
- const defaultSyncMode = { default: CONSTANTS.SYNC.MODES[0] };
284
+ const defaultSyncMode = {
285
+ default: AppConstants.SYNC.MODES[0],
286
+ };
211
287
  const resolveSyncModeForPlatform = (configuredMode, platformKey) => {
212
288
  if (platformKey === "wsl") {
213
289
  return configuredMode.wsl ?? configuredMode.linux ?? configuredMode.default;
@@ -327,9 +403,12 @@ export const parseSyncConfig = (input, context) => {
327
403
  throw new DotweaveError("Sync configuration is invalid.", {
328
404
  code: "CONFIG_VALIDATION_FAILED",
329
405
  details: formatInputIssues(result.error.issues).split("\n"),
330
- hint: `Fix the invalid fields in ${CONSTANTS.SYNC.CONFIG_FILE_NAME}, then run the command again.`,
406
+ hint: `Fix the invalid fields in ${AppConstants.SYNC.CONFIG_FILE_NAME}, then run the command again.`,
331
407
  });
332
408
  }
409
+ const profiles = normalizeProfileRegistry(result.data.version === 7
410
+ ? collectLegacyProfileRegistry(result.data.entries)
411
+ : result.data.profiles);
333
412
  const rawEntries = result.data.entries.map((entry) => {
334
413
  const resolvedLocalPath = resolveSyncEntryLocalPath(entry.localPath, context);
335
414
  const configuredRepoPath = entry.repoPath === undefined
@@ -368,6 +447,7 @@ export const parseSyncConfig = (input, context) => {
368
447
  });
369
448
  validateResolvedSyncConfigEntries(rawEntries);
370
449
  const entries = applyEntryInheritance(rawEntries, platformKey);
450
+ validateEntryProfileReferences(entries, profiles);
371
451
  const age = result.data.age === undefined
372
452
  ? undefined
373
453
  : {
@@ -376,17 +456,57 @@ export const parseSyncConfig = (input, context) => {
376
456
  return {
377
457
  ...(age === undefined ? {} : { age }),
378
458
  entries,
459
+ profiles,
379
460
  version: result.data.version,
380
461
  };
381
462
  };
382
463
  export const createInitialSyncConfig = (age) => {
383
464
  return {
384
- version: CONSTANTS.SYNC.CONFIG_VERSION,
465
+ version: AppConstants.SYNC.CONFIG_VERSION,
385
466
  age,
467
+ profiles: [],
386
468
  entries: [],
387
469
  };
388
470
  };
389
471
  export const formatSyncConfig = (config) => {
390
472
  return ensureTrailingNewline(JSON.stringify(config, null, 2));
391
473
  };
474
+ export const resolveSyncConfigFilePath = (syncDirectory) => {
475
+ return join(syncDirectory, AppConstants.SYNC.CONFIG_FILE_NAME);
476
+ };
477
+ export const readSyncConfig = async (syncDirectory, context) => {
478
+ const filePath = await validateJsoncConfigPath(resolveSyncConfigFilePath(syncDirectory));
479
+ try {
480
+ const contents = await readFile(filePath, "utf8");
481
+ const parsed = parseJsonc(contents);
482
+ const migration = applyConfigMigrations(parsed, syncConfigMigrationRegistry, AppConstants.SYNC.CONFIG_VERSION, filePath);
483
+ const resolved = parseSyncConfig(migration.config, context);
484
+ if (migration.migrated && migration.originalVersion !== undefined) {
485
+ const backupPath = join(dirname(filePath), `${basename(filePath)}.v${migration.originalVersion}.bak`);
486
+ await writeFile(backupPath, ensureTrailingNewline(JSON.stringify(parsed, null, 2)), "utf8");
487
+ await writeTextFileAtomically(filePath, ensureTrailingNewline(JSON.stringify(migration.config, null, 2)));
488
+ }
489
+ return resolved;
490
+ }
491
+ catch (error) {
492
+ if (error instanceof DotweaveError) {
493
+ throw error;
494
+ }
495
+ if (error instanceof SyntaxError) {
496
+ throw new DotweaveError("Sync configuration is not valid JSON.", {
497
+ code: "CONFIG_INVALID_JSON",
498
+ details: [`Config file: ${filePath}`, error.message],
499
+ hint: `Fix the JSON syntax in ${AppConstants.SYNC.CONFIG_FILE_NAME}, then run the command again.`,
500
+ });
501
+ }
502
+ throw new DotweaveError("Failed to read sync configuration.", {
503
+ code: "CONFIG_READ_FAILED",
504
+ details: [
505
+ `Config file: ${filePath}`,
506
+ ...(error instanceof Error ? [error.message] : []),
507
+ ],
508
+ hint: "Run 'dotweave init' if the sync directory has not been initialized yet.",
509
+ });
510
+ }
511
+ };
392
512
  //# sourceMappingURL=sync-schema.js.map