@translation-cms/sync 1.2.9 → 1.2.12

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 (116) hide show
  1. package/README.md +304 -151
  2. package/dist/api.d.ts +79 -0
  3. package/dist/api.d.ts.map +1 -0
  4. package/dist/api.js +151 -0
  5. package/dist/api.js.map +1 -0
  6. package/dist/bin.js +51 -17
  7. package/dist/bin.js.map +1 -1
  8. package/dist/commands/init.d.ts +8 -0
  9. package/dist/commands/init.d.ts.map +1 -1
  10. package/dist/commands/init.js +18 -0
  11. package/dist/commands/init.js.map +1 -1
  12. package/dist/commands/pull.d.ts +7 -0
  13. package/dist/commands/pull.d.ts.map +1 -1
  14. package/dist/commands/pull.js +15 -2
  15. package/dist/commands/pull.js.map +1 -1
  16. package/dist/commands/status.d.ts +12 -0
  17. package/dist/commands/status.d.ts.map +1 -1
  18. package/dist/commands/status.js +16 -0
  19. package/dist/commands/status.js.map +1 -1
  20. package/dist/commands/sync.d.ts +10 -0
  21. package/dist/commands/sync.d.ts.map +1 -1
  22. package/dist/commands/sync.js +23 -4
  23. package/dist/commands/sync.js.map +1 -1
  24. package/dist/commands/watch.d.ts +14 -0
  25. package/dist/commands/watch.d.ts.map +1 -1
  26. package/dist/commands/watch.js +23 -3
  27. package/dist/commands/watch.js.map +1 -1
  28. package/dist/config/config-internals/args.d.ts +11 -0
  29. package/dist/config/config-internals/args.d.ts.map +1 -0
  30. package/dist/config/config-internals/args.js +22 -0
  31. package/dist/config/config-internals/args.js.map +1 -0
  32. package/dist/config/config-internals/env.d.ts +10 -0
  33. package/dist/config/config-internals/env.d.ts.map +1 -0
  34. package/dist/config/config-internals/env.js +35 -0
  35. package/dist/config/config-internals/env.js.map +1 -0
  36. package/dist/config/config-internals/file.d.ts +11 -0
  37. package/dist/config/config-internals/file.d.ts.map +1 -0
  38. package/dist/config/config-internals/file.js +28 -0
  39. package/dist/config/config-internals/file.js.map +1 -0
  40. package/dist/config/config-internals/resolve.d.ts +21 -0
  41. package/dist/config/config-internals/resolve.d.ts.map +1 -0
  42. package/dist/config/config-internals/resolve.js +73 -0
  43. package/dist/config/config-internals/resolve.js.map +1 -0
  44. package/dist/config/config-internals/root.d.ts +9 -0
  45. package/dist/config/config-internals/root.d.ts.map +1 -0
  46. package/dist/config/config-internals/root.js +22 -0
  47. package/dist/config/config-internals/root.js.map +1 -0
  48. package/dist/config/config-internals/types.d.ts +83 -0
  49. package/dist/config/config-internals/types.d.ts.map +1 -0
  50. package/dist/config/config-internals/types.js +9 -0
  51. package/dist/config/config-internals/types.js.map +1 -0
  52. package/dist/config/resolve-config.d.ts +9 -90
  53. package/dist/config/resolve-config.d.ts.map +1 -1
  54. package/dist/config/resolve-config.js +7 -123
  55. package/dist/config/resolve-config.js.map +1 -1
  56. package/dist/core/api-internals/pull.d.ts +9 -1
  57. package/dist/core/api-internals/pull.d.ts.map +1 -1
  58. package/dist/core/api-internals/pull.js +41 -28
  59. package/dist/core/api-internals/pull.js.map +1 -1
  60. package/dist/core/api-internals/sync.d.ts +9 -2
  61. package/dist/core/api-internals/sync.d.ts.map +1 -1
  62. package/dist/core/api-internals/sync.js +18 -2
  63. package/dist/core/api-internals/sync.js.map +1 -1
  64. package/dist/core/cache-internals/format.d.ts +16 -0
  65. package/dist/core/cache-internals/format.d.ts.map +1 -1
  66. package/dist/core/cache-internals/format.js +17 -0
  67. package/dist/core/cache-internals/format.js.map +1 -1
  68. package/dist/core/cache-internals/params.d.ts.map +1 -1
  69. package/dist/core/cache-internals/params.js +24 -24
  70. package/dist/core/cache-internals/params.js.map +1 -1
  71. package/dist/core/cache-internals/pull.d.ts +12 -0
  72. package/dist/core/cache-internals/pull.d.ts.map +1 -1
  73. package/dist/core/cache-internals/pull.js +13 -0
  74. package/dist/core/cache-internals/pull.js.map +1 -1
  75. package/dist/core/cache-internals/sync.d.ts +23 -0
  76. package/dist/core/cache-internals/sync.d.ts.map +1 -1
  77. package/dist/core/cache-internals/sync.js +33 -0
  78. package/dist/core/cache-internals/sync.js.map +1 -1
  79. package/dist/core/cache-internals/types.d.ts +20 -0
  80. package/dist/core/cache-internals/types.d.ts.map +1 -1
  81. package/dist/core/scanner-internals/ast.d.ts +23 -5
  82. package/dist/core/scanner-internals/ast.d.ts.map +1 -1
  83. package/dist/core/scanner-internals/ast.js +25 -5
  84. package/dist/core/scanner-internals/ast.js.map +1 -1
  85. package/dist/core/scanner-internals/file-walker.d.ts +3 -2
  86. package/dist/core/scanner-internals/file-walker.d.ts.map +1 -1
  87. package/dist/core/scanner-internals/file-walker.js +10 -12
  88. package/dist/core/scanner-internals/file-walker.js.map +1 -1
  89. package/dist/core/scanner-internals/import-resolver.d.ts +9 -1
  90. package/dist/core/scanner-internals/import-resolver.d.ts.map +1 -1
  91. package/dist/core/scanner-internals/import-resolver.js +58 -63
  92. package/dist/core/scanner-internals/import-resolver.js.map +1 -1
  93. package/dist/core/scanner-internals/key-extractor.d.ts +12 -8
  94. package/dist/core/scanner-internals/key-extractor.d.ts.map +1 -1
  95. package/dist/core/scanner-internals/key-extractor.js +125 -97
  96. package/dist/core/scanner-internals/key-extractor.js.map +1 -1
  97. package/dist/core/scanner-internals/route-detector.d.ts +16 -8
  98. package/dist/core/scanner-internals/route-detector.d.ts.map +1 -1
  99. package/dist/core/scanner-internals/route-detector.js +37 -33
  100. package/dist/core/scanner-internals/route-detector.js.map +1 -1
  101. package/dist/core/scanner.d.ts.map +1 -1
  102. package/dist/core/scanner.js +25 -8
  103. package/dist/core/scanner.js.map +1 -1
  104. package/dist/next.d.ts +28 -0
  105. package/dist/next.d.ts.map +1 -0
  106. package/dist/next.js +65 -0
  107. package/dist/next.js.map +1 -0
  108. package/dist/preview/internals/highlight.d.ts +16 -7
  109. package/dist/preview/internals/highlight.d.ts.map +1 -1
  110. package/dist/preview/internals/highlight.js +71 -60
  111. package/dist/preview/internals/highlight.js.map +1 -1
  112. package/dist/scaffold/intenrals/scaffold.d.ts +17 -0
  113. package/dist/scaffold/intenrals/scaffold.d.ts.map +1 -1
  114. package/dist/scaffold/intenrals/scaffold.js +19 -0
  115. package/dist/scaffold/intenrals/scaffold.js.map +1 -1
  116. package/package.json +16 -3
@@ -1 +1 @@
1
- {"version":3,"file":"sync.d.ts","sourceRoot":"","sources":["../../../src/core/api-internals/sync.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,gCAAgC,CAAC;AAC7D,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAClD,OAAO,KAAK,EAAE,iBAAiB,EAAgB,MAAM,YAAY,CAAC;AAYlE;;;GAGG;AACH,wBAAsB,UAAU,CAC5B,MAAM,EAAE,MAAM,EACd,UAAU,EAAE,YAAY,EACxB,IAAI,GAAE,iBAA2C,GAClD,OAAO,CAAC,IAAI,CAAC,CA+Hf"}
1
+ {"version":3,"file":"sync.d.ts","sourceRoot":"","sources":["../../../src/core/api-internals/sync.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,gCAAgC,CAAC;AAC7D,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAClD,OAAO,KAAK,EAAE,iBAAiB,EAAgB,MAAM,YAAY,CAAC;AAYlE;;;;;;;;;;GAUG;AACH,wBAAsB,UAAU,CAC5B,MAAM,EAAE,MAAM,EACd,UAAU,EAAE,YAAY,EACxB,IAAI,GAAE,iBAA2C,GAClD,OAAO,CAAC,IAAI,CAAC,CAwIf"}
@@ -4,10 +4,18 @@
4
4
  import { loadSyncCache, saveSyncCache, isSyncNeeded, computeDiff, writeReport, serializeNamespaces, formatPreviewRoutes, } from '../cache.js';
5
5
  import { resolveReportPath } from './helpers.js';
6
6
  /**
7
- * Push translation keys to the CMS for syncing.
8
- * Optionally supports dry-run mode and report generation.
7
+ * Push discovered translation keys to the CMS sync endpoint.
8
+ *
9
+ * Three possible outcomes:
10
+ * 1. **Dry-run** (`opts.dryRun`) — prints a diff against the last cache and
11
+ * optionally writes a report, but never POSTs to the CMS.
12
+ * 2. **No changes** — skips the POST when the serialized keys are identical
13
+ * to the last cache and `--force` was not passed.
14
+ * 3. **Sync** — POSTs the full namespace map; on success saves the new cache
15
+ * and optionally writes a report.
9
16
  */
10
17
  export async function postToSync(config, namespaces, opts = { root: process.cwd() }) {
18
+ // Flatten NamespaceMap → plain serializable object for the API payload and cache
11
19
  const { serialized, totalKeys } = serializeNamespaces(namespaces);
12
20
  const namespaceCount = Object.keys(serialized).length;
13
21
  console.log(`Found ${totalKeys} key(s) across ${namespaceCount} namespace(s): ${Object.keys(serialized).join(', ')}`);
@@ -15,6 +23,7 @@ export async function postToSync(config, namespaces, opts = { root: process.cwd(
15
23
  console.log('Nothing to sync.');
16
24
  return;
17
25
  }
26
+ // Load the baseline from the last successful sync to diff against
18
27
  const cached = loadSyncCache(opts.root);
19
28
  // ---- Dry-run: print diff and return without posting --------------------
20
29
  if (opts.dryRun) {
@@ -48,14 +57,18 @@ export async function postToSync(config, namespaces, opts = { root: process.cwd(
48
57
  return;
49
58
  }
50
59
  // ---- Skip if no changes ------------------------------------------------
60
+ // isSyncNeeded compares serialized keys against the cache — if identical,
61
+ // there's nothing new for the CMS to process.
51
62
  if (!opts.force && !isSyncNeeded(serialized, cached)) {
52
63
  console.log('No changes detected — skipping sync. Use --force to override.');
53
64
  if (opts.reportPath) {
65
+ // Write a report even when skipping so CI artefacts stay up-to-date
54
66
  writeReport(resolveReportPath(opts.root, opts.reportPath), serialized);
55
67
  }
56
68
  return;
57
69
  }
58
70
  // ---- Post to CMS -------------------------------------------------------
71
+ // Strip trailing slash to avoid double slashes in the URL
59
72
  const url = `${config.cmsUrl.replace(/\/$/, '')}/api/sync/${config.projectId}`;
60
73
  console.log(`Posting to ${url}...`);
61
74
  const response = await fetch(url, {
@@ -70,6 +83,7 @@ export async function postToSync(config, namespaces, opts = { root: process.cwd(
70
83
  const isJson = contentType.includes('application/json');
71
84
  if (!response.ok) {
72
85
  console.error(`Sync failed: ${response.status} ${response.statusText}`);
86
+ // HTML response usually means the endpoint doesn't exist (wrong URL / not deployed)
73
87
  if (!isJson) {
74
88
  console.error(`The CMS returned HTML instead of JSON. Is the sync endpoint available at ${url}?`);
75
89
  }
@@ -78,6 +92,7 @@ export async function postToSync(config, namespaces, opts = { root: process.cwd(
78
92
  }
79
93
  process.exit(1);
80
94
  }
95
+ // A 2xx with an HTML body is also invalid — guard against misconfigured proxies
81
96
  if (!isJson) {
82
97
  console.error(`The CMS returned HTML instead of JSON. Is the sync endpoint available at ${url}?`);
83
98
  process.exit(1);
@@ -86,6 +101,7 @@ export async function postToSync(config, namespaces, opts = { root: process.cwd(
86
101
  console.log(`Synced: ${data.created} created, ${data.updated ?? 0} routes updated, ${data.existing} existing`);
87
102
  if (data.message)
88
103
  console.log(data.message);
104
+ // Persist the new baseline so subsequent runs can detect changes correctly
89
105
  saveSyncCache(opts.root, serialized);
90
106
  if (opts.reportPath) {
91
107
  const diff = computeDiff(serialized, cached);
@@ -1 +1 @@
1
- {"version":3,"file":"sync.js","sourceRoot":"","sources":["../../../src/core/api-internals/sync.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"sync.js","sourceRoot":"","sources":["../../../src/core/api-internals/sync.ts"],"names":[],"mappings":"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"}
@@ -1,4 +1,20 @@
1
1
  import type { PreviewRoute } from '../scanner.js';
2
+ /**
3
+ * Format a single PreviewRoute for human-readable output.
4
+ *
5
+ * Plain string routes are returned as-is.
6
+ * Object routes (with params) are rendered as `/path (key=value, …)`.
7
+ *
8
+ * @example
9
+ * formatPreviewRoute('/dashboard') // → "/dashboard"
10
+ * formatPreviewRoute({ route: '/blog/[slug]', params: { slug: 'hello' } })
11
+ * // → "/blog/[slug] (slug=hello)"
12
+ */
2
13
  export declare function formatPreviewRoute(route: PreviewRoute): string;
14
+ /**
15
+ * Format an array of PreviewRoutes as a comma-separated string.
16
+ * Returns `"no route"` for keys that have no associated preview routes
17
+ * (e.g. keys inside dialogs or overlays).
18
+ */
3
19
  export declare function formatPreviewRoutes(routes: PreviewRoute[]): string;
4
20
  //# sourceMappingURL=format.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"format.d.ts","sourceRoot":"","sources":["../../../src/core/cache-internals/format.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAElD,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,YAAY,GAAG,MAAM,CAQ9D;AAED,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,YAAY,EAAE,GAAG,MAAM,CAGlE"}
1
+ {"version":3,"file":"format.d.ts","sourceRoot":"","sources":["../../../src/core/cache-internals/format.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAElD;;;;;;;;;;GAUG;AACH,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,YAAY,GAAG,MAAM,CAS9D;AAED;;;;GAIG;AACH,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,YAAY,EAAE,GAAG,MAAM,CAGlE"}
@@ -1,6 +1,18 @@
1
+ /**
2
+ * Format a single PreviewRoute for human-readable output.
3
+ *
4
+ * Plain string routes are returned as-is.
5
+ * Object routes (with params) are rendered as `/path (key=value, …)`.
6
+ *
7
+ * @example
8
+ * formatPreviewRoute('/dashboard') // → "/dashboard"
9
+ * formatPreviewRoute({ route: '/blog/[slug]', params: { slug: 'hello' } })
10
+ * // → "/blog/[slug] (slug=hello)"
11
+ */
1
12
  export function formatPreviewRoute(route) {
2
13
  if (typeof route === 'string')
3
14
  return route;
15
+ // Append param list only when params are present
4
16
  const params = route.params
5
17
  ? ` (${Object.entries(route.params)
6
18
  .map(([k, v]) => `${k}=${v}`)
@@ -8,6 +20,11 @@ export function formatPreviewRoute(route) {
8
20
  : '';
9
21
  return `${route.route}${params}`;
10
22
  }
23
+ /**
24
+ * Format an array of PreviewRoutes as a comma-separated string.
25
+ * Returns `"no route"` for keys that have no associated preview routes
26
+ * (e.g. keys inside dialogs or overlays).
27
+ */
11
28
  export function formatPreviewRoutes(routes) {
12
29
  if (routes.length === 0)
13
30
  return 'no route';
@@ -1 +1 @@
1
- {"version":3,"file":"format.js","sourceRoot":"","sources":["../../../src/core/cache-internals/format.ts"],"names":[],"mappings":"AAEA,MAAM,UAAU,kBAAkB,CAAC,KAAmB;IAClD,IAAI,OAAO,KAAK,KAAK,QAAQ;QAAE,OAAO,KAAK,CAAC;IAC5C,MAAM,MAAM,GAAG,KAAK,CAAC,MAAM;QACvB,CAAC,CAAC,KAAK,MAAM,CAAC,OAAO,CAAC,KAAK,CAAC,MAAM,CAAC;aAC5B,GAAG,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC;aAC5B,IAAI,CAAC,IAAI,CAAC,GAAG;QACpB,CAAC,CAAC,EAAE,CAAC;IACT,OAAO,GAAG,KAAK,CAAC,KAAK,GAAG,MAAM,EAAE,CAAC;AACrC,CAAC;AAED,MAAM,UAAU,mBAAmB,CAAC,MAAsB;IACtD,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,UAAU,CAAC;IAC3C,OAAO,MAAM,CAAC,GAAG,CAAC,kBAAkB,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AACrD,CAAC"}
1
+ {"version":3,"file":"format.js","sourceRoot":"","sources":["../../../src/core/cache-internals/format.ts"],"names":[],"mappings":"AAEA;;;;;;;;;;GAUG;AACH,MAAM,UAAU,kBAAkB,CAAC,KAAmB;IAClD,IAAI,OAAO,KAAK,KAAK,QAAQ;QAAE,OAAO,KAAK,CAAC;IAC5C,iDAAiD;IACjD,MAAM,MAAM,GAAG,KAAK,CAAC,MAAM;QACvB,CAAC,CAAC,KAAK,MAAM,CAAC,OAAO,CAAC,KAAK,CAAC,MAAM,CAAC;aAC5B,GAAG,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC;aAC5B,IAAI,CAAC,IAAI,CAAC,GAAG;QACpB,CAAC,CAAC,EAAE,CAAC;IACT,OAAO,GAAG,KAAK,CAAC,KAAK,GAAG,MAAM,EAAE,CAAC;AACrC,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,mBAAmB,CAAC,MAAsB;IACtD,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,UAAU,CAAC;IAC3C,OAAO,MAAM,CAAC,GAAG,CAAC,kBAAkB,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AACrD,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"params.d.ts","sourceRoot":"","sources":["../../../src/core/cache-internals/params.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,YAAY,CAAC;AA+CpD;;;;;;;;;GASG;AACH,wBAAgB,mBAAmB,CAC/B,MAAM,EAAE,MAAM,EAAE,GACjB,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAexC;AAED;;GAEG;AACH,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,MAAM,GAAG,iBAAiB,GAAG,IAAI,CAU3E;AAED;;GAEG;AACH,wBAAgB,oBAAoB,CAChC,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,GAC/C,IAAI,CAUN;AAED;;;;;;;;;;GAUG;AACH,wBAAgB,iBAAiB,CAC7B,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,EAC9C,kBAAkB,EAAE,MAAM,GAC3B,IAAI,CAkCN"}
1
+ {"version":3,"file":"params.d.ts","sourceRoot":"","sources":["../../../src/core/cache-internals/params.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,YAAY,CAAC;AA2CpD;;;;;;;;;GASG;AACH,wBAAgB,mBAAmB,CAC/B,MAAM,EAAE,MAAM,EAAE,GACjB,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAexC;AAED;;GAEG;AACH,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,MAAM,GAAG,iBAAiB,GAAG,IAAI,CAU3E;AAED;;GAEG;AACH,wBAAgB,oBAAoB,CAChC,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,GAC/C,IAAI,CAUN;AAED;;;;;;;;;;GAUG;AACH,wBAAgB,iBAAiB,CAC7B,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,EAC9C,kBAAkB,EAAE,MAAM,GAC3B,IAAI,CAoCN"}
@@ -1,5 +1,6 @@
1
1
  import fs from 'fs';
2
2
  import path from 'path';
3
+ import { randomUUID } from 'crypto';
3
4
  /**
4
5
  * Extract dynamic parameter names from a route string.
5
6
  * E.g. "/[locale]/blog/[slug]" → ["locale", "slug"]
@@ -9,35 +10,34 @@ function extractParamNames(route) {
9
10
  return matches.map(m => m.slice(1, -1));
10
11
  }
11
12
  /**
12
- * Generate a sensible default value for a param name.
13
+ * Generate a sensible default value for any dynamic route param name.
13
14
  *
14
- * Rules:
15
- * - locale/lang "en"
16
- * - id/ID-containing names → "123"
17
- * - slug/username/code "demo" or descriptive
18
- * - others "demo"
15
+ * Matches by suffix/pattern so it works generically — e.g. `productId`,
16
+ * `orderId`, `articleSlug`, `teamName` — without hardcoding every variant.
17
+ *
18
+ * Fallback: converts the param name from camelCase to kebab-case, which is
19
+ * both human-readable and a valid value for slug-style params.
20
+ * e.g. `articleSlug` → `"article-slug"`, `teamName` → `"team-name"`
19
21
  */
20
22
  function generateDefaultParamValue(paramName) {
21
23
  const lower = paramName.toLowerCase();
22
- if (lower === 'locale' || lower === 'lang' || lower === 'language') {
23
- return 'en';
24
- }
25
- if (lower.includes('id') ||
26
- lower === 'postid' ||
27
- lower === 'productid' ||
28
- lower === 'userid') {
29
- return '123';
30
- }
31
- if (lower === 'slug') {
32
- return 'demo';
33
- }
34
- if (lower === 'username') {
35
- return 'demo-user';
36
- }
37
- if (lower === 'email') {
24
+ // Any param ending in "id" (userId, productId, orderId, …) UUID
25
+ if (lower.endsWith('id'))
26
+ return randomUUID();
27
+ // Email addresses
28
+ if (lower.includes('email'))
38
29
  return 'demo@example.com';
39
- }
40
- return 'demo';
30
+ // Dates (createdDate, startDate, …)
31
+ if (lower.includes('date'))
32
+ return '2024-01-01';
33
+ // Pagination and numeric indices (page, pageNum, stepIndex, …)
34
+ if (lower === 'page' || lower.endsWith('num') || lower.endsWith('index') || lower.endsWith('page'))
35
+ return '1';
36
+ // Version strings (version, apiVersion, ver, …)
37
+ if (lower.includes('version') || lower === 'ver')
38
+ return 'v1';
39
+ // Fallback: kebab-case the param name so the value is always meaningful
40
+ return paramName.replace(/([A-Z])/g, '-$1').toLowerCase().replace(/^-/, '');
41
41
  }
42
42
  /**
43
43
  * Generate route params from detected routes.
@@ -1 +1 @@
1
- {"version":3,"file":"params.js","sourceRoot":"","sources":["../../../src/core/cache-internals/params.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,IAAI,CAAC;AACpB,OAAO,IAAI,MAAM,MAAM,CAAC;AAGxB;;;GAGG;AACH,SAAS,iBAAiB,CAAC,KAAa;IACpC,MAAM,OAAO,GAAG,KAAK,CAAC,KAAK,CAAC,YAAY,CAAC,IAAI,EAAE,CAAC;IAChD,OAAO,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;AAC5C,CAAC;AAED;;;;;;;;GAQG;AACH,SAAS,yBAAyB,CAAC,SAAiB;IAChD,MAAM,KAAK,GAAG,SAAS,CAAC,WAAW,EAAE,CAAC;IAEtC,IAAI,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,MAAM,IAAI,KAAK,KAAK,UAAU,EAAE,CAAC;QACjE,OAAO,IAAI,CAAC;IAChB,CAAC;IACD,IACI,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC;QACpB,KAAK,KAAK,QAAQ;QAClB,KAAK,KAAK,WAAW;QACrB,KAAK,KAAK,QAAQ,EACpB,CAAC;QACC,OAAO,KAAK,CAAC;IACjB,CAAC;IACD,IAAI,KAAK,KAAK,MAAM,EAAE,CAAC;QACnB,OAAO,MAAM,CAAC;IAClB,CAAC;IACD,IAAI,KAAK,KAAK,UAAU,EAAE,CAAC;QACvB,OAAO,WAAW,CAAC;IACvB,CAAC;IACD,IAAI,KAAK,KAAK,OAAO,EAAE,CAAC;QACpB,OAAO,kBAAkB,CAAC;IAC9B,CAAC;IAED,OAAO,MAAM,CAAC;AAClB,CAAC;AAED;;;;;;;;;GASG;AACH,MAAM,UAAU,mBAAmB,CAC/B,MAAgB;IAEhB,MAAM,MAAM,GAA2C,EAAE,CAAC;IAE1D,KAAK,MAAM,KAAK,IAAI,MAAM,EAAE,CAAC;QACzB,MAAM,MAAM,GAAG,iBAAiB,CAAC,KAAK,CAAC,CAAC;QACxC,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC;YAAE,SAAS;QAElC,MAAM,QAAQ,GAA2B,EAAE,CAAC;QAC5C,KAAK,MAAM,KAAK,IAAI,MAAM,EAAE,CAAC;YACzB,QAAQ,CAAC,KAAK,CAAC,GAAG,yBAAyB,CAAC,KAAK,CAAC,CAAC;QACvD,CAAC;QACD,MAAM,CAAC,KAAK,CAAC,GAAG,QAAQ,CAAC;IAC7B,CAAC;IAED,OAAO,MAAM,CAAC;AAClB,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,oBAAoB,CAAC,IAAY;IAC7C,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,2BAA2B,CAAC,CAAC;IAC9D,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,QAAQ,CAAC;QAAE,OAAO,IAAI,CAAC;IAC1C,IAAI,CAAC;QACD,OAAO,IAAI,CAAC,KAAK,CACb,EAAE,CAAC,YAAY,CAAC,QAAQ,EAAE,OAAO,CAAC,CAChB,CAAC;IAC3B,CAAC;IAAC,MAAM,CAAC;QACL,OAAO,IAAI,CAAC;IAChB,CAAC;AACL,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,oBAAoB,CAChC,IAAY,EACZ,MAA8C;IAE9C,MAAM,MAAM,GAAsB;QAC9B,SAAS,EAAE,MAAM;QACjB,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;KACtC,CAAC;IACF,EAAE,CAAC,aAAa,CACZ,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,2BAA2B,CAAC,EAC5C,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC,EAC/B,OAAO,CACV,CAAC;AACN,CAAC;AAED;;;;;;;;;;GAUG;AACH,MAAM,UAAU,iBAAiB,CAC7B,IAAY,EACZ,MAA8C,EAC9C,kBAA0B;IAE1B,IAAI,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO;IAE7C,MAAM,OAAO,GAAG,MAAM,CAAC,OAAO,CAAC,MAAM,CAAC;SACjC,GAAG,CAAC,CAAC,CAAC,KAAK,EAAE,CAAC,CAAC,EAAE,EAAE;QAChB,MAAM,KAAK,GAAG,MAAM,CAAC,OAAO,CAAC,CAAC,CAAC;aAC1B,GAAG,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,OAAO,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,KAAK,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC;aACjE,IAAI,CAAC,KAAK,CAAC,CAAC;QACjB,OAAO,KAAK,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,QAAQ,KAAK,QAAQ,CAAC;IAC3D,CAAC,CAAC;SACD,IAAI,CAAC,KAAK,CAAC,CAAC;IAEjB,MAAM,OAAO,GAAG;QACZ,+DAA+D;QAC/D,2CAA2C;QAC3C,EAAE;QACF,iCAAiC;QACjC,OAAO,GAAG,GAAG;QACb,aAAa;QACb,EAAE;QACF,qDAAqD;QACrD,8EAA8E;QAC9E,EAAE;KACL,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAEb,MAAM,OAAO,GAAG,IAAI,CAAC,UAAU,CAAC,kBAAkB,CAAC;QAC/C,CAAC,CAAC,kBAAkB;QACpB,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,kBAAkB,CAAC,CAAC;IAE1C,MAAM,GAAG,GAAG,IAAI,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC;IAClC,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,GAAG,CAAC;QAAE,EAAE,CAAC,SAAS,CAAC,GAAG,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAEhE,EAAE,CAAC,aAAa,CAAC,OAAO,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;IAC5C,OAAO,CAAC,GAAG,CAAC,0BAA0B,IAAI,CAAC,QAAQ,CAAC,IAAI,EAAE,OAAO,CAAC,EAAE,CAAC,CAAC;AAC1E,CAAC"}
1
+ {"version":3,"file":"params.js","sourceRoot":"","sources":["../../../src/core/cache-internals/params.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,IAAI,CAAC;AACpB,OAAO,IAAI,MAAM,MAAM,CAAC;AACxB,OAAO,EAAE,UAAU,EAAE,MAAM,QAAQ,CAAC;AAGpC;;;GAGG;AACH,SAAS,iBAAiB,CAAC,KAAa;IACpC,MAAM,OAAO,GAAG,KAAK,CAAC,KAAK,CAAC,YAAY,CAAC,IAAI,EAAE,CAAC;IAChD,OAAO,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;AAC5C,CAAC;AAED;;;;;;;;;GASG;AACH,SAAS,yBAAyB,CAAC,SAAiB;IAChD,MAAM,KAAK,GAAG,SAAS,CAAC,WAAW,EAAE,CAAC;IAEtC,kEAAkE;IAClE,IAAI,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC;QAAE,OAAO,UAAU,EAAE,CAAC;IAE9C,kBAAkB;IAClB,IAAI,KAAK,CAAC,QAAQ,CAAC,OAAO,CAAC;QAAE,OAAO,kBAAkB,CAAC;IAEvD,oCAAoC;IACpC,IAAI,KAAK,CAAC,QAAQ,CAAC,MAAM,CAAC;QAAE,OAAO,YAAY,CAAC;IAEhD,+DAA+D;IAC/D,IAAI,KAAK,KAAK,MAAM,IAAI,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,QAAQ,CAAC,OAAO,CAAC,IAAI,KAAK,CAAC,QAAQ,CAAC,MAAM,CAAC;QAAE,OAAO,GAAG,CAAC;IAE/G,gDAAgD;IAChD,IAAI,KAAK,CAAC,QAAQ,CAAC,SAAS,CAAC,IAAI,KAAK,KAAK,KAAK;QAAE,OAAO,IAAI,CAAC;IAE9D,wEAAwE;IACxE,OAAO,SAAS,CAAC,OAAO,CAAC,UAAU,EAAE,KAAK,CAAC,CAAC,WAAW,EAAE,CAAC,OAAO,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;AAChF,CAAC;AAED;;;;;;;;;GASG;AACH,MAAM,UAAU,mBAAmB,CAC/B,MAAgB;IAEhB,MAAM,MAAM,GAA2C,EAAE,CAAC;IAE1D,KAAK,MAAM,KAAK,IAAI,MAAM,EAAE,CAAC;QACzB,MAAM,MAAM,GAAG,iBAAiB,CAAC,KAAK,CAAC,CAAC;QACxC,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC;YAAE,SAAS;QAElC,MAAM,QAAQ,GAA2B,EAAE,CAAC;QAC5C,KAAK,MAAM,KAAK,IAAI,MAAM,EAAE,CAAC;YACzB,QAAQ,CAAC,KAAK,CAAC,GAAG,yBAAyB,CAAC,KAAK,CAAC,CAAC;QACvD,CAAC;QACD,MAAM,CAAC,KAAK,CAAC,GAAG,QAAQ,CAAC;IAC7B,CAAC;IAED,OAAO,MAAM,CAAC;AAClB,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,oBAAoB,CAAC,IAAY;IAC7C,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,2BAA2B,CAAC,CAAC;IAC9D,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,QAAQ,CAAC;QAAE,OAAO,IAAI,CAAC;IAC1C,IAAI,CAAC;QACD,OAAO,IAAI,CAAC,KAAK,CACb,EAAE,CAAC,YAAY,CAAC,QAAQ,EAAE,OAAO,CAAC,CAChB,CAAC;IAC3B,CAAC;IAAC,MAAM,CAAC;QACL,OAAO,IAAI,CAAC;IAChB,CAAC;AACL,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,oBAAoB,CAChC,IAAY,EACZ,MAA8C;IAE9C,MAAM,MAAM,GAAsB;QAC9B,SAAS,EAAE,MAAM;QACjB,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;KACtC,CAAC;IACF,EAAE,CAAC,aAAa,CACZ,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,2BAA2B,CAAC,EAC5C,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC,EAC/B,OAAO,CACV,CAAC;AACN,CAAC;AAED;;;;;;;;;;GAUG;AACH,MAAM,UAAU,iBAAiB,CAC7B,IAAY,EACZ,MAA8C,EAC9C,kBAA0B;IAE1B,IAAI,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO;IAE7C,MAAM,OAAO,GAAG,MAAM,CAAC,OAAO,CAAC,MAAM,CAAC;SACjC,GAAG,CAAC,CAAC,CAAC,KAAK,EAAE,CAAC,CAAC,EAAE,EAAE;QAChB,MAAM,KAAK,GAAG,MAAM,CAAC,OAAO,CAAC,CAAC,CAAC;aAC1B,GAAG,CACA,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,OAAO,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,KAAK,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,EAAE,CAC/D;aACA,IAAI,CAAC,KAAK,CAAC,CAAC;QACjB,OAAO,KAAK,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,QAAQ,KAAK,QAAQ,CAAC;IAC3D,CAAC,CAAC;SACD,IAAI,CAAC,KAAK,CAAC,CAAC;IAEjB,MAAM,OAAO,GAAG;QACZ,+DAA+D;QAC/D,2CAA2C;QAC3C,EAAE;QACF,iCAAiC;QACjC,OAAO,GAAG,GAAG;QACb,aAAa;QACb,EAAE;QACF,qDAAqD;QACrD,8EAA8E;QAC9E,EAAE;KACL,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAEb,MAAM,OAAO,GAAG,IAAI,CAAC,UAAU,CAAC,kBAAkB,CAAC;QAC/C,CAAC,CAAC,kBAAkB;QACpB,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,kBAAkB,CAAC,CAAC;IAE1C,MAAM,GAAG,GAAG,IAAI,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC;IAClC,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,GAAG,CAAC;QAAE,EAAE,CAAC,SAAS,CAAC,GAAG,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAEhE,EAAE,CAAC,aAAa,CAAC,OAAO,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;IAC5C,OAAO,CAAC,GAAG,CAAC,0BAA0B,IAAI,CAAC,QAAQ,CAAC,IAAI,EAAE,OAAO,CAAC,EAAE,CAAC,CAAC;AAC1E,CAAC"}
@@ -1,5 +1,17 @@
1
+ /** Filename of the pull timestamp marker written inside the output directory. */
1
2
  export declare const PULL_META_FILE = ".last-pulled";
3
+ /** Default TTL before a pull is considered stale and a re-fetch is triggered. */
2
4
  export declare const DEFAULT_PULL_TTL_MS: number;
5
+ /**
6
+ * Read the timestamp of the last successful pull from the marker file.
7
+ * Returns the time as a Unix timestamp (ms), or null when the file is absent
8
+ * or contains an unparseable date.
9
+ */
3
10
  export declare function getLastPulledTime(outputDir: string): number | null;
11
+ /**
12
+ * Write the current time as an ISO 8601 string to the marker file.
13
+ * Creates the output directory if it doesn't exist yet.
14
+ * Called after a successful pull to reset the TTL clock.
15
+ */
4
16
  export declare function saveLastPulledTime(outputDir: string): void;
5
17
  //# sourceMappingURL=pull.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"pull.d.ts","sourceRoot":"","sources":["../../../src/core/cache-internals/pull.ts"],"names":[],"mappings":"AAGA,eAAO,MAAM,cAAc,iBAAiB,CAAC;AAC7C,eAAO,MAAM,mBAAmB,QAAgB,CAAC;AAEjD,wBAAgB,iBAAiB,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CASlE;AAED,wBAAgB,kBAAkB,CAAC,SAAS,EAAE,MAAM,GAAG,IAAI,CAO1D"}
1
+ {"version":3,"file":"pull.d.ts","sourceRoot":"","sources":["../../../src/core/cache-internals/pull.ts"],"names":[],"mappings":"AAGA,iFAAiF;AACjF,eAAO,MAAM,cAAc,iBAAiB,CAAC;AAE7C,iFAAiF;AACjF,eAAO,MAAM,mBAAmB,QAAgB,CAAC;AAEjD;;;;GAIG;AACH,wBAAgB,iBAAiB,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAUlE;AAED;;;;GAIG;AACH,wBAAgB,kBAAkB,CAAC,SAAS,EAAE,MAAM,GAAG,IAAI,CAO1D"}
@@ -1,19 +1,32 @@
1
1
  import fs from 'fs';
2
2
  import path from 'path';
3
+ /** Filename of the pull timestamp marker written inside the output directory. */
3
4
  export const PULL_META_FILE = '.last-pulled';
5
+ /** Default TTL before a pull is considered stale and a re-fetch is triggered. */
4
6
  export const DEFAULT_PULL_TTL_MS = 5 * 60 * 1000; // 5 minutes
7
+ /**
8
+ * Read the timestamp of the last successful pull from the marker file.
9
+ * Returns the time as a Unix timestamp (ms), or null when the file is absent
10
+ * or contains an unparseable date.
11
+ */
5
12
  export function getLastPulledTime(outputDir) {
6
13
  const p = path.join(outputDir, PULL_META_FILE);
7
14
  if (!fs.existsSync(p))
8
15
  return null;
9
16
  try {
10
17
  const ts = new Date(fs.readFileSync(p, 'utf-8').trim()).getTime();
18
+ // isNaN guard handles a corrupted or empty file
11
19
  return isNaN(ts) ? null : ts;
12
20
  }
13
21
  catch {
14
22
  return null;
15
23
  }
16
24
  }
25
+ /**
26
+ * Write the current time as an ISO 8601 string to the marker file.
27
+ * Creates the output directory if it doesn't exist yet.
28
+ * Called after a successful pull to reset the TTL clock.
29
+ */
17
30
  export function saveLastPulledTime(outputDir) {
18
31
  fs.mkdirSync(outputDir, { recursive: true });
19
32
  fs.writeFileSync(path.join(outputDir, PULL_META_FILE), new Date().toISOString(), 'utf-8');
@@ -1 +1 @@
1
- {"version":3,"file":"pull.js","sourceRoot":"","sources":["../../../src/core/cache-internals/pull.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,IAAI,CAAC;AACpB,OAAO,IAAI,MAAM,MAAM,CAAC;AAExB,MAAM,CAAC,MAAM,cAAc,GAAG,cAAc,CAAC;AAC7C,MAAM,CAAC,MAAM,mBAAmB,GAAG,CAAC,GAAG,EAAE,GAAG,IAAI,CAAC,CAAC,YAAY;AAE9D,MAAM,UAAU,iBAAiB,CAAC,SAAiB;IAC/C,MAAM,CAAC,GAAG,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,cAAc,CAAC,CAAC;IAC/C,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,CAAC,CAAC;QAAE,OAAO,IAAI,CAAC;IACnC,IAAI,CAAC;QACD,MAAM,EAAE,GAAG,IAAI,IAAI,CAAC,EAAE,CAAC,YAAY,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC,OAAO,EAAE,CAAC;QAClE,OAAO,KAAK,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC;IACjC,CAAC;IAAC,MAAM,CAAC;QACL,OAAO,IAAI,CAAC;IAChB,CAAC;AACL,CAAC;AAED,MAAM,UAAU,kBAAkB,CAAC,SAAiB;IAChD,EAAE,CAAC,SAAS,CAAC,SAAS,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC7C,EAAE,CAAC,aAAa,CACZ,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,cAAc,CAAC,EACpC,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE,EACxB,OAAO,CACV,CAAC;AACN,CAAC"}
1
+ {"version":3,"file":"pull.js","sourceRoot":"","sources":["../../../src/core/cache-internals/pull.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,IAAI,CAAC;AACpB,OAAO,IAAI,MAAM,MAAM,CAAC;AAExB,iFAAiF;AACjF,MAAM,CAAC,MAAM,cAAc,GAAG,cAAc,CAAC;AAE7C,iFAAiF;AACjF,MAAM,CAAC,MAAM,mBAAmB,GAAG,CAAC,GAAG,EAAE,GAAG,IAAI,CAAC,CAAC,YAAY;AAE9D;;;;GAIG;AACH,MAAM,UAAU,iBAAiB,CAAC,SAAiB;IAC/C,MAAM,CAAC,GAAG,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,cAAc,CAAC,CAAC;IAC/C,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,CAAC,CAAC;QAAE,OAAO,IAAI,CAAC;IACnC,IAAI,CAAC;QACD,MAAM,EAAE,GAAG,IAAI,IAAI,CAAC,EAAE,CAAC,YAAY,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC,OAAO,EAAE,CAAC;QAClE,gDAAgD;QAChD,OAAO,KAAK,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC;IACjC,CAAC;IAAC,MAAM,CAAC;QACL,OAAO,IAAI,CAAC;IAChB,CAAC;AACL,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,kBAAkB,CAAC,SAAiB;IAChD,EAAE,CAAC,SAAS,CAAC,SAAS,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC7C,EAAE,CAAC,aAAa,CACZ,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,cAAc,CAAC,EACpC,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE,EACxB,OAAO,CACV,CAAC;AACN,CAAC"}
@@ -1,6 +1,29 @@
1
1
  import type { SerializedNamespaces, SyncDiff } from './types.js';
2
+ /**
3
+ * Load the serialized namespace map from the last successful sync.
4
+ * Returns null when no cache exists yet or when the file is unreadable.
5
+ */
2
6
  export declare function loadSyncCache(root: string): SerializedNamespaces | null;
7
+ /**
8
+ * Persist the serialized namespace map as the new sync baseline.
9
+ * Subsequent runs diff against this to detect changes.
10
+ */
3
11
  export declare function saveSyncCache(root: string, data: SerializedNamespaces): void;
12
+ /**
13
+ * Returns true when the current scan differs from the cached baseline,
14
+ * meaning the CMS needs to be updated.
15
+ * Always returns true when there is no cache yet (first run).
16
+ */
4
17
  export declare function isSyncNeeded(current: SerializedNamespaces, cached: SerializedNamespaces | null): boolean;
18
+ /**
19
+ * Compute a three-way diff between the current scan and the cached baseline:
20
+ *
21
+ * - `added` keys present in current but not in cache
22
+ * - `removed` keys present in cache but no longer in current
23
+ * - `routesChanged` keys present in both but with different preview routes
24
+ * - `unchanged` count of keys that are identical in both
25
+ *
26
+ * Preview routes are compared order-independently by sorting before joining.
27
+ */
5
28
  export declare function computeDiff(current: SerializedNamespaces, cached: SerializedNamespaces | null): SyncDiff;
6
29
  //# sourceMappingURL=sync.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"sync.d.ts","sourceRoot":"","sources":["../../../src/core/cache-internals/sync.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,oBAAoB,EAAE,QAAQ,EAAE,MAAM,YAAY,CAAC;AAIjE,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,oBAAoB,GAAG,IAAI,CAQvE;AAED,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,oBAAoB,GAAG,IAAI,CAM5E;AAED,wBAAgB,YAAY,CACxB,OAAO,EAAE,oBAAoB,EAC7B,MAAM,EAAE,oBAAoB,GAAG,IAAI,GACpC,OAAO,CAGT;AAED,wBAAgB,WAAW,CACvB,OAAO,EAAE,oBAAoB,EAC7B,MAAM,EAAE,oBAAoB,GAAG,IAAI,GACpC,QAAQ,CA6CV"}
1
+ {"version":3,"file":"sync.d.ts","sourceRoot":"","sources":["../../../src/core/cache-internals/sync.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,oBAAoB,EAAE,QAAQ,EAAE,MAAM,YAAY,CAAC;AAKjE;;;GAGG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,oBAAoB,GAAG,IAAI,CAQvE;AAED;;;GAGG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,oBAAoB,GAAG,IAAI,CAM5E;AAED;;;;GAIG;AACH,wBAAgB,YAAY,CACxB,OAAO,EAAE,oBAAoB,EAC7B,MAAM,EAAE,oBAAoB,GAAG,IAAI,GACpC,OAAO,CAIT;AAED;;;;;;;;;GASG;AACH,wBAAgB,WAAW,CACvB,OAAO,EAAE,oBAAoB,EAC7B,MAAM,EAAE,oBAAoB,GAAG,IAAI,GACpC,QAAQ,CAgDV"}
@@ -1,6 +1,11 @@
1
1
  import fs from 'fs';
2
2
  import path from 'path';
3
+ /** Filename of the sync baseline cache written at the project root. */
3
4
  const CACHE_FILE = '.cms-sync-cache.json';
5
+ /**
6
+ * Load the serialized namespace map from the last successful sync.
7
+ * Returns null when no cache exists yet or when the file is unreadable.
8
+ */
4
9
  export function loadSyncCache(root) {
5
10
  const p = path.join(root, CACHE_FILE);
6
11
  if (!fs.existsSync(p))
@@ -12,19 +17,40 @@ export function loadSyncCache(root) {
12
17
  return null;
13
18
  }
14
19
  }
20
+ /**
21
+ * Persist the serialized namespace map as the new sync baseline.
22
+ * Subsequent runs diff against this to detect changes.
23
+ */
15
24
  export function saveSyncCache(root, data) {
16
25
  fs.writeFileSync(path.join(root, CACHE_FILE), JSON.stringify(data, null, 2), 'utf-8');
17
26
  }
27
+ /**
28
+ * Returns true when the current scan differs from the cached baseline,
29
+ * meaning the CMS needs to be updated.
30
+ * Always returns true when there is no cache yet (first run).
31
+ */
18
32
  export function isSyncNeeded(current, cached) {
19
33
  if (!cached)
20
34
  return true;
35
+ // Stringify comparison is sufficient — order is stable because serializeNamespaces sorts keys
21
36
  return JSON.stringify(current) !== JSON.stringify(cached);
22
37
  }
38
+ /**
39
+ * Compute a three-way diff between the current scan and the cached baseline:
40
+ *
41
+ * - `added` keys present in current but not in cache
42
+ * - `removed` keys present in cache but no longer in current
43
+ * - `routesChanged` keys present in both but with different preview routes
44
+ * - `unchanged` count of keys that are identical in both
45
+ *
46
+ * Preview routes are compared order-independently by sorting before joining.
47
+ */
23
48
  export function computeDiff(current, cached) {
24
49
  const added = [];
25
50
  const removed = [];
26
51
  const routesChanged = [];
27
52
  let unchanged = 0;
53
+ // Forward pass: find added keys and route changes
28
54
  for (const [ns, keys] of Object.entries(current)) {
29
55
  for (const { key, previewRoutes } of keys) {
30
56
  const cachedEntry = cached?.[ns]?.find(k => k.key === key);
@@ -32,6 +58,7 @@ export function computeDiff(current, cached) {
32
58
  added.push({ namespace: ns, key, routes: previewRoutes });
33
59
  }
34
60
  else {
61
+ // Sort both sides so route order doesn't cause false positives
35
62
  const before = [...cachedEntry.previewRoutes]
36
63
  .map(routeToString)
37
64
  .sort()
@@ -54,6 +81,7 @@ export function computeDiff(current, cached) {
54
81
  }
55
82
  }
56
83
  }
84
+ // Reverse pass: find keys that exist in cache but are gone from current
57
85
  if (cached) {
58
86
  for (const [ns, keys] of Object.entries(cached)) {
59
87
  for (const { key } of keys) {
@@ -65,6 +93,11 @@ export function computeDiff(current, cached) {
65
93
  }
66
94
  return { added, removed, routesChanged, unchanged };
67
95
  }
96
+ /**
97
+ * Normalise a PreviewRoute to a string for stable comparison.
98
+ * String routes are returned as-is; object routes are JSON-stringified.
99
+ */
100
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
68
101
  function routeToString(r) {
69
102
  return typeof r === 'string' ? r : JSON.stringify(r);
70
103
  }
@@ -1 +1 @@
1
- {"version":3,"file":"sync.js","sourceRoot":"","sources":["../../../src/core/cache-internals/sync.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"sync.js","sourceRoot":"","sources":["../../../src/core/cache-internals/sync.ts"],"names":[],"mappings":"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"}
@@ -1,8 +1,21 @@
1
1
  import type { PreviewRoute } from '../scanner.js';
2
+ /**
3
+ * The serialized form of a NamespaceMap written to the sync cache and sent to
4
+ * the CMS API. Each namespace maps to an ordered array of key entries so the
5
+ * structure is JSON-serializable without Maps.
6
+ */
2
7
  export type SerializedNamespaces = Record<string, Array<{
3
8
  key: string;
4
9
  previewRoutes: PreviewRoute[];
5
10
  }>>;
11
+ /**
12
+ * Result of diffing the current scan against the cached baseline.
13
+ *
14
+ * - `added` keys new since the last sync
15
+ * - `removed` keys that no longer exist in the source
16
+ * - `routesChanged` keys whose set of preview routes has changed
17
+ * - `unchanged` count of keys identical in both snapshots
18
+ */
6
19
  export interface SyncDiff {
7
20
  added: Array<{
8
21
  namespace: string;
@@ -21,6 +34,13 @@ export interface SyncDiff {
21
34
  }>;
22
35
  unchanged: number;
23
36
  }
37
+ /**
38
+ * Shape of the `.cms-sync-cache-meta.json` file that stores auto-generated
39
+ * route params between sync runs.
40
+ *
41
+ * - `generated` route → param map produced by the last sync
42
+ * - `timestamp` ISO 8601 string of when the cache was last written
43
+ */
24
44
  export interface CachedRouteParams {
25
45
  generated: Record<string, Record<string, string>>;
26
46
  timestamp: string;
@@ -1 +1 @@
1
- {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../src/core/cache-internals/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAElD,MAAM,MAAM,oBAAoB,GAAG,MAAM,CACrC,MAAM,EACN,KAAK,CAAC;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,aAAa,EAAE,YAAY,EAAE,CAAA;CAAE,CAAC,CACxD,CAAC;AAEF,MAAM,WAAW,QAAQ;IACrB,KAAK,EAAE,KAAK,CAAC;QAAE,SAAS,EAAE,MAAM,CAAC;QAAC,GAAG,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,YAAY,EAAE,CAAA;KAAE,CAAC,CAAC;IACzE,OAAO,EAAE,KAAK,CAAC;QAAE,SAAS,EAAE,MAAM,CAAC;QAAC,GAAG,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;IACnD,aAAa,EAAE,KAAK,CAAC;QACjB,SAAS,EAAE,MAAM,CAAC;QAClB,GAAG,EAAE,MAAM,CAAC;QACZ,MAAM,EAAE,YAAY,EAAE,CAAC;QACvB,KAAK,EAAE,YAAY,EAAE,CAAC;KACzB,CAAC,CAAC;IACH,SAAS,EAAE,MAAM,CAAC;CACrB;AAED,MAAM,WAAW,iBAAiB;IAC9B,SAAS,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAAC;IAClD,SAAS,EAAE,MAAM,CAAC;CACrB"}
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../src/core/cache-internals/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAElD;;;;GAIG;AACH,MAAM,MAAM,oBAAoB,GAAG,MAAM,CACrC,MAAM,EACN,KAAK,CAAC;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,aAAa,EAAE,YAAY,EAAE,CAAA;CAAE,CAAC,CACxD,CAAC;AAEF;;;;;;;GAOG;AACH,MAAM,WAAW,QAAQ;IACrB,KAAK,EAAE,KAAK,CAAC;QAAE,SAAS,EAAE,MAAM,CAAC;QAAC,GAAG,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,YAAY,EAAE,CAAA;KAAE,CAAC,CAAC;IACzE,OAAO,EAAE,KAAK,CAAC;QAAE,SAAS,EAAE,MAAM,CAAC;QAAC,GAAG,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;IACnD,aAAa,EAAE,KAAK,CAAC;QACjB,SAAS,EAAE,MAAM,CAAC;QAClB,GAAG,EAAE,MAAM,CAAC;QACZ,MAAM,EAAE,YAAY,EAAE,CAAC;QACvB,KAAK,EAAE,YAAY,EAAE,CAAC;KACzB,CAAC,CAAC;IACH,SAAS,EAAE,MAAM,CAAC;CACrB;AAED;;;;;;GAMG;AACH,MAAM,WAAW,iBAAiB;IAC9B,SAAS,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAAC;IAClD,SAAS,EAAE,MAAM,CAAC;CACrB"}
@@ -3,20 +3,38 @@
3
3
  */
4
4
  import type { AstNode } from './types.js';
5
5
  /**
6
- * Walk an AST tree depth-first, calling visit() for each node.
6
+ * Walk an AST node depth-first, calling visit() for every node encountered.
7
+ *
8
+ * Handles three cases:
9
+ * - Arrays → recurse into each element
10
+ * - AST nodes → call visit(), then recurse into all object-valued properties
11
+ * - Primitives → stop (nothing to traverse)
7
12
  */
8
13
  export declare function walk(node: unknown, visit: (node: AstNode) => void): void;
9
14
  /**
10
- * Parse source code using Babel with appropriate plugins based on file extension.
15
+ * Parse source code into a Babel AST with the appropriate plugins for the
16
+ * file extension.
17
+ *
18
+ * - `.ts` → typescript
19
+ * - `.tsx`, `.jsx`, `.js` → typescript (if .tsx) + jsx
20
+ *
21
+ * `errorRecovery: true` lets the parser continue past syntax errors so a
22
+ * single broken file doesn't abort the entire scan.
11
23
  */
12
24
  export declare function parseSource(filePath: string, source: string): unknown;
13
25
  /**
14
- * Returns the string value of a StringLiteral or no-expression TemplateLiteral node.
26
+ * Extract the static string value from a `StringLiteral` or a `TemplateLiteral`
27
+ * that contains no expressions (i.e. `` `plain string` ``).
28
+ * Returns null for dynamic expressions or any other node type.
15
29
  */
16
30
  export declare function stringValue(node: unknown): string | null;
17
31
  /**
18
- * Extracts namespace string(s) from a useTranslation/getTranslation argument.
19
- * Handles both single strings and arrays of strings.
32
+ * Extract namespace string(s) from the first argument of a
33
+ * `useTranslation()` / `getTranslation()` call.
34
+ *
35
+ * Handles:
36
+ * - Single string: `useTranslation('sidebar')` → `['sidebar']`
37
+ * - Array of strings: `useTranslation(['common', 'nav'])` → `['common', 'nav']`
20
38
  */
21
39
  export declare function namespacesFromArg(node: unknown): string[];
22
40
  //# sourceMappingURL=ast.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"ast.d.ts","sourceRoot":"","sources":["../../../src/core/scanner-internals/ast.ts"],"names":[],"mappings":"AAAA;;GAEG;AAIH,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,YAAY,CAAC;AAE1C;;GAEG;AACH,wBAAgB,IAAI,CAAC,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC,IAAI,EAAE,OAAO,KAAK,IAAI,GAAG,IAAI,CAWxE;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAUrE;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,IAAI,EAAE,OAAO,GAAG,MAAM,GAAG,IAAI,CAgBxD;AAED;;;GAGG;AACH,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,OAAO,GAAG,MAAM,EAAE,CAWzD"}
1
+ {"version":3,"file":"ast.d.ts","sourceRoot":"","sources":["../../../src/core/scanner-internals/ast.ts"],"names":[],"mappings":"AAAA;;GAEG;AAIH,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,YAAY,CAAC;AAE1C;;;;;;;GAOG;AACH,wBAAgB,IAAI,CAAC,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC,IAAI,EAAE,OAAO,KAAK,IAAI,GAAG,IAAI,CAYxE;AAED;;;;;;;;;GASG;AACH,wBAAgB,WAAW,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAUrE;AAED;;;;GAIG;AACH,wBAAgB,WAAW,CAAC,IAAI,EAAE,OAAO,GAAG,MAAM,GAAG,IAAI,CAiBxD;AAED;;;;;;;GAOG;AACH,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,OAAO,GAAG,MAAM,EAAE,CAWzD"}
@@ -4,7 +4,12 @@
4
4
  import { parse } from '@babel/parser';
5
5
  import path from 'path';
6
6
  /**
7
- * Walk an AST tree depth-first, calling visit() for each node.
7
+ * Walk an AST node depth-first, calling visit() for every node encountered.
8
+ *
9
+ * Handles three cases:
10
+ * - Arrays → recurse into each element
11
+ * - AST nodes → call visit(), then recurse into all object-valued properties
12
+ * - Primitives → stop (nothing to traverse)
8
13
  */
9
14
  export function walk(node, visit) {
10
15
  if (!node || typeof node !== 'object')
@@ -15,6 +20,7 @@ export function walk(node, visit) {
15
20
  return;
16
21
  }
17
22
  const n = node;
23
+ // Visit before recursing so parents are seen before their children
18
24
  if (typeof n.type === 'string')
19
25
  visit(n);
20
26
  for (const value of Object.values(n)) {
@@ -23,7 +29,14 @@ export function walk(node, visit) {
23
29
  }
24
30
  }
25
31
  /**
26
- * Parse source code using Babel with appropriate plugins based on file extension.
32
+ * Parse source code into a Babel AST with the appropriate plugins for the
33
+ * file extension.
34
+ *
35
+ * - `.ts` → typescript
36
+ * - `.tsx`, `.jsx`, `.js` → typescript (if .tsx) + jsx
37
+ *
38
+ * `errorRecovery: true` lets the parser continue past syntax errors so a
39
+ * single broken file doesn't abort the entire scan.
27
40
  */
28
41
  export function parseSource(filePath, source) {
29
42
  const ext = path.extname(filePath);
@@ -39,7 +52,9 @@ export function parseSource(filePath, source) {
39
52
  });
40
53
  }
41
54
  /**
42
- * Returns the string value of a StringLiteral or no-expression TemplateLiteral node.
55
+ * Extract the static string value from a `StringLiteral` or a `TemplateLiteral`
56
+ * that contains no expressions (i.e. `` `plain string` ``).
57
+ * Returns null for dynamic expressions or any other node type.
43
58
  */
44
59
  export function stringValue(node) {
45
60
  if (!node || typeof node !== 'object')
@@ -50,6 +65,7 @@ export function stringValue(node) {
50
65
  if (n.type === 'TemplateLiteral') {
51
66
  const exprs = n.expressions;
52
67
  const quasis = n.quasis;
68
+ // Only static template literals (no ${…} expressions) can be resolved
53
69
  if (exprs.length === 0 && quasis.length === 1) {
54
70
  const quasi = quasis[0];
55
71
  if (quasi?.value) {
@@ -60,8 +76,12 @@ export function stringValue(node) {
60
76
  return null;
61
77
  }
62
78
  /**
63
- * Extracts namespace string(s) from a useTranslation/getTranslation argument.
64
- * Handles both single strings and arrays of strings.
79
+ * Extract namespace string(s) from the first argument of a
80
+ * `useTranslation()` / `getTranslation()` call.
81
+ *
82
+ * Handles:
83
+ * - Single string: `useTranslation('sidebar')` → `['sidebar']`
84
+ * - Array of strings: `useTranslation(['common', 'nav'])` → `['common', 'nav']`
65
85
  */
66
86
  export function namespacesFromArg(node) {
67
87
  const single = stringValue(node);