@csszyx/unplugin 0.5.0 → 0.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -154,6 +154,7 @@ import { preprocess as vuePreprocess } from "@csszyx/vue-adapter";
154
154
  import { createUnplugin } from "unplugin";
155
155
 
156
156
  // src/html-transformer.ts
157
+ import { createHash } from "crypto";
157
158
  function injectChecksum(html, checksum, minify = false) {
158
159
  const attrName = minify ? "data-sz-cs" : "data-sz-checksum";
159
160
  const htmlTagPattern = /<html([^>]*)>/i;
@@ -213,6 +214,46 @@ function injectHydrationData(html, mangleMap, checksum, options = {}) {
213
214
  function transformIndexHtml(html, mangleMap, checksum, options = {}) {
214
215
  return injectHydrationData(html, mangleMap, checksum, options);
215
216
  }
217
+ function buildRecoveryManifest(tokens, options = {}) {
218
+ const stripped = options.production === true;
219
+ const strippedDevOnlyPaths = [];
220
+ const sorted = {};
221
+ const sortedKeys = [...tokens.keys()].sort();
222
+ for (const key of sortedKeys) {
223
+ const data = tokens.get(key);
224
+ if (!data) {
225
+ continue;
226
+ }
227
+ if (stripped && data.mode === "dev-only") {
228
+ strippedDevOnlyPaths.push(data.path);
229
+ continue;
230
+ }
231
+ sorted[key] = data;
232
+ }
233
+ const serialised = JSON.stringify(sorted);
234
+ const fullChecksum = createHash("sha256").update(serialised).digest("hex");
235
+ const checksum = fullChecksum.substring(0, 16);
236
+ const buildId = `${Date.now().toString(36)}-${fullChecksum.substring(0, 6)}`;
237
+ return {
238
+ manifest: { buildId, checksum, tokens: sorted },
239
+ strippedDevOnlyPaths
240
+ };
241
+ }
242
+ function injectRecoveryManifest(html, manifest) {
243
+ if (Object.keys(manifest.tokens).length === 0) {
244
+ return html;
245
+ }
246
+ const json = JSON.stringify(manifest);
247
+ const scriptTag = `<script id="__SZ_RECOVERY_MANIFEST__" type="application/json">${json}</script>`;
248
+ if (html.includes("</head>")) {
249
+ return html.replace("</head>", `${scriptTag}
250
+ </head>`);
251
+ } else if (html.includes("</html>")) {
252
+ return html.replace("</html>", `${scriptTag}
253
+ </html>`);
254
+ }
255
+ return html + scriptTag;
256
+ }
216
257
 
217
258
  // src/theme-type-writer.ts
218
259
  import { mkdirSync, writeFileSync } from "fs";
@@ -542,7 +583,8 @@ function createCsszyxPlugins(options = {}) {
542
583
  mangleMap: {},
543
584
  checksum: "",
544
585
  finalized: false,
545
- rootDir: process.cwd()
586
+ rootDir: process.cwd(),
587
+ recoveryTokens: /* @__PURE__ */ new Map()
546
588
  };
547
589
  const SAFELIST_FILENAME = "csszyx-classes.html";
548
590
  const SOURCE_EXTENSIONS = /* @__PURE__ */ new Set([".tsx", ".jsx", ".ts", ".js"]);
@@ -587,7 +629,7 @@ function createCsszyxPlugins(options = {}) {
587
629
  if (!content.includes("sz=") && !content.includes("sz:")) {
588
630
  continue;
589
631
  }
590
- const result = transformSourceCode(content);
632
+ const result = transformSourceCode(content, filePath);
591
633
  if (!result.transformed) {
592
634
  continue;
593
635
  }
@@ -597,6 +639,9 @@ function createCsszyxPlugins(options = {}) {
597
639
  for (const cls of result.rawClassNames) {
598
640
  rawDiscoveredClasses.add(cls);
599
641
  }
642
+ for (const [token, data] of result.recoveryTokens) {
643
+ state.recoveryTokens.set(token, data);
644
+ }
600
645
  if (result.usesRuntime) {
601
646
  const szCallRe = /_sz\(\s*\{/g;
602
647
  let szMatch;
@@ -818,7 +863,7 @@ ${sourceDirective}`
818
863
  transformed = true;
819
864
  }
820
865
  } else {
821
- const result = transformSourceCode(code);
866
+ const result = transformSourceCode(code, id);
822
867
  transformedCode = result.code;
823
868
  usesRuntime = result.usesRuntime;
824
869
  usesMerge = result.usesMerge;
@@ -831,6 +876,9 @@ ${sourceDirective}`
831
876
  ${msg}`);
832
877
  }
833
878
  }
879
+ for (const [token, data] of result.recoveryTokens) {
880
+ state.recoveryTokens.set(token, data);
881
+ }
834
882
  }
835
883
  }
836
884
  if (transformedCode.includes("<html") && /layout|Root|Document|app\\.tsx?$/i.test(id)) {
@@ -971,7 +1019,7 @@ ${sourceDirective}`
971
1019
  return;
972
1020
  }
973
1021
  try {
974
- result = transformSourceCode(fileContent);
1022
+ result = transformSourceCode(fileContent, ctx.file);
975
1023
  } catch {
976
1024
  return;
977
1025
  }
@@ -982,6 +1030,9 @@ ${sourceDirective}`
982
1030
  for (const cls of result.classes) {
983
1031
  state.classes.add(cls);
984
1032
  }
1033
+ for (const [token, data] of result.recoveryTokens) {
1034
+ state.recoveryTokens.set(token, data);
1035
+ }
985
1036
  if (state.classes.size > sizeBefore) {
986
1037
  writeSafelistFile(state.classes);
987
1038
  const safelistPath = path.join(state.rootDir, SAFELIST_FILENAME);
@@ -998,10 +1049,24 @@ ${sourceDirective}`
998
1049
  */
999
1050
  handler(html) {
1000
1051
  finalizeMangleMap();
1001
- return transformIndexHtml(html, state.mangleMap, state.checksum, {
1052
+ let result = transformIndexHtml(html, state.mangleMap, state.checksum, {
1002
1053
  mode: options.production?.injectChecksum === false ? "script" : "script",
1003
1054
  minify: process.env.NODE_ENV === "production"
1004
1055
  });
1056
+ if (state.recoveryTokens.size > 0) {
1057
+ const isProduction = process.env.NODE_ENV === "production";
1058
+ const { manifest, strippedDevOnlyPaths } = buildRecoveryManifest(
1059
+ state.recoveryTokens,
1060
+ { production: isProduction }
1061
+ );
1062
+ if (strippedDevOnlyPaths.length > 0) {
1063
+ console.warn(
1064
+ `[csszyx] Stripped ${strippedDevOnlyPaths.length} szRecover="dev-only" token(s) from the production manifest. Recovery for these elements is disabled in production by design. Sites: ${strippedDevOnlyPaths.join(", ")}`
1065
+ );
1066
+ }
1067
+ result = injectRecoveryManifest(result, manifest);
1068
+ }
1069
+ return result;
1005
1070
  }
1006
1071
  }
1007
1072
  }
package/dist/index.cjs CHANGED
@@ -395,6 +395,7 @@ var import_vue_adapter = require("@csszyx/vue-adapter");
395
395
  var import_unplugin = require("unplugin");
396
396
 
397
397
  // src/html-transformer.ts
398
+ var import_node_crypto = require("crypto");
398
399
  function injectChecksum(html, checksum, minify = false) {
399
400
  const attrName = minify ? "data-sz-cs" : "data-sz-checksum";
400
401
  const htmlTagPattern = /<html([^>]*)>/i;
@@ -454,6 +455,46 @@ function injectHydrationData(html, mangleMap, checksum, options = {}) {
454
455
  function transformIndexHtml(html, mangleMap, checksum, options = {}) {
455
456
  return injectHydrationData(html, mangleMap, checksum, options);
456
457
  }
458
+ function buildRecoveryManifest(tokens, options = {}) {
459
+ const stripped = options.production === true;
460
+ const strippedDevOnlyPaths = [];
461
+ const sorted = {};
462
+ const sortedKeys = [...tokens.keys()].sort();
463
+ for (const key of sortedKeys) {
464
+ const data = tokens.get(key);
465
+ if (!data) {
466
+ continue;
467
+ }
468
+ if (stripped && data.mode === "dev-only") {
469
+ strippedDevOnlyPaths.push(data.path);
470
+ continue;
471
+ }
472
+ sorted[key] = data;
473
+ }
474
+ const serialised = JSON.stringify(sorted);
475
+ const fullChecksum = (0, import_node_crypto.createHash)("sha256").update(serialised).digest("hex");
476
+ const checksum = fullChecksum.substring(0, 16);
477
+ const buildId = `${Date.now().toString(36)}-${fullChecksum.substring(0, 6)}`;
478
+ return {
479
+ manifest: { buildId, checksum, tokens: sorted },
480
+ strippedDevOnlyPaths
481
+ };
482
+ }
483
+ function injectRecoveryManifest(html, manifest) {
484
+ if (Object.keys(manifest.tokens).length === 0) {
485
+ return html;
486
+ }
487
+ const json = JSON.stringify(manifest);
488
+ const scriptTag = `<script id="__SZ_RECOVERY_MANIFEST__" type="application/json">${json}</script>`;
489
+ if (html.includes("</head>")) {
490
+ return html.replace("</head>", `${scriptTag}
491
+ </head>`);
492
+ } else if (html.includes("</html>")) {
493
+ return html.replace("</html>", `${scriptTag}
494
+ </html>`);
495
+ }
496
+ return html + scriptTag;
497
+ }
457
498
 
458
499
  // src/theme-type-writer.ts
459
500
  var import_node_fs = require("fs");
@@ -783,7 +824,8 @@ function createCsszyxPlugins(options = {}) {
783
824
  mangleMap: {},
784
825
  checksum: "",
785
826
  finalized: false,
786
- rootDir: process.cwd()
827
+ rootDir: process.cwd(),
828
+ recoveryTokens: /* @__PURE__ */ new Map()
787
829
  };
788
830
  const SAFELIST_FILENAME = "csszyx-classes.html";
789
831
  const SOURCE_EXTENSIONS = /* @__PURE__ */ new Set([".tsx", ".jsx", ".ts", ".js"]);
@@ -828,7 +870,7 @@ function createCsszyxPlugins(options = {}) {
828
870
  if (!content.includes("sz=") && !content.includes("sz:")) {
829
871
  continue;
830
872
  }
831
- const result = (0, import_compiler.transformSourceCode)(content);
873
+ const result = (0, import_compiler.transformSourceCode)(content, filePath);
832
874
  if (!result.transformed) {
833
875
  continue;
834
876
  }
@@ -838,6 +880,9 @@ function createCsszyxPlugins(options = {}) {
838
880
  for (const cls of result.rawClassNames) {
839
881
  rawDiscoveredClasses.add(cls);
840
882
  }
883
+ for (const [token, data] of result.recoveryTokens) {
884
+ state.recoveryTokens.set(token, data);
885
+ }
841
886
  if (result.usesRuntime) {
842
887
  const szCallRe = /_sz\(\s*\{/g;
843
888
  let szMatch;
@@ -1059,7 +1104,7 @@ ${sourceDirective}`
1059
1104
  transformed = true;
1060
1105
  }
1061
1106
  } else {
1062
- const result = (0, import_compiler.transformSourceCode)(code);
1107
+ const result = (0, import_compiler.transformSourceCode)(code, id);
1063
1108
  transformedCode = result.code;
1064
1109
  usesRuntime = result.usesRuntime;
1065
1110
  usesMerge = result.usesMerge;
@@ -1072,6 +1117,9 @@ ${sourceDirective}`
1072
1117
  ${msg}`);
1073
1118
  }
1074
1119
  }
1120
+ for (const [token, data] of result.recoveryTokens) {
1121
+ state.recoveryTokens.set(token, data);
1122
+ }
1075
1123
  }
1076
1124
  }
1077
1125
  if (transformedCode.includes("<html") && /layout|Root|Document|app\\.tsx?$/i.test(id)) {
@@ -1212,7 +1260,7 @@ ${sourceDirective}`
1212
1260
  return;
1213
1261
  }
1214
1262
  try {
1215
- result = (0, import_compiler.transformSourceCode)(fileContent);
1263
+ result = (0, import_compiler.transformSourceCode)(fileContent, ctx.file);
1216
1264
  } catch {
1217
1265
  return;
1218
1266
  }
@@ -1223,6 +1271,9 @@ ${sourceDirective}`
1223
1271
  for (const cls of result.classes) {
1224
1272
  state.classes.add(cls);
1225
1273
  }
1274
+ for (const [token, data] of result.recoveryTokens) {
1275
+ state.recoveryTokens.set(token, data);
1276
+ }
1226
1277
  if (state.classes.size > sizeBefore) {
1227
1278
  writeSafelistFile(state.classes);
1228
1279
  const safelistPath = path.join(state.rootDir, SAFELIST_FILENAME);
@@ -1239,10 +1290,24 @@ ${sourceDirective}`
1239
1290
  */
1240
1291
  handler(html) {
1241
1292
  finalizeMangleMap();
1242
- return transformIndexHtml(html, state.mangleMap, state.checksum, {
1293
+ let result = transformIndexHtml(html, state.mangleMap, state.checksum, {
1243
1294
  mode: options.production?.injectChecksum === false ? "script" : "script",
1244
1295
  minify: process.env.NODE_ENV === "production"
1245
1296
  });
1297
+ if (state.recoveryTokens.size > 0) {
1298
+ const isProduction = process.env.NODE_ENV === "production";
1299
+ const { manifest, strippedDevOnlyPaths } = buildRecoveryManifest(
1300
+ state.recoveryTokens,
1301
+ { production: isProduction }
1302
+ );
1303
+ if (strippedDevOnlyPaths.length > 0) {
1304
+ console.warn(
1305
+ `[csszyx] Stripped ${strippedDevOnlyPaths.length} szRecover="dev-only" token(s) from the production manifest. Recovery for these elements is disabled in production by design. Sites: ${strippedDevOnlyPaths.join(", ")}`
1306
+ );
1307
+ }
1308
+ result = injectRecoveryManifest(result, manifest);
1309
+ }
1310
+ return result;
1246
1311
  }
1247
1312
  }
1248
1313
  }
package/dist/index.js CHANGED
@@ -8,7 +8,7 @@ import {
8
8
  unplugin,
9
9
  vitePlugin,
10
10
  webpackPlugin
11
- } from "./chunk-CW4XYEQR.js";
11
+ } from "./chunk-HOQTC45W.js";
12
12
  import {
13
13
  createPostCSSPlugin,
14
14
  escapeCSSClassName,
package/dist/vite.cjs CHANGED
@@ -140,6 +140,7 @@ function mangleCSSSync(css, mangleMap, options = {}) {
140
140
  }
141
141
 
142
142
  // src/html-transformer.ts
143
+ var import_node_crypto = require("crypto");
143
144
  function injectChecksum(html, checksum, minify = false) {
144
145
  const attrName = minify ? "data-sz-cs" : "data-sz-checksum";
145
146
  const htmlTagPattern = /<html([^>]*)>/i;
@@ -199,6 +200,46 @@ function injectHydrationData(html, mangleMap, checksum, options = {}) {
199
200
  function transformIndexHtml(html, mangleMap, checksum, options = {}) {
200
201
  return injectHydrationData(html, mangleMap, checksum, options);
201
202
  }
203
+ function buildRecoveryManifest(tokens, options = {}) {
204
+ const stripped = options.production === true;
205
+ const strippedDevOnlyPaths = [];
206
+ const sorted = {};
207
+ const sortedKeys = [...tokens.keys()].sort();
208
+ for (const key of sortedKeys) {
209
+ const data = tokens.get(key);
210
+ if (!data) {
211
+ continue;
212
+ }
213
+ if (stripped && data.mode === "dev-only") {
214
+ strippedDevOnlyPaths.push(data.path);
215
+ continue;
216
+ }
217
+ sorted[key] = data;
218
+ }
219
+ const serialised = JSON.stringify(sorted);
220
+ const fullChecksum = (0, import_node_crypto.createHash)("sha256").update(serialised).digest("hex");
221
+ const checksum = fullChecksum.substring(0, 16);
222
+ const buildId = `${Date.now().toString(36)}-${fullChecksum.substring(0, 6)}`;
223
+ return {
224
+ manifest: { buildId, checksum, tokens: sorted },
225
+ strippedDevOnlyPaths
226
+ };
227
+ }
228
+ function injectRecoveryManifest(html, manifest) {
229
+ if (Object.keys(manifest.tokens).length === 0) {
230
+ return html;
231
+ }
232
+ const json = JSON.stringify(manifest);
233
+ const scriptTag = `<script id="__SZ_RECOVERY_MANIFEST__" type="application/json">${json}</script>`;
234
+ if (html.includes("</head>")) {
235
+ return html.replace("</head>", `${scriptTag}
236
+ </head>`);
237
+ } else if (html.includes("</html>")) {
238
+ return html.replace("</html>", `${scriptTag}
239
+ </html>`);
240
+ }
241
+ return html + scriptTag;
242
+ }
202
243
 
203
244
  // src/theme-scanner.ts
204
245
  var EMPTY_THEME = { colors: [], spacings: [], fonts: [], radii: [], shadows: [] };
@@ -667,7 +708,8 @@ function createCsszyxPlugins(options = {}) {
667
708
  mangleMap: {},
668
709
  checksum: "",
669
710
  finalized: false,
670
- rootDir: process.cwd()
711
+ rootDir: process.cwd(),
712
+ recoveryTokens: /* @__PURE__ */ new Map()
671
713
  };
672
714
  const SAFELIST_FILENAME = "csszyx-classes.html";
673
715
  const SOURCE_EXTENSIONS = /* @__PURE__ */ new Set([".tsx", ".jsx", ".ts", ".js"]);
@@ -712,7 +754,7 @@ function createCsszyxPlugins(options = {}) {
712
754
  if (!content.includes("sz=") && !content.includes("sz:")) {
713
755
  continue;
714
756
  }
715
- const result = (0, import_compiler.transformSourceCode)(content);
757
+ const result = (0, import_compiler.transformSourceCode)(content, filePath);
716
758
  if (!result.transformed) {
717
759
  continue;
718
760
  }
@@ -722,6 +764,9 @@ function createCsszyxPlugins(options = {}) {
722
764
  for (const cls of result.rawClassNames) {
723
765
  rawDiscoveredClasses.add(cls);
724
766
  }
767
+ for (const [token, data] of result.recoveryTokens) {
768
+ state.recoveryTokens.set(token, data);
769
+ }
725
770
  if (result.usesRuntime) {
726
771
  const szCallRe = /_sz\(\s*\{/g;
727
772
  let szMatch;
@@ -943,7 +988,7 @@ ${sourceDirective}`
943
988
  transformed = true;
944
989
  }
945
990
  } else {
946
- const result = (0, import_compiler.transformSourceCode)(code);
991
+ const result = (0, import_compiler.transformSourceCode)(code, id);
947
992
  transformedCode = result.code;
948
993
  usesRuntime = result.usesRuntime;
949
994
  usesMerge = result.usesMerge;
@@ -956,6 +1001,9 @@ ${sourceDirective}`
956
1001
  ${msg}`);
957
1002
  }
958
1003
  }
1004
+ for (const [token, data] of result.recoveryTokens) {
1005
+ state.recoveryTokens.set(token, data);
1006
+ }
959
1007
  }
960
1008
  }
961
1009
  if (transformedCode.includes("<html") && /layout|Root|Document|app\\.tsx?$/i.test(id)) {
@@ -1096,7 +1144,7 @@ ${sourceDirective}`
1096
1144
  return;
1097
1145
  }
1098
1146
  try {
1099
- result = (0, import_compiler.transformSourceCode)(fileContent);
1147
+ result = (0, import_compiler.transformSourceCode)(fileContent, ctx.file);
1100
1148
  } catch {
1101
1149
  return;
1102
1150
  }
@@ -1107,6 +1155,9 @@ ${sourceDirective}`
1107
1155
  for (const cls of result.classes) {
1108
1156
  state.classes.add(cls);
1109
1157
  }
1158
+ for (const [token, data] of result.recoveryTokens) {
1159
+ state.recoveryTokens.set(token, data);
1160
+ }
1110
1161
  if (state.classes.size > sizeBefore) {
1111
1162
  writeSafelistFile(state.classes);
1112
1163
  const safelistPath = path.join(state.rootDir, SAFELIST_FILENAME);
@@ -1123,10 +1174,24 @@ ${sourceDirective}`
1123
1174
  */
1124
1175
  handler(html) {
1125
1176
  finalizeMangleMap();
1126
- return transformIndexHtml(html, state.mangleMap, state.checksum, {
1177
+ let result = transformIndexHtml(html, state.mangleMap, state.checksum, {
1127
1178
  mode: options.production?.injectChecksum === false ? "script" : "script",
1128
1179
  minify: process.env.NODE_ENV === "production"
1129
1180
  });
1181
+ if (state.recoveryTokens.size > 0) {
1182
+ const isProduction = process.env.NODE_ENV === "production";
1183
+ const { manifest, strippedDevOnlyPaths } = buildRecoveryManifest(
1184
+ state.recoveryTokens,
1185
+ { production: isProduction }
1186
+ );
1187
+ if (strippedDevOnlyPaths.length > 0) {
1188
+ console.warn(
1189
+ `[csszyx] Stripped ${strippedDevOnlyPaths.length} szRecover="dev-only" token(s) from the production manifest. Recovery for these elements is disabled in production by design. Sites: ${strippedDevOnlyPaths.join(", ")}`
1190
+ );
1191
+ }
1192
+ result = injectRecoveryManifest(result, manifest);
1193
+ }
1194
+ return result;
1130
1195
  }
1131
1196
  }
1132
1197
  }
package/dist/vite.js CHANGED
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  vitePlugin
3
- } from "./chunk-CW4XYEQR.js";
3
+ } from "./chunk-HOQTC45W.js";
4
4
  import "./chunk-4M7CPGP7.js";
5
5
 
6
6
  // src/vite.ts
package/dist/webpack.cjs CHANGED
@@ -140,6 +140,7 @@ function mangleCSSSync(css, mangleMap, options = {}) {
140
140
  }
141
141
 
142
142
  // src/html-transformer.ts
143
+ var import_node_crypto = require("crypto");
143
144
  function injectChecksum(html, checksum, minify = false) {
144
145
  const attrName = minify ? "data-sz-cs" : "data-sz-checksum";
145
146
  const htmlTagPattern = /<html([^>]*)>/i;
@@ -199,6 +200,46 @@ function injectHydrationData(html, mangleMap, checksum, options = {}) {
199
200
  function transformIndexHtml(html, mangleMap, checksum, options = {}) {
200
201
  return injectHydrationData(html, mangleMap, checksum, options);
201
202
  }
203
+ function buildRecoveryManifest(tokens, options = {}) {
204
+ const stripped = options.production === true;
205
+ const strippedDevOnlyPaths = [];
206
+ const sorted = {};
207
+ const sortedKeys = [...tokens.keys()].sort();
208
+ for (const key of sortedKeys) {
209
+ const data = tokens.get(key);
210
+ if (!data) {
211
+ continue;
212
+ }
213
+ if (stripped && data.mode === "dev-only") {
214
+ strippedDevOnlyPaths.push(data.path);
215
+ continue;
216
+ }
217
+ sorted[key] = data;
218
+ }
219
+ const serialised = JSON.stringify(sorted);
220
+ const fullChecksum = (0, import_node_crypto.createHash)("sha256").update(serialised).digest("hex");
221
+ const checksum = fullChecksum.substring(0, 16);
222
+ const buildId = `${Date.now().toString(36)}-${fullChecksum.substring(0, 6)}`;
223
+ return {
224
+ manifest: { buildId, checksum, tokens: sorted },
225
+ strippedDevOnlyPaths
226
+ };
227
+ }
228
+ function injectRecoveryManifest(html, manifest) {
229
+ if (Object.keys(manifest.tokens).length === 0) {
230
+ return html;
231
+ }
232
+ const json = JSON.stringify(manifest);
233
+ const scriptTag = `<script id="__SZ_RECOVERY_MANIFEST__" type="application/json">${json}</script>`;
234
+ if (html.includes("</head>")) {
235
+ return html.replace("</head>", `${scriptTag}
236
+ </head>`);
237
+ } else if (html.includes("</html>")) {
238
+ return html.replace("</html>", `${scriptTag}
239
+ </html>`);
240
+ }
241
+ return html + scriptTag;
242
+ }
202
243
 
203
244
  // src/theme-scanner.ts
204
245
  var EMPTY_THEME = { colors: [], spacings: [], fonts: [], radii: [], shadows: [] };
@@ -667,7 +708,8 @@ function createCsszyxPlugins(options = {}) {
667
708
  mangleMap: {},
668
709
  checksum: "",
669
710
  finalized: false,
670
- rootDir: process.cwd()
711
+ rootDir: process.cwd(),
712
+ recoveryTokens: /* @__PURE__ */ new Map()
671
713
  };
672
714
  const SAFELIST_FILENAME = "csszyx-classes.html";
673
715
  const SOURCE_EXTENSIONS = /* @__PURE__ */ new Set([".tsx", ".jsx", ".ts", ".js"]);
@@ -712,7 +754,7 @@ function createCsszyxPlugins(options = {}) {
712
754
  if (!content.includes("sz=") && !content.includes("sz:")) {
713
755
  continue;
714
756
  }
715
- const result = (0, import_compiler.transformSourceCode)(content);
757
+ const result = (0, import_compiler.transformSourceCode)(content, filePath);
716
758
  if (!result.transformed) {
717
759
  continue;
718
760
  }
@@ -722,6 +764,9 @@ function createCsszyxPlugins(options = {}) {
722
764
  for (const cls of result.rawClassNames) {
723
765
  rawDiscoveredClasses.add(cls);
724
766
  }
767
+ for (const [token, data] of result.recoveryTokens) {
768
+ state.recoveryTokens.set(token, data);
769
+ }
725
770
  if (result.usesRuntime) {
726
771
  const szCallRe = /_sz\(\s*\{/g;
727
772
  let szMatch;
@@ -943,7 +988,7 @@ ${sourceDirective}`
943
988
  transformed = true;
944
989
  }
945
990
  } else {
946
- const result = (0, import_compiler.transformSourceCode)(code);
991
+ const result = (0, import_compiler.transformSourceCode)(code, id);
947
992
  transformedCode = result.code;
948
993
  usesRuntime = result.usesRuntime;
949
994
  usesMerge = result.usesMerge;
@@ -956,6 +1001,9 @@ ${sourceDirective}`
956
1001
  ${msg}`);
957
1002
  }
958
1003
  }
1004
+ for (const [token, data] of result.recoveryTokens) {
1005
+ state.recoveryTokens.set(token, data);
1006
+ }
959
1007
  }
960
1008
  }
961
1009
  if (transformedCode.includes("<html") && /layout|Root|Document|app\\.tsx?$/i.test(id)) {
@@ -1096,7 +1144,7 @@ ${sourceDirective}`
1096
1144
  return;
1097
1145
  }
1098
1146
  try {
1099
- result = (0, import_compiler.transformSourceCode)(fileContent);
1147
+ result = (0, import_compiler.transformSourceCode)(fileContent, ctx.file);
1100
1148
  } catch {
1101
1149
  return;
1102
1150
  }
@@ -1107,6 +1155,9 @@ ${sourceDirective}`
1107
1155
  for (const cls of result.classes) {
1108
1156
  state.classes.add(cls);
1109
1157
  }
1158
+ for (const [token, data] of result.recoveryTokens) {
1159
+ state.recoveryTokens.set(token, data);
1160
+ }
1110
1161
  if (state.classes.size > sizeBefore) {
1111
1162
  writeSafelistFile(state.classes);
1112
1163
  const safelistPath = path.join(state.rootDir, SAFELIST_FILENAME);
@@ -1123,10 +1174,24 @@ ${sourceDirective}`
1123
1174
  */
1124
1175
  handler(html) {
1125
1176
  finalizeMangleMap();
1126
- return transformIndexHtml(html, state.mangleMap, state.checksum, {
1177
+ let result = transformIndexHtml(html, state.mangleMap, state.checksum, {
1127
1178
  mode: options.production?.injectChecksum === false ? "script" : "script",
1128
1179
  minify: process.env.NODE_ENV === "production"
1129
1180
  });
1181
+ if (state.recoveryTokens.size > 0) {
1182
+ const isProduction = process.env.NODE_ENV === "production";
1183
+ const { manifest, strippedDevOnlyPaths } = buildRecoveryManifest(
1184
+ state.recoveryTokens,
1185
+ { production: isProduction }
1186
+ );
1187
+ if (strippedDevOnlyPaths.length > 0) {
1188
+ console.warn(
1189
+ `[csszyx] Stripped ${strippedDevOnlyPaths.length} szRecover="dev-only" token(s) from the production manifest. Recovery for these elements is disabled in production by design. Sites: ${strippedDevOnlyPaths.join(", ")}`
1190
+ );
1191
+ }
1192
+ result = injectRecoveryManifest(result, manifest);
1193
+ }
1194
+ return result;
1130
1195
  }
1131
1196
  }
1132
1197
  }
package/dist/webpack.js CHANGED
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  webpackPlugin
3
- } from "./chunk-CW4XYEQR.js";
3
+ } from "./chunk-HOQTC45W.js";
4
4
  import "./chunk-4M7CPGP7.js";
5
5
 
6
6
  // src/webpack.ts
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@csszyx/unplugin",
3
- "version": "0.5.0",
3
+ "version": "0.6.0",
4
4
  "description": "Vite and Webpack integration for csszyx",
5
5
  "keywords": [
6
6
  "csszyx",
@@ -55,11 +55,11 @@
55
55
  "postcss": "^8.4.35",
56
56
  "postcss-selector-parser": "^6.0.15",
57
57
  "unplugin": "^1.10.1",
58
- "@csszyx/compiler": "0.5.0",
59
- "@csszyx/core": "0.5.0",
60
- "@csszyx/svelte-adapter": "0.5.0",
61
- "@csszyx/types": "0.5.0",
62
- "@csszyx/vue-adapter": "0.5.0"
58
+ "@csszyx/compiler": "0.6.0",
59
+ "@csszyx/svelte-adapter": "0.6.0",
60
+ "@csszyx/core": "0.6.0",
61
+ "@csszyx/types": "0.6.0",
62
+ "@csszyx/vue-adapter": "0.6.0"
63
63
  },
64
64
  "devDependencies": {
65
65
  "@types/node": "^20.11.0",