@steambrew/ttc 3.1.1 → 3.2.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/bun.lock CHANGED
@@ -25,6 +25,7 @@
25
25
  "glob": "^11.0.2",
26
26
  "magic-string": "^0.30.17",
27
27
  "rollup": "^4.42.0",
28
+ "rollup-plugin-esbuild": "^6.0.0",
28
29
  "rollup-plugin-inject-process-env": "^1.3.1",
29
30
  "rollup-plugin-polyfill-node": "^0.13.0",
30
31
  "rollup-plugin-scss": "^4.0.1",
@@ -234,6 +235,58 @@
234
235
 
235
236
  "@babel/types": ["@babel/types@7.27.6", "", { "dependencies": { "@babel/helper-string-parser": "7.27.1", "@babel/helper-validator-identifier": "7.27.1" } }, "sha512-ETyHEk2VHHvl9b9jZP5IHPavHYk57EhanlRRuae9XCpb/j5bDCbPPMOBfCWhnl/7EDJz0jEMCi/RhccCE8r1+Q=="],
236
237
 
238
+ "@esbuild/aix-ppc64": ["@esbuild/aix-ppc64@0.27.3", "", { "os": "aix", "cpu": "ppc64" }, "sha512-9fJMTNFTWZMh5qwrBItuziu834eOCUcEqymSH7pY+zoMVEZg3gcPuBNxH1EvfVYe9h0x/Ptw8KBzv7qxb7l8dg=="],
239
+
240
+ "@esbuild/android-arm": ["@esbuild/android-arm@0.27.3", "", { "os": "android", "cpu": "arm" }, "sha512-i5D1hPY7GIQmXlXhs2w8AWHhenb00+GxjxRncS2ZM7YNVGNfaMxgzSGuO8o8SJzRc/oZwU2bcScvVERk03QhzA=="],
241
+
242
+ "@esbuild/android-arm64": ["@esbuild/android-arm64@0.27.3", "", { "os": "android", "cpu": "arm64" }, "sha512-YdghPYUmj/FX2SYKJ0OZxf+iaKgMsKHVPF1MAq/P8WirnSpCStzKJFjOjzsW0QQ7oIAiccHdcqjbHmJxRb/dmg=="],
243
+
244
+ "@esbuild/android-x64": ["@esbuild/android-x64@0.27.3", "", { "os": "android", "cpu": "x64" }, "sha512-IN/0BNTkHtk8lkOM8JWAYFg4ORxBkZQf9zXiEOfERX/CzxW3Vg1ewAhU7QSWQpVIzTW+b8Xy+lGzdYXV6UZObQ=="],
245
+
246
+ "@esbuild/darwin-arm64": ["@esbuild/darwin-arm64@0.27.3", "", { "os": "darwin", "cpu": "arm64" }, "sha512-Re491k7ByTVRy0t3EKWajdLIr0gz2kKKfzafkth4Q8A5n1xTHrkqZgLLjFEHVD+AXdUGgQMq+Godfq45mGpCKg=="],
247
+
248
+ "@esbuild/darwin-x64": ["@esbuild/darwin-x64@0.27.3", "", { "os": "darwin", "cpu": "x64" }, "sha512-vHk/hA7/1AckjGzRqi6wbo+jaShzRowYip6rt6q7VYEDX4LEy1pZfDpdxCBnGtl+A5zq8iXDcyuxwtv3hNtHFg=="],
249
+
250
+ "@esbuild/freebsd-arm64": ["@esbuild/freebsd-arm64@0.27.3", "", { "os": "freebsd", "cpu": "arm64" }, "sha512-ipTYM2fjt3kQAYOvo6vcxJx3nBYAzPjgTCk7QEgZG8AUO3ydUhvelmhrbOheMnGOlaSFUoHXB6un+A7q4ygY9w=="],
251
+
252
+ "@esbuild/freebsd-x64": ["@esbuild/freebsd-x64@0.27.3", "", { "os": "freebsd", "cpu": "x64" }, "sha512-dDk0X87T7mI6U3K9VjWtHOXqwAMJBNN2r7bejDsc+j03SEjtD9HrOl8gVFByeM0aJksoUuUVU9TBaZa2rgj0oA=="],
253
+
254
+ "@esbuild/linux-arm": ["@esbuild/linux-arm@0.27.3", "", { "os": "linux", "cpu": "arm" }, "sha512-s6nPv2QkSupJwLYyfS+gwdirm0ukyTFNl3KTgZEAiJDd+iHZcbTPPcWCcRYH+WlNbwChgH2QkE9NSlNrMT8Gfw=="],
255
+
256
+ "@esbuild/linux-arm64": ["@esbuild/linux-arm64@0.27.3", "", { "os": "linux", "cpu": "arm64" }, "sha512-sZOuFz/xWnZ4KH3YfFrKCf1WyPZHakVzTiqji3WDc0BCl2kBwiJLCXpzLzUBLgmp4veFZdvN5ChW4Eq/8Fc2Fg=="],
257
+
258
+ "@esbuild/linux-ia32": ["@esbuild/linux-ia32@0.27.3", "", { "os": "linux", "cpu": "ia32" }, "sha512-yGlQYjdxtLdh0a3jHjuwOrxQjOZYD/C9PfdbgJJF3TIZWnm/tMd/RcNiLngiu4iwcBAOezdnSLAwQDPqTmtTYg=="],
259
+
260
+ "@esbuild/linux-loong64": ["@esbuild/linux-loong64@0.27.3", "", { "os": "linux", "cpu": "none" }, "sha512-WO60Sn8ly3gtzhyjATDgieJNet/KqsDlX5nRC5Y3oTFcS1l0KWba+SEa9Ja1GfDqSF1z6hif/SkpQJbL63cgOA=="],
261
+
262
+ "@esbuild/linux-mips64el": ["@esbuild/linux-mips64el@0.27.3", "", { "os": "linux", "cpu": "none" }, "sha512-APsymYA6sGcZ4pD6k+UxbDjOFSvPWyZhjaiPyl/f79xKxwTnrn5QUnXR5prvetuaSMsb4jgeHewIDCIWljrSxw=="],
263
+
264
+ "@esbuild/linux-ppc64": ["@esbuild/linux-ppc64@0.27.3", "", { "os": "linux", "cpu": "ppc64" }, "sha512-eizBnTeBefojtDb9nSh4vvVQ3V9Qf9Df01PfawPcRzJH4gFSgrObw+LveUyDoKU3kxi5+9RJTCWlj4FjYXVPEA=="],
265
+
266
+ "@esbuild/linux-riscv64": ["@esbuild/linux-riscv64@0.27.3", "", { "os": "linux", "cpu": "none" }, "sha512-3Emwh0r5wmfm3ssTWRQSyVhbOHvqegUDRd0WhmXKX2mkHJe1SFCMJhagUleMq+Uci34wLSipf8Lagt4LlpRFWQ=="],
267
+
268
+ "@esbuild/linux-s390x": ["@esbuild/linux-s390x@0.27.3", "", { "os": "linux", "cpu": "s390x" }, "sha512-pBHUx9LzXWBc7MFIEEL0yD/ZVtNgLytvx60gES28GcWMqil8ElCYR4kvbV2BDqsHOvVDRrOxGySBM9Fcv744hw=="],
269
+
270
+ "@esbuild/linux-x64": ["@esbuild/linux-x64@0.27.3", "", { "os": "linux", "cpu": "x64" }, "sha512-Czi8yzXUWIQYAtL/2y6vogER8pvcsOsk5cpwL4Gk5nJqH5UZiVByIY8Eorm5R13gq+DQKYg0+JyQoytLQas4dA=="],
271
+
272
+ "@esbuild/netbsd-arm64": ["@esbuild/netbsd-arm64@0.27.3", "", { "os": "none", "cpu": "arm64" }, "sha512-sDpk0RgmTCR/5HguIZa9n9u+HVKf40fbEUt+iTzSnCaGvY9kFP0YKBWZtJaraonFnqef5SlJ8/TiPAxzyS+UoA=="],
273
+
274
+ "@esbuild/netbsd-x64": ["@esbuild/netbsd-x64@0.27.3", "", { "os": "none", "cpu": "x64" }, "sha512-P14lFKJl/DdaE00LItAukUdZO5iqNH7+PjoBm+fLQjtxfcfFE20Xf5CrLsmZdq5LFFZzb5JMZ9grUwvtVYzjiA=="],
275
+
276
+ "@esbuild/openbsd-arm64": ["@esbuild/openbsd-arm64@0.27.3", "", { "os": "openbsd", "cpu": "arm64" }, "sha512-AIcMP77AvirGbRl/UZFTq5hjXK+2wC7qFRGoHSDrZ5v5b8DK/GYpXW3CPRL53NkvDqb9D+alBiC/dV0Fb7eJcw=="],
277
+
278
+ "@esbuild/openbsd-x64": ["@esbuild/openbsd-x64@0.27.3", "", { "os": "openbsd", "cpu": "x64" }, "sha512-DnW2sRrBzA+YnE70LKqnM3P+z8vehfJWHXECbwBmH/CU51z6FiqTQTHFenPlHmo3a8UgpLyH3PT+87OViOh1AQ=="],
279
+
280
+ "@esbuild/openharmony-arm64": ["@esbuild/openharmony-arm64@0.27.3", "", { "os": "none", "cpu": "arm64" }, "sha512-NinAEgr/etERPTsZJ7aEZQvvg/A6IsZG/LgZy+81wON2huV7SrK3e63dU0XhyZP4RKGyTm7aOgmQk0bGp0fy2g=="],
281
+
282
+ "@esbuild/sunos-x64": ["@esbuild/sunos-x64@0.27.3", "", { "os": "sunos", "cpu": "x64" }, "sha512-PanZ+nEz+eWoBJ8/f8HKxTTD172SKwdXebZ0ndd953gt1HRBbhMsaNqjTyYLGLPdoWHy4zLU7bDVJztF5f3BHA=="],
283
+
284
+ "@esbuild/win32-arm64": ["@esbuild/win32-arm64@0.27.3", "", { "os": "win32", "cpu": "arm64" }, "sha512-B2t59lWWYrbRDw/tjiWOuzSsFh1Y/E95ofKz7rIVYSQkUYBjfSgf6oeYPNWHToFRr2zx52JKApIcAS/D5TUBnA=="],
285
+
286
+ "@esbuild/win32-ia32": ["@esbuild/win32-ia32@0.27.3", "", { "os": "win32", "cpu": "ia32" }, "sha512-QLKSFeXNS8+tHW7tZpMtjlNb7HKau0QDpwm49u0vUp9y1WOF+PEzkU84y9GqYaAVW8aH8f3GcBck26jh54cX4Q=="],
287
+
288
+ "@esbuild/win32-x64": ["@esbuild/win32-x64@0.27.3", "", { "os": "win32", "cpu": "x64" }, "sha512-4uJGhsxuptu3OcpVAzli+/gWusVGwZZHTlS63hh++ehExkVT8SgiEf7/uC/PclrPPkLhZqGgCTjd0VWLo6xMqA=="],
289
+
237
290
  "@isaacs/cliui": ["@isaacs/cliui@8.0.2", "", { "dependencies": { "string-width": "5.1.2", "string-width-cjs": "npm:string-width@4.2.3", "strip-ansi": "7.1.0", "strip-ansi-cjs": "npm:strip-ansi@6.0.1", "wrap-ansi": "8.1.0", "wrap-ansi-cjs": "npm:wrap-ansi@7.0.0" } }, "sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA=="],
238
291
 
239
292
  "@jridgewell/gen-mapping": ["@jridgewell/gen-mapping@0.3.8", "", { "dependencies": { "@jridgewell/set-array": "1.2.1", "@jridgewell/sourcemap-codec": "1.5.0", "@jridgewell/trace-mapping": "0.3.25" } }, "sha512-imAbBGkb+ebQyxKgzv5Hu2nmROxoDOXHh80evxdoXNOrvAnVx7zimzc1Oo5h9RlfV4vPXaE2iM5pOFbvOCClWA=="],
@@ -404,6 +457,10 @@
404
457
 
405
458
  "emoji-regex": ["emoji-regex@9.2.2", "", {}, "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg=="],
406
459
 
460
+ "es-module-lexer": ["es-module-lexer@1.7.0", "", {}, "sha512-jEQoCwk8hyb2AZziIOLhDqpm5+2ww5uIE6lkO/6jcOCusfk6LhMHpXXfBLXTZ7Ydyt0j4VoUQv6uGNYbdW+kBA=="],
461
+
462
+ "esbuild": ["esbuild@0.27.3", "", { "optionalDependencies": { "@esbuild/aix-ppc64": "0.27.3", "@esbuild/android-arm": "0.27.3", "@esbuild/android-arm64": "0.27.3", "@esbuild/android-x64": "0.27.3", "@esbuild/darwin-arm64": "0.27.3", "@esbuild/darwin-x64": "0.27.3", "@esbuild/freebsd-arm64": "0.27.3", "@esbuild/freebsd-x64": "0.27.3", "@esbuild/linux-arm": "0.27.3", "@esbuild/linux-arm64": "0.27.3", "@esbuild/linux-ia32": "0.27.3", "@esbuild/linux-loong64": "0.27.3", "@esbuild/linux-mips64el": "0.27.3", "@esbuild/linux-ppc64": "0.27.3", "@esbuild/linux-riscv64": "0.27.3", "@esbuild/linux-s390x": "0.27.3", "@esbuild/linux-x64": "0.27.3", "@esbuild/netbsd-arm64": "0.27.3", "@esbuild/netbsd-x64": "0.27.3", "@esbuild/openbsd-arm64": "0.27.3", "@esbuild/openbsd-x64": "0.27.3", "@esbuild/openharmony-arm64": "0.27.3", "@esbuild/sunos-x64": "0.27.3", "@esbuild/win32-arm64": "0.27.3", "@esbuild/win32-ia32": "0.27.3", "@esbuild/win32-x64": "0.27.3" }, "bin": { "esbuild": "bin/esbuild" } }, "sha512-8VwMnyGCONIs6cWue2IdpHxHnAjzxnw2Zr7MkVxB2vjmQ2ivqGFb4LEG3SMnv0Gb2F/G/2yA8zUaiL1gywDCCg=="],
463
+
407
464
  "escalade": ["escalade@3.2.0", "", {}, "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA=="],
408
465
 
409
466
  "estree-walker": ["estree-walker@2.0.2", "", {}, "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w=="],
@@ -424,6 +481,8 @@
424
481
 
425
482
  "gensync": ["gensync@1.0.0-beta.2", "", {}, "sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg=="],
426
483
 
484
+ "get-tsconfig": ["get-tsconfig@4.13.6", "", { "dependencies": { "resolve-pkg-maps": "^1.0.0" } }, "sha512-shZT/QMiSHc/YBLxxOkMtgSid5HFoauqCE3/exfsEcwg1WkeqjG+V40yBbBrsD+jW2HDXcs28xOfcbm2jI8Ddw=="],
485
+
427
486
  "glob": ["glob@11.0.2", "", { "dependencies": { "foreground-child": "3.3.1", "jackspeak": "4.1.1", "minimatch": "10.0.1", "minipass": "7.1.2", "package-json-from-dist": "1.0.1", "path-scurry": "2.0.0" }, "bin": { "glob": "dist/esm/bin.mjs" } }, "sha512-YT7U7Vye+t5fZ/QMkBFrTJ7ZQxInIUjwyAjVj84CYXqgBdv30MFUPGnBR6sQaVq6Is15wYJUsnzTuWaGRBhBAQ=="],
428
487
 
429
488
  "globals": ["globals@11.12.0", "", {}, "sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA=="],
@@ -486,6 +545,8 @@
486
545
 
487
546
  "path-scurry": ["path-scurry@2.0.0", "", { "dependencies": { "lru-cache": "11.1.0", "minipass": "7.1.2" } }, "sha512-ypGJsmGtdXUOeM5u93TyeIEfEhM6s+ljAhrk5vAvSx8uyY/02OvrZnA0YNGUrPXfpJMgI1ODd3nwz8Npx4O4cg=="],
488
547
 
548
+ "pathe": ["pathe@2.0.3", "", {}, "sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w=="],
549
+
489
550
  "picocolors": ["picocolors@1.1.1", "", {}, "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA=="],
490
551
 
491
552
  "picomatch": ["picomatch@4.0.2", "", {}, "sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg=="],
@@ -506,8 +567,12 @@
506
567
 
507
568
  "resolve": ["resolve@1.22.10", "", { "dependencies": { "is-core-module": "2.16.1", "path-parse": "1.0.7", "supports-preserve-symlinks-flag": "1.0.0" }, "bin": { "resolve": "bin/resolve" } }, "sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w=="],
508
569
 
570
+ "resolve-pkg-maps": ["resolve-pkg-maps@1.0.0", "", {}, "sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw=="],
571
+
509
572
  "rollup": ["rollup@4.42.0", "", { "dependencies": { "@types/estree": "1.0.7" }, "optionalDependencies": { "@rollup/rollup-android-arm-eabi": "4.42.0", "@rollup/rollup-android-arm64": "4.42.0", "@rollup/rollup-darwin-arm64": "4.42.0", "@rollup/rollup-darwin-x64": "4.42.0", "@rollup/rollup-freebsd-arm64": "4.42.0", "@rollup/rollup-freebsd-x64": "4.42.0", "@rollup/rollup-linux-arm-gnueabihf": "4.42.0", "@rollup/rollup-linux-arm-musleabihf": "4.42.0", "@rollup/rollup-linux-arm64-gnu": "4.42.0", "@rollup/rollup-linux-arm64-musl": "4.42.0", "@rollup/rollup-linux-loongarch64-gnu": "4.42.0", "@rollup/rollup-linux-powerpc64le-gnu": "4.42.0", "@rollup/rollup-linux-riscv64-gnu": "4.42.0", "@rollup/rollup-linux-riscv64-musl": "4.42.0", "@rollup/rollup-linux-s390x-gnu": "4.42.0", "@rollup/rollup-linux-x64-gnu": "4.42.0", "@rollup/rollup-linux-x64-musl": "4.42.0", "@rollup/rollup-win32-arm64-msvc": "4.42.0", "@rollup/rollup-win32-ia32-msvc": "4.42.0", "@rollup/rollup-win32-x64-msvc": "4.42.0", "fsevents": "2.3.3" }, "bin": { "rollup": "dist/bin/rollup" } }, "sha512-LW+Vse3BJPyGJGAJt1j8pWDKPd73QM8cRXYK1IxOBgL2AGLu7Xd2YOW0M2sLUBCkF5MshXXtMApyEAEzMVMsnw=="],
510
573
 
574
+ "rollup-plugin-esbuild": ["rollup-plugin-esbuild@6.2.1", "", { "dependencies": { "debug": "^4.4.0", "es-module-lexer": "^1.6.0", "get-tsconfig": "^4.10.0", "unplugin-utils": "^0.2.4" }, "peerDependencies": { "esbuild": ">=0.18.0", "rollup": "^1.20.0 || ^2.0.0 || ^3.0.0 || ^4.0.0" } }, "sha512-jTNOMGoMRhs0JuueJrJqbW8tOwxumaWYq+V5i+PD+8ecSCVkuX27tGW7BXqDgoULQ55rO7IdNxPcnsWtshz3AA=="],
575
+
511
576
  "rollup-plugin-inject-process-env": ["rollup-plugin-inject-process-env@1.3.1", "", { "dependencies": { "magic-string": "0.25.9" } }, "sha512-kKDoL30IZr0wxbNVJjq+OS92RJSKRbKV6B5eNW4q3mZTFqoWDh6lHy+mPDYuuGuERFNKXkG+AKxvYqC9+DRpKQ=="],
512
577
 
513
578
  "rollup-plugin-polyfill-node": ["rollup-plugin-polyfill-node@0.13.0", "", { "dependencies": { "@rollup/plugin-inject": "5.0.5" }, "peerDependencies": { "rollup": "4.42.0" } }, "sha512-FYEvpCaD5jGtyBuBFcQImEGmTxDTPbiHjJdrYIp+mFIwgXiXabxvKUK7ZT9P31ozu2Tqm9llYQMRWsfvTMTAOw=="],
@@ -568,6 +633,8 @@
568
633
 
569
634
  "unicode-property-aliases-ecmascript": ["unicode-property-aliases-ecmascript@2.1.0", "", {}, "sha512-6t3foTQI9qne+OZoVQB/8x8rk2k1eVy1gRXhV3oFQ5T6R1dqQ1xtin3XqSlx3+ATBkliTaR/hHyJBm+LVPNM8w=="],
570
635
 
636
+ "unplugin-utils": ["unplugin-utils@0.2.5", "", { "dependencies": { "pathe": "^2.0.3", "picomatch": "^4.0.3" } }, "sha512-gwXJnPRewT4rT7sBi/IvxKTjsms7jX7QIDLOClApuZwR49SXbrB1z2NLUZ+vDHyqCj/n58OzRRqaW+B8OZi8vg=="],
637
+
571
638
  "update-browserslist-db": ["update-browserslist-db@1.1.3", "", { "dependencies": { "escalade": "3.2.0", "picocolors": "1.1.1" }, "peerDependencies": { "browserslist": "4.25.0" }, "bin": { "update-browserslist-db": "cli.js" } }, "sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw=="],
572
639
 
573
640
  "which": ["which@2.0.2", "", { "dependencies": { "isexe": "2.0.0" }, "bin": { "node-which": "./bin/node-which" } }, "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA=="],
@@ -596,6 +663,8 @@
596
663
 
597
664
  "strip-ansi-cjs/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="],
598
665
 
666
+ "unplugin-utils/picomatch": ["picomatch@4.0.3", "", {}, "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q=="],
667
+
599
668
  "wrap-ansi-cjs/ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="],
600
669
 
601
670
  "wrap-ansi-cjs/string-width": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "8.0.0", "is-fullwidth-code-point": "3.0.0", "strip-ansi": "6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="],
package/dist/index.js CHANGED
@@ -11,6 +11,7 @@ import resolve, { nodeResolve } from '@rollup/plugin-node-resolve';
11
11
  import replace from '@rollup/plugin-replace';
12
12
  import terser from '@rollup/plugin-terser';
13
13
  import typescript from '@rollup/plugin-typescript';
14
+ import esbuild from 'rollup-plugin-esbuild';
14
15
  import url from '@rollup/plugin-url';
15
16
  import nodePolyfills from 'rollup-plugin-polyfill-node';
16
17
  import { watch, rollup } from 'rollup';
@@ -275,6 +276,7 @@ function constSysfsExpr(options = {}) {
275
276
  return null;
276
277
  const magicString = new MagicString(code);
277
278
  let hasReplaced = false;
279
+ let constSysfsImport = null;
278
280
  try {
279
281
  const stringVariables = new Map();
280
282
  const ast = parser.parse(code, {
@@ -289,6 +291,25 @@ function constSysfsExpr(options = {}) {
289
291
  stringVariables.set(id.name, init.value);
290
292
  }
291
293
  },
294
+ ImportDeclaration(nodePath) {
295
+ const decl = nodePath.node;
296
+ const specifiers = decl.specifiers;
297
+ const idx = specifiers.findIndex((s) => s.type === 'ImportSpecifier' && (s.imported?.name === 'constSysfsExpr' || s.local?.name === 'constSysfsExpr'));
298
+ if (idx !== -1 && typeof decl.start === 'number' && typeof decl.end === 'number') {
299
+ const spec = specifiers[idx];
300
+ if (typeof spec.start === 'number' && typeof spec.end === 'number') {
301
+ constSysfsImport = {
302
+ specifierStart: spec.start,
303
+ specifierEnd: spec.end,
304
+ declStart: decl.start,
305
+ declEnd: decl.end,
306
+ isOnlySpecifier: specifiers.length === 1,
307
+ prevSpecifierEnd: idx > 0 && typeof specifiers[idx - 1].end === 'number' ? specifiers[idx - 1].end : null,
308
+ nextSpecifierStart: idx < specifiers.length - 1 && typeof specifiers[idx + 1].start === 'number' ? specifiers[idx + 1].start : null,
309
+ };
310
+ }
311
+ }
312
+ },
292
313
  });
293
314
  traverse(ast, {
294
315
  CallExpression: (nodePath) => {
@@ -427,7 +448,7 @@ function constSysfsExpr(options = {}) {
427
448
  this.addWatchFile(singleFilePath);
428
449
  }
429
450
  catch (fileError) {
430
- let message = String(fileError instanceof Error ? fileError.message : fileError ?? 'Unknown file read error');
451
+ let message = String(fileError instanceof Error ? fileError.message : (fileError ?? 'Unknown file read error'));
431
452
  this.error(`Error reading file ${singleFilePath}: ${message}`, node.loc?.start.index);
432
453
  return;
433
454
  }
@@ -451,7 +472,7 @@ function constSysfsExpr(options = {}) {
451
472
  this.addWatchFile(fullPath);
452
473
  }
453
474
  catch (fileError) {
454
- let message = String(fileError instanceof Error ? fileError.message : fileError ?? 'Unknown file read error');
475
+ let message = String(fileError instanceof Error ? fileError.message : (fileError ?? 'Unknown file read error'));
455
476
  this.warn(`Error reading file ${fullPath}: ${message}`);
456
477
  }
457
478
  }
@@ -463,7 +484,7 @@ function constSysfsExpr(options = {}) {
463
484
  count++;
464
485
  }
465
486
  catch (error) {
466
- const message = String(error instanceof Error ? error.message : error ?? 'Unknown error during file processing');
487
+ const message = String(error instanceof Error ? error.message : (error ?? 'Unknown error during file processing'));
467
488
  this.error(`Could not process files for constSysfsExpr: ${message}`, node.loc?.start.index);
468
489
  return;
469
490
  }
@@ -472,10 +493,27 @@ function constSysfsExpr(options = {}) {
472
493
  });
473
494
  }
474
495
  catch (error) {
475
- const message = String(error instanceof Error ? error.message : error ?? 'Unknown parsing error');
496
+ const message = String(error instanceof Error ? error.message : (error ?? 'Unknown parsing error'));
476
497
  this.error(`Failed to parse ${id}: ${message}`);
477
498
  return null;
478
499
  }
500
+ if (constSysfsImport !== null && hasReplaced) {
501
+ const info = constSysfsImport;
502
+ if (info.isOnlySpecifier) {
503
+ let endPos = info.declEnd;
504
+ if (code[endPos] === '\n')
505
+ endPos++;
506
+ else if (code[endPos] === '\r' && code[endPos + 1] === '\n')
507
+ endPos += 2;
508
+ magicString.remove(info.declStart, endPos);
509
+ }
510
+ else if (info.nextSpecifierStart !== null) {
511
+ magicString.remove(info.specifierStart, info.nextSpecifierStart);
512
+ }
513
+ else if (info.prevSpecifierEnd !== null) {
514
+ magicString.remove(info.prevSpecifierEnd, info.specifierEnd);
515
+ }
516
+ }
479
517
  // If no replacements were made, return null
480
518
  if (!hasReplaced) {
481
519
  return null;
@@ -567,6 +605,148 @@ function stripPluginPrefix(message) {
567
605
  }
568
606
  class BuildFailedError extends Error {
569
607
  }
608
+ /**
609
+ * tsconfig.json files use JSONC, not regular JSON.
610
+ * JSONC supports comments and trailing commas, while JSON does not.
611
+ * This function sanitizes JSONC into JSON.parse()-able content.
612
+ *
613
+ * @param text input text
614
+ * @returns object
615
+ */
616
+ function parseJsonc(text) {
617
+ let out = '';
618
+ let i = 0;
619
+ const n = text.length;
620
+ while (i < n) {
621
+ const ch = text[i];
622
+ if (ch === '"') {
623
+ out += ch;
624
+ i++;
625
+ while (i < n) {
626
+ const c = text[i];
627
+ out += c;
628
+ if (c === '\\') {
629
+ i++;
630
+ if (i < n) {
631
+ out += text[i];
632
+ i++;
633
+ }
634
+ }
635
+ else if (c === '"') {
636
+ i++;
637
+ break;
638
+ }
639
+ else
640
+ i++;
641
+ }
642
+ }
643
+ else if (ch === '/' && i + 1 < n && text[i + 1] === '/') {
644
+ i += 2;
645
+ while (i < n && text[i] !== '\n')
646
+ i++;
647
+ }
648
+ else if (ch === '/' && i + 1 < n && text[i + 1] === '*') {
649
+ i += 2;
650
+ while (i < n - 1 && !(text[i] === '*' && text[i + 1] === '/'))
651
+ i++;
652
+ i += 2;
653
+ }
654
+ else if (ch === ',') {
655
+ let j = i + 1;
656
+ while (j < n && (text[j] === ' ' || text[j] === '\t' || text[j] === '\n' || text[j] === '\r'))
657
+ j++;
658
+ if (j < n && (text[j] === '}' || text[j] === ']')) {
659
+ i++;
660
+ }
661
+ else {
662
+ out += ch;
663
+ i++;
664
+ }
665
+ }
666
+ else {
667
+ out += ch;
668
+ i++;
669
+ }
670
+ }
671
+ return JSON.parse(out);
672
+ }
673
+ function tsconfigPathsPlugin(tsconfigPath) {
674
+ function readConfig(cfgPath) {
675
+ const dir = path.dirname(path.resolve(cfgPath));
676
+ let raw;
677
+ try {
678
+ raw = parseJsonc(fs.readFileSync(cfgPath, 'utf8'));
679
+ }
680
+ catch {
681
+ return { baseUrl: null, entries: [] };
682
+ }
683
+ let parentResult = { baseUrl: null, entries: [] };
684
+ if (raw.extends) {
685
+ const ext = raw.extends;
686
+ const parentPath = path.resolve(dir, ext.endsWith('.json') ? ext : `${ext}.json`);
687
+ parentResult = readConfig(parentPath);
688
+ }
689
+ const opts = raw.compilerOptions ?? {};
690
+ const baseUrl = opts.baseUrl ? path.resolve(dir, opts.baseUrl) : parentResult.baseUrl;
691
+ const ownEntries = Object.entries(opts.paths ?? {}).map(([pattern, targets]) => ({
692
+ pattern,
693
+ targets: targets,
694
+ configDir: dir,
695
+ }));
696
+ const ownPatterns = new Set(ownEntries.map((e) => e.pattern));
697
+ const parentEntries = parentResult.entries.filter((e) => !ownPatterns.has(e.pattern));
698
+ return { baseUrl, entries: [...ownEntries, ...parentEntries] };
699
+ }
700
+ const { baseUrl, entries } = readConfig(tsconfigPath);
701
+ function resolveWithExtensions(base) {
702
+ for (const ext of ['', '.ts', '.tsx', '.js', '.jsx', '/index.ts', '/index.tsx']) {
703
+ if (fs.existsSync(base + ext))
704
+ return base + ext;
705
+ }
706
+ return null;
707
+ }
708
+ return {
709
+ name: 'tsconfig-paths',
710
+ async resolveId(source, importer) {
711
+ for (const { pattern, targets, configDir } of entries) {
712
+ if (!targets.length)
713
+ continue;
714
+ const isWild = pattern.endsWith('/*');
715
+ if (isWild) {
716
+ const prefix = pattern.slice(0, -2);
717
+ if (source === prefix || source.startsWith(prefix + '/')) {
718
+ const rest = source.startsWith(prefix + '/') ? source.slice(prefix.length + 1) : '';
719
+ const targetBase = path.resolve(configDir, targets[0].replace('*', rest));
720
+ const resolved = resolveWithExtensions(targetBase);
721
+ if (resolved) {
722
+ const result = await this.resolve(resolved, importer, { skipSelf: true });
723
+ if (result)
724
+ return result;
725
+ }
726
+ }
727
+ }
728
+ else if (source === pattern) {
729
+ const targetBase = path.resolve(configDir, targets[0]);
730
+ const resolved = resolveWithExtensions(targetBase);
731
+ if (resolved) {
732
+ const result = await this.resolve(resolved, importer, { skipSelf: true });
733
+ if (result)
734
+ return result;
735
+ }
736
+ }
737
+ }
738
+ if (baseUrl && !source.startsWith('.') && !source.startsWith('/') && !source.startsWith('\0') && !source.startsWith('@')) {
739
+ const resolved = resolveWithExtensions(path.resolve(baseUrl, source));
740
+ if (resolved) {
741
+ const result = await this.resolve(resolved, importer, { skipSelf: true });
742
+ if (result)
743
+ return result;
744
+ }
745
+ }
746
+ return null;
747
+ },
748
+ };
749
+ }
570
750
  class MillenniumBuild {
571
751
  isExternal(id) {
572
752
  const hint = this.forbidden.get(id);
@@ -629,8 +809,12 @@ class FrontendBuild extends MillenniumBuild {
629
809
  this.forbidden = new Map([['@steambrew/webkit', 'use @steambrew/client in the frontend module']]);
630
810
  }
631
811
  plugins(sysfsPlugin) {
632
- const tsPlugin = typescript({ tsconfig: resolveTsConfig(this.frontendDir), compilerOptions: { noCheck: !this.props.minify, outDir: undefined } });
812
+ const tsconfigPath = resolveTsConfig(this.frontendDir);
813
+ const tsPlugin = this.props.minify
814
+ ? typescript({ tsconfig: tsconfigPath, compilerOptions: { outDir: undefined } })
815
+ : esbuild({ tsconfig: tsconfigPath, target: 'esnext', jsx: 'automatic' });
633
816
  return [
817
+ ...(this.props.minify ? [] : [tsconfigPathsPlugin(tsconfigPath)]),
634
818
  tsPlugin,
635
819
  url({ include: ['**/*.gif', '**/*.webm', '**/*.svg'], limit: 0, fileName: '[hash][extname]' }),
636
820
  insertMillennium(BuildTarget.Plugin, this.props),
@@ -678,8 +862,10 @@ class WebkitBuild extends MillenniumBuild {
678
862
  this.forbidden = new Map([['@steambrew/client', 'use @steambrew/webkit in the webkit module']]);
679
863
  }
680
864
  async plugins(sysfsPlugin) {
681
- const tsPlugin = typescript({ tsconfig: './webkit/tsconfig.json', compilerOptions: { noCheck: !this.props.minify } });
865
+ const webkitTsconfig = './webkit/tsconfig.json';
866
+ const tsPlugin = this.props.minify ? typescript({ tsconfig: webkitTsconfig }) : esbuild({ tsconfig: webkitTsconfig, target: 'esnext', jsx: 'automatic' });
682
867
  const base = [
868
+ ...(this.props.minify ? [] : [tsconfigPathsPlugin(webkitTsconfig)]),
683
869
  insertMillennium(BuildTarget.Webkit, this.props),
684
870
  tsPlugin,
685
871
  url({ include: ['**/*.mp4', '**/*.webm', '**/*.ogg'], limit: 0, fileName: '[name][extname]', destDir: 'dist/assets' }),
@@ -695,7 +881,7 @@ class WebkitBuild extends MillenniumBuild {
695
881
  'webkit.Millennium.exposeObj(': 'webkit.Millennium.exposeObj(exports, ',
696
882
  'client.BindPluginSettings()': 'client.BindPluginSettings(pluginName)',
697
883
  }),
698
- babel({ presets: ['@babel/preset-env', '@babel/preset-react'], babelHelpers: 'bundled' }),
884
+ ...(this.props.minify ? [babel({ presets: ['@babel/preset-env', '@babel/preset-react'], babelHelpers: 'bundled' })] : []),
699
885
  ...(Object.keys(env).length > 0 ? [injectProcessEnv(env)] : []),
700
886
  ];
701
887
  const merged = await withUserPlugins(base);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@steambrew/ttc",
3
- "version": "3.1.1",
3
+ "version": "3.2.2",
4
4
  "type": "module",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.js",
@@ -40,6 +40,7 @@
40
40
  "glob": "^11.0.2",
41
41
  "magic-string": "^0.30.17",
42
42
  "rollup": "^4.42.0",
43
+ "rollup-plugin-esbuild": "^6.0.0",
43
44
  "rollup-plugin-inject-process-env": "^1.3.1",
44
45
  "rollup-plugin-polyfill-node": "^0.13.0",
45
46
  "rollup-plugin-scss": "^4.0.1",
@@ -33,6 +33,16 @@ interface FileInfo {
33
33
  fileName: string;
34
34
  }
35
35
 
36
+ interface ImportSpecifierInfo {
37
+ specifierStart: number;
38
+ specifierEnd: number;
39
+ declStart: number;
40
+ declEnd: number;
41
+ isOnlySpecifier: boolean;
42
+ prevSpecifierEnd: number | null;
43
+ nextSpecifierStart: number | null;
44
+ }
45
+
36
46
  export default function constSysfsExpr(options: EmbedPluginOptions = {}): SysfsPlugin {
37
47
  const filter = createFilter(options.include, options.exclude);
38
48
  const pluginName = 'millennium-const-sysfs-expr';
@@ -47,6 +57,7 @@ export default function constSysfsExpr(options: EmbedPluginOptions = {}): SysfsP
47
57
 
48
58
  const magicString = new MagicString(code);
49
59
  let hasReplaced = false;
60
+ let constSysfsImport: ImportSpecifierInfo | null = null;
50
61
 
51
62
  try {
52
63
  const stringVariables = new Map<string, string>();
@@ -64,6 +75,28 @@ export default function constSysfsExpr(options: EmbedPluginOptions = {}): SysfsP
64
75
  stringVariables.set(id.name, init.value);
65
76
  }
66
77
  },
78
+ ImportDeclaration(nodePath) {
79
+ const decl = nodePath.node;
80
+ const specifiers = decl.specifiers;
81
+ const idx = specifiers.findIndex(
82
+ (s) => s.type === 'ImportSpecifier' && ((s as any).imported?.name === 'constSysfsExpr' || (s as any).local?.name === 'constSysfsExpr'),
83
+ );
84
+ if (idx !== -1 && typeof decl.start === 'number' && typeof decl.end === 'number') {
85
+ const spec = specifiers[idx];
86
+ if (typeof spec.start === 'number' && typeof spec.end === 'number') {
87
+ constSysfsImport = {
88
+ specifierStart: spec.start,
89
+ specifierEnd: spec.end,
90
+ declStart: decl.start,
91
+ declEnd: decl.end,
92
+ isOnlySpecifier: specifiers.length === 1,
93
+ prevSpecifierEnd: idx > 0 && typeof specifiers[idx - 1].end === 'number' ? (specifiers[idx - 1].end as number) : null,
94
+ nextSpecifierStart:
95
+ idx < specifiers.length - 1 && typeof specifiers[idx + 1].start === 'number' ? (specifiers[idx + 1].start as number) : null,
96
+ };
97
+ }
98
+ }
99
+ },
67
100
  });
68
101
 
69
102
  traverse(ast, {
@@ -177,14 +210,13 @@ export default function constSysfsExpr(options: EmbedPluginOptions = {}): SysfsP
177
210
  }
178
211
 
179
212
  try {
180
-
181
213
  const searchBasePath = callOptions.basePath
182
214
  ? path.isAbsolute(callOptions.basePath)
183
215
  ? callOptions.basePath
184
216
  : path.resolve(path.dirname(id), callOptions.basePath)
185
217
  : path.isAbsolute(pathOrPattern) && !/[?*+!@()[\]{}]/.test(pathOrPattern)
186
- ? path.dirname(pathOrPattern)
187
- : path.resolve(path.dirname(id), path.dirname(pathOrPattern));
218
+ ? path.dirname(pathOrPattern)
219
+ : path.resolve(path.dirname(id), path.dirname(pathOrPattern));
188
220
 
189
221
  let embeddedContent: string;
190
222
 
@@ -206,15 +238,13 @@ export default function constSysfsExpr(options: EmbedPluginOptions = {}): SysfsP
206
238
  fileName: path.relative(searchBasePath, singleFilePath),
207
239
  };
208
240
  embeddedContent = JSON.stringify(fileInfo);
209
- this.addWatchFile(singleFilePath);
210
- } catch (fileError: unknown) {
211
- let message = String(fileError instanceof Error ? fileError.message : fileError ?? 'Unknown file read error');
241
+ this.addWatchFile(singleFilePath);
242
+ } catch (fileError: unknown) {
243
+ let message = String(fileError instanceof Error ? fileError.message : (fileError ?? 'Unknown file read error'));
212
244
  this.error(`Error reading file ${singleFilePath}: ${message}`, node.loc?.start.index);
213
245
  return;
214
246
  }
215
247
  } else {
216
-
217
-
218
248
  const matchingFiles = glob.sync(pathOrPattern, {
219
249
  cwd: searchBasePath,
220
250
  nodir: true,
@@ -233,7 +263,7 @@ export default function constSysfsExpr(options: EmbedPluginOptions = {}): SysfsP
233
263
  });
234
264
  this.addWatchFile(fullPath);
235
265
  } catch (fileError: unknown) {
236
- let message = String(fileError instanceof Error ? fileError.message : fileError ?? 'Unknown file read error');
266
+ let message = String(fileError instanceof Error ? fileError.message : (fileError ?? 'Unknown file read error'));
237
267
  this.warn(`Error reading file ${fullPath}: ${message}`);
238
268
  }
239
269
  }
@@ -245,7 +275,7 @@ export default function constSysfsExpr(options: EmbedPluginOptions = {}): SysfsP
245
275
  hasReplaced = true;
246
276
  count++;
247
277
  } catch (error: unknown) {
248
- const message = String(error instanceof Error ? error.message : error ?? 'Unknown error during file processing');
278
+ const message = String(error instanceof Error ? error.message : (error ?? 'Unknown error during file processing'));
249
279
  this.error(`Could not process files for constSysfsExpr: ${message}`, node.loc?.start.index);
250
280
  return;
251
281
  }
@@ -253,11 +283,25 @@ export default function constSysfsExpr(options: EmbedPluginOptions = {}): SysfsP
253
283
  },
254
284
  });
255
285
  } catch (error: unknown) {
256
- const message = String(error instanceof Error ? error.message : error ?? 'Unknown parsing error');
286
+ const message = String(error instanceof Error ? error.message : (error ?? 'Unknown parsing error'));
257
287
  this.error(`Failed to parse ${id}: ${message}`);
258
288
  return null;
259
289
  }
260
290
 
291
+ if (constSysfsImport !== null && hasReplaced) {
292
+ const info = constSysfsImport as ImportSpecifierInfo;
293
+ if (info.isOnlySpecifier) {
294
+ let endPos = info.declEnd;
295
+ if (code[endPos] === '\n') endPos++;
296
+ else if (code[endPos] === '\r' && code[endPos + 1] === '\n') endPos += 2;
297
+ magicString.remove(info.declStart, endPos);
298
+ } else if (info.nextSpecifierStart !== null) {
299
+ magicString.remove(info.specifierStart, info.nextSpecifierStart);
300
+ } else if (info.prevSpecifierEnd !== null) {
301
+ magicString.remove(info.prevSpecifierEnd, info.specifierEnd);
302
+ }
303
+ }
304
+
261
305
  // If no replacements were made, return null
262
306
  if (!hasReplaced) {
263
307
  return null;
package/src/transpiler.ts CHANGED
@@ -5,6 +5,7 @@ import resolve, { nodeResolve } from '@rollup/plugin-node-resolve';
5
5
  import replace from '@rollup/plugin-replace';
6
6
  import terser from '@rollup/plugin-terser';
7
7
  import typescript from '@rollup/plugin-typescript';
8
+ import esbuild from 'rollup-plugin-esbuild';
8
9
  import url from '@rollup/plugin-url';
9
10
  import nodePolyfills from 'rollup-plugin-polyfill-node';
10
11
  import chalk from 'chalk';
@@ -136,6 +137,148 @@ function stripPluginPrefix(message: string): string {
136
137
 
137
138
  class BuildFailedError extends Error {}
138
139
 
140
+ interface PathEntry {
141
+ pattern: string;
142
+ targets: string[];
143
+ configDir: string;
144
+ }
145
+
146
+ /**
147
+ * tsconfig.json files use JSONC, not regular JSON.
148
+ * JSONC supports comments and trailing commas, while JSON does not.
149
+ * This function sanitizes JSONC into JSON.parse()-able content.
150
+ *
151
+ * @param text input text
152
+ * @returns object
153
+ */
154
+ function parseJsonc(text: string): any {
155
+ let out = '';
156
+ let i = 0;
157
+ const n = text.length;
158
+ while (i < n) {
159
+ const ch = text[i];
160
+ if (ch === '"') {
161
+ out += ch;
162
+ i++;
163
+ while (i < n) {
164
+ const c = text[i];
165
+ out += c;
166
+ if (c === '\\') {
167
+ i++;
168
+ if (i < n) {
169
+ out += text[i];
170
+ i++;
171
+ }
172
+ } else if (c === '"') {
173
+ i++;
174
+ break;
175
+ } else i++;
176
+ }
177
+ } else if (ch === '/' && i + 1 < n && text[i + 1] === '/') {
178
+ i += 2;
179
+ while (i < n && text[i] !== '\n') i++;
180
+ } else if (ch === '/' && i + 1 < n && text[i + 1] === '*') {
181
+ i += 2;
182
+ while (i < n - 1 && !(text[i] === '*' && text[i + 1] === '/')) i++;
183
+ i += 2;
184
+ } else if (ch === ',') {
185
+ let j = i + 1;
186
+ while (j < n && (text[j] === ' ' || text[j] === '\t' || text[j] === '\n' || text[j] === '\r')) j++;
187
+ if (j < n && (text[j] === '}' || text[j] === ']')) {
188
+ i++;
189
+ } else {
190
+ out += ch;
191
+ i++;
192
+ }
193
+ } else {
194
+ out += ch;
195
+ i++;
196
+ }
197
+ }
198
+ return JSON.parse(out);
199
+ }
200
+
201
+ function tsconfigPathsPlugin(tsconfigPath: string): InputPluginOption {
202
+ function readConfig(cfgPath: string): { baseUrl: string | null; entries: PathEntry[] } {
203
+ const dir = path.dirname(path.resolve(cfgPath));
204
+ let raw: any;
205
+ try {
206
+ raw = parseJsonc(fs.readFileSync(cfgPath, 'utf8'));
207
+ } catch {
208
+ return { baseUrl: null, entries: [] };
209
+ }
210
+
211
+ let parentResult: { baseUrl: string | null; entries: PathEntry[] } = { baseUrl: null, entries: [] };
212
+ if (raw.extends) {
213
+ const ext = raw.extends as string;
214
+ const parentPath = path.resolve(dir, ext.endsWith('.json') ? ext : `${ext}.json`);
215
+ parentResult = readConfig(parentPath);
216
+ }
217
+
218
+ const opts = raw.compilerOptions ?? {};
219
+ const baseUrl = opts.baseUrl ? path.resolve(dir, opts.baseUrl as string) : parentResult.baseUrl;
220
+
221
+ const ownEntries: PathEntry[] = Object.entries(opts.paths ?? {}).map(([pattern, targets]) => ({
222
+ pattern,
223
+ targets: targets as string[],
224
+ configDir: dir,
225
+ }));
226
+
227
+ const ownPatterns = new Set(ownEntries.map((e) => e.pattern));
228
+ const parentEntries = parentResult.entries.filter((e) => !ownPatterns.has(e.pattern));
229
+
230
+ return { baseUrl, entries: [...ownEntries, ...parentEntries] };
231
+ }
232
+
233
+ const { baseUrl, entries } = readConfig(tsconfigPath);
234
+
235
+ function resolveWithExtensions(base: string): string | null {
236
+ for (const ext of ['', '.ts', '.tsx', '.js', '.jsx', '/index.ts', '/index.tsx']) {
237
+ if (fs.existsSync(base + ext)) return base + ext;
238
+ }
239
+ return null;
240
+ }
241
+
242
+ return {
243
+ name: 'tsconfig-paths',
244
+ async resolveId(source: string, importer: string | undefined) {
245
+ for (const { pattern, targets, configDir } of entries) {
246
+ if (!targets.length) continue;
247
+ const isWild = pattern.endsWith('/*');
248
+ if (isWild) {
249
+ const prefix = pattern.slice(0, -2);
250
+ if (source === prefix || source.startsWith(prefix + '/')) {
251
+ const rest = source.startsWith(prefix + '/') ? source.slice(prefix.length + 1) : '';
252
+ const targetBase = path.resolve(configDir, targets[0].replace('*', rest));
253
+ const resolved = resolveWithExtensions(targetBase);
254
+ if (resolved) {
255
+ const result = await this.resolve(resolved, importer, { skipSelf: true });
256
+ if (result) return result;
257
+ }
258
+ }
259
+ } else if (source === pattern) {
260
+ const targetBase = path.resolve(configDir, targets[0]);
261
+ const resolved = resolveWithExtensions(targetBase);
262
+ if (resolved) {
263
+ const result = await this.resolve(resolved, importer, { skipSelf: true });
264
+ if (result) return result;
265
+ }
266
+ }
267
+ }
268
+
269
+ if (baseUrl && !source.startsWith('.') && !source.startsWith('/') && !source.startsWith('\0') && !source.startsWith('@')) {
270
+ const resolved = resolveWithExtensions(path.resolve(baseUrl, source));
271
+ if (resolved) {
272
+ const result = await this.resolve(resolved, importer, { skipSelf: true });
273
+ if (result) return result;
274
+ }
275
+ }
276
+
277
+ return null;
278
+ },
279
+ };
280
+ }
281
+
139
282
  abstract class MillenniumBuild {
140
283
  protected abstract readonly externals: ReadonlySet<string>;
141
284
  protected abstract readonly forbidden: ReadonlyMap<string, string>;
@@ -209,9 +352,13 @@ class FrontendBuild extends MillenniumBuild {
209
352
  }
210
353
 
211
354
  protected plugins(sysfsPlugin: InputPluginOption): InputPluginOption[] {
212
- const tsPlugin = typescript({ tsconfig: resolveTsConfig(this.frontendDir), compilerOptions: { noCheck: !this.props.minify, outDir: undefined } });
355
+ const tsconfigPath = resolveTsConfig(this.frontendDir);
356
+ const tsPlugin = this.props.minify
357
+ ? typescript({ tsconfig: tsconfigPath, compilerOptions: { outDir: undefined } })
358
+ : esbuild({ tsconfig: tsconfigPath, target: 'esnext', jsx: 'automatic' });
213
359
 
214
360
  return [
361
+ ...(this.props.minify ? [] : [tsconfigPathsPlugin(tsconfigPath)]),
215
362
  tsPlugin,
216
363
  url({ include: ['**/*.gif', '**/*.webm', '**/*.svg'], limit: 0, fileName: '[hash][extname]' }),
217
364
  insertMillennium(BuildTarget.Plugin, this.props),
@@ -262,9 +409,11 @@ class WebkitBuild extends MillenniumBuild {
262
409
  }
263
410
 
264
411
  protected async plugins(sysfsPlugin: InputPluginOption): Promise<InputPluginOption[]> {
265
- const tsPlugin = typescript({ tsconfig: './webkit/tsconfig.json', compilerOptions: { noCheck: !this.props.minify } });
412
+ const webkitTsconfig = './webkit/tsconfig.json';
413
+ const tsPlugin = this.props.minify ? typescript({ tsconfig: webkitTsconfig }) : esbuild({ tsconfig: webkitTsconfig, target: 'esnext', jsx: 'automatic' });
266
414
 
267
415
  const base: InputPluginOption[] = [
416
+ ...(this.props.minify ? [] : [tsconfigPathsPlugin(webkitTsconfig)]),
268
417
  insertMillennium(BuildTarget.Webkit, this.props),
269
418
  tsPlugin,
270
419
  url({ include: ['**/*.mp4', '**/*.webm', '**/*.ogg'], limit: 0, fileName: '[name][extname]', destDir: 'dist/assets' }),
@@ -280,7 +429,7 @@ class WebkitBuild extends MillenniumBuild {
280
429
  'webkit.Millennium.exposeObj(': 'webkit.Millennium.exposeObj(exports, ',
281
430
  'client.BindPluginSettings()': 'client.BindPluginSettings(pluginName)',
282
431
  }),
283
- babel({ presets: ['@babel/preset-env', '@babel/preset-react'], babelHelpers: 'bundled' }),
432
+ ...(this.props.minify ? [babel({ presets: ['@babel/preset-env', '@babel/preset-react'], babelHelpers: 'bundled' })] : []),
284
433
  ...(Object.keys(env).length > 0 ? [injectProcessEnv(env)] : []),
285
434
  ];
286
435