@rstest/core 0.9.1 → 0.9.3

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 (54) hide show
  1. package/LICENSE.md +1 -1
  2. package/dist/{0~89.js → 0~8843.js} +24 -28
  3. package/dist/{0~1472.js → 0~browserLoader.js} +11 -11
  4. package/dist/{0~7882.js → 0~browser~1.js} +60 -61
  5. package/dist/{0~8426.js → 0~checkThresholds.js} +6 -6
  6. package/dist/{0~7583.js → 0~chokidar.js} +113 -72
  7. package/dist/{0~130.js → 0~console.js} +19 -20
  8. package/dist/{0~9744.js → 0~dist.js} +57 -57
  9. package/dist/{0~4403.js → 0~generate.js} +9 -6
  10. package/dist/{0~4809.js → 0~happyDom.js} +2 -2
  11. package/dist/{0~3346.js → 0~interop.js} +0 -1
  12. package/dist/{0~62.js → 0~jsdom.js} +2 -2
  13. package/dist/{0~262.js → 0~lib.js} +4 -1
  14. package/dist/{0~9634.js → 0~listTests.js} +15 -24
  15. package/dist/{0~6923.js → 0~loadEsModule.js} +7 -7
  16. package/dist/{0~5835.js → 0~loadModule.js} +11 -11
  17. package/dist/{0~6907.js → 0~magic-string.es.js} +2 -1
  18. package/dist/0~mergeReports.js +127 -0
  19. package/dist/{0~2255.js → 0~plugin.js} +2 -4
  20. package/dist/{0~6588.js → 0~restart.js} +8 -12
  21. package/dist/{0~2173.js → 0~runTests.js} +51 -60
  22. package/dist/{487.js → 1255.js} +22 -15
  23. package/dist/{6151.js → 1949.js} +41 -25
  24. package/dist/{6973.js → 255.js} +9 -10
  25. package/dist/{9131.js → 3145.js} +229 -479
  26. package/dist/{1157.js → 4411.js} +37 -37
  27. package/dist/{4484.js → 5040.js} +1 -2
  28. package/dist/{3160.js → 6830.js} +429 -106
  29. package/dist/7011.js +1 -1
  30. package/dist/{1294.js → 7552.js} +106 -83
  31. package/dist/{5734.js → 7704.js} +7 -6
  32. package/dist/browser-runtime/{2~907.js → 2~magic-string.es.js} +18 -11
  33. package/dist/browser-runtime/{389.js → 723.js} +178 -134
  34. package/dist/browser-runtime/{389.js.LICENSE.txt → 723.js.LICENSE.txt} +0 -22
  35. package/dist/browser-runtime/index.d.ts +40 -5
  36. package/dist/browser-runtime/index.js +1 -1
  37. package/dist/browser-runtime/rslib-runtime.js +11 -3
  38. package/dist/browser.d.ts +40 -5
  39. package/dist/browser.js +9 -7
  40. package/dist/globalSetupWorker.js +7 -14
  41. package/dist/index.d.ts +53 -6
  42. package/dist/index.js +2 -2
  43. package/dist/rslib-runtime.js +5 -8
  44. package/dist/worker.d.ts +30 -3
  45. package/dist/worker.js +20 -46
  46. package/package.json +19 -18
  47. package/dist/3160.js.LICENSE.txt +0 -21
  48. package/dist/4881.js +0 -2
  49. package/dist/6198.js +0 -2
  50. /package/dist/{0~7583.js.LICENSE.txt → 0~chokidar.js.LICENSE.txt} +0 -0
  51. /package/dist/{0~3062.js → 0~utils.js} +0 -0
  52. /package/dist/{6151.js.LICENSE.txt → 1949.js.LICENSE.txt} +0 -0
  53. /package/dist/{4597.js → 1983.js} +0 -0
  54. /package/dist/{1294.js.LICENSE.txt → 7552.js.LICENSE.txt} +0 -0
@@ -1,12 +1,35 @@
1
1
  import "node:module";
2
2
  import { __webpack_require__ } from "./rslib-runtime.js";
3
- import { basename, isTTY, dirname as pathe_M_eThtNZ_dirname, resolve as pathe_M_eThtNZ_resolve, node_process, relative, getAbsolutePath, join, bgColor, formatRootStr, determineAgent, logger as logger_logger, castArray, prettyTime, isDebug, color, isAbsolute, getTaskNameWithPrefix, normalize, formatError } from "./3160.js";
4
- import { isDynamicPattern, glob, DEFAULT_CONFIG_NAME, prettyTestPath, globalApis, promises, TEMP_RSTEST_OUTPUT_DIR_GLOB, formatTestPath, filterProjects, DEFAULT_CONFIG_EXTENSIONS, TS_CONFIG_FILE } from "./1157.js";
5
- import { rsbuild as __rspack_external__rsbuild_core_1b356efc } from "./4484.js";
3
+ import node_fs, { existsSync, mkdirSync, readFileSync, statSync, writeFileSync } from "node:fs";
4
+ import { loadConfig, mergeRsbuildConfig } from "@rsbuild/core";
5
+ import { stripVTControlCharacters } from "node:util";
6
+ import promises from "node:fs/promises";
7
+ import node_path, { dirname as external_node_path_dirname, resolve as external_node_path_resolve } from "node:path";
8
+ import { createRequire } from "node:module";
9
+ import node_process from "node:process";
10
+ import { basename, isTTY, dirname as pathe_M_eThtNZ_dirname, resolve as pathe_M_eThtNZ_resolve, relative, getAbsolutePath, join, bgColor, formatRootStr, determineAgent, logger as logger_logger, castArray, dist_m, prettyTime, isDebug, color as logger_color, isAbsolute, getTaskNameWithPrefix, normalize, formatError } from "./6830.js";
11
+ import { isDynamicPattern, glob, DEFAULT_CONFIG_NAME, prettyTestPath, globalApis, TEMP_RSTEST_OUTPUT_DIR_GLOB, formatTestPath, filterProjects, DEFAULT_CONFIG_EXTENSIONS, TS_CONFIG_FILE } from "./4411.js";
6
12
  import { posix } from "./7011.js";
7
13
  import { parse as stack_trace_parser_esm_parse } from "./1672.js";
8
14
  import { decode } from "./4397.js";
9
- import { createRequire } from "./4881.js";
15
+ import "./5040.js";
16
+ var init_namespaceObject = {};
17
+ __webpack_require__.r(init_namespaceObject);
18
+ __webpack_require__.d(init_namespaceObject, {
19
+ initCli: ()=>init_initCli
20
+ });
21
+ var src_core_namespaceObject = {};
22
+ __webpack_require__.r(src_core_namespaceObject);
23
+ __webpack_require__.d(src_core_namespaceObject, {
24
+ createRstest: ()=>core_createRstest
25
+ });
26
+ var error_namespaceObject = {};
27
+ __webpack_require__.r(error_namespaceObject);
28
+ __webpack_require__.d(error_namespaceObject, {
29
+ C: ()=>formatStack,
30
+ parseErrorStacktrace: ()=>error_parseErrorStacktrace,
31
+ printError: ()=>error_printError
32
+ });
10
33
  function toArr(any) {
11
34
  return null == any ? [] : Array.isArray(any) ? any : [
12
35
  any
@@ -564,7 +587,7 @@ function prepareCli() {
564
587
  if (!npm_execpath || npm_execpath.includes('npx-cli.js') || npm_execpath.includes('.bun')) logger_logger.log();
565
588
  }
566
589
  function showRstest() {
567
- logger_logger.greet(" Rstest v0.9.1");
590
+ logger_logger.greet(" Rstest v0.9.3");
568
591
  logger_logger.log('');
569
592
  }
570
593
  const applyCommonOptions = (cli)=>{
@@ -585,13 +608,9 @@ const runRest = async ({ options, filters, command })=>{
585
608
  handleUnexpectedExit(rstest, err);
586
609
  };
587
610
  try {
588
- const { initCli } = await Promise.resolve().then(()=>({
589
- initCli: init_initCli
590
- }));
611
+ const { initCli } = await Promise.resolve(init_namespaceObject);
591
612
  const { config, configFilePath, projects } = await initCli(options);
592
- const { createRstest } = await Promise.resolve().then(()=>({
593
- createRstest: core_createRstest
594
- }));
613
+ const { createRstest } = await Promise.resolve(src_core_namespaceObject);
595
614
  rstest = createRstest({
596
615
  config,
597
616
  configFilePath,
@@ -600,10 +619,7 @@ const runRest = async ({ options, filters, command })=>{
600
619
  process.on('uncaughtException', unexpectedlyExitHandler);
601
620
  process.on('unhandledRejection', unexpectedlyExitHandler);
602
621
  if ('watch' === command) {
603
- const { watchFilesForRestart, onBeforeRestart } = await import("./0~6588.js").then((mod)=>({
604
- watchFilesForRestart: mod.watchFilesForRestart,
605
- onBeforeRestart: mod.onBeforeRestart
606
- }));
622
+ const { watchFilesForRestart, onBeforeRestart } = await import("./0~restart.js");
607
623
  onBeforeRestart(()=>{
608
624
  process.off('uncaughtException', unexpectedlyExitHandler);
609
625
  process.off('unhandledRejection', unexpectedlyExitHandler);
@@ -622,7 +638,7 @@ const runRest = async ({ options, filters, command })=>{
622
638
  function setupCommands() {
623
639
  const cli = cac('rstest');
624
640
  cli.help();
625
- cli.version("0.9.1");
641
+ cli.version("0.9.3");
626
642
  applyCommonOptions(cli);
627
643
  cli.command('[...filters]', 'run tests').option('-w, --watch', 'Run tests in watch mode').action(async (filters, options)=>{
628
644
  if (!determineAgent().isAgent) showRstest();
@@ -655,14 +671,10 @@ function setupCommands() {
655
671
  });
656
672
  cli.command('list [...filters]', 'lists all test files that Rstest will run').option('--filesOnly', 'only list the test files').option('--json [boolean/path]', 'print tests as JSON or write to a file').option('--includeSuites', 'include suites in output').option('--printLocation', 'print test case location').action(async (filters, options)=>{
657
673
  try {
658
- const { initCli } = await Promise.resolve().then(()=>({
659
- initCli: init_initCli
660
- }));
674
+ const { initCli } = await Promise.resolve(init_namespaceObject);
661
675
  const { config, configFilePath, projects } = await initCli(options);
662
676
  if (options.printLocation) config.includeTaskLocation = true;
663
- const { createRstest } = await Promise.resolve().then(()=>({
664
- createRstest: core_createRstest
665
- }));
677
+ const { createRstest } = await Promise.resolve(src_core_namespaceObject);
666
678
  const rstest = createRstest({
667
679
  config,
668
680
  configFilePath,
@@ -680,14 +692,32 @@ function setupCommands() {
680
692
  process.exit(1);
681
693
  }
682
694
  });
695
+ cli.command('merge-reports [path]', 'Merge blob reports from multiple shards into a unified report').option('--cleanup', 'Remove blob reports directory after merging').action(async (path, options)=>{
696
+ if (!determineAgent().isAgent) showRstest();
697
+ try {
698
+ const { initCli } = await Promise.resolve(init_namespaceObject);
699
+ const { config, configFilePath, projects } = await initCli(options);
700
+ const { createRstest } = await Promise.resolve(src_core_namespaceObject);
701
+ const rstest = createRstest({
702
+ config,
703
+ configFilePath,
704
+ projects
705
+ }, 'merge-reports', []);
706
+ await rstest.mergeReports({
707
+ path,
708
+ cleanup: options.cleanup
709
+ });
710
+ } catch (err) {
711
+ logger_logger.error('Failed to merge reports.');
712
+ logger_logger.error(formatError(err));
713
+ process.exit(1);
714
+ }
715
+ });
683
716
  cli.command('init [project]', 'Initialize rstest configuration').option('--yes', 'Use default options (non-interactive)').action(async (project, options)=>{
684
717
  try {
685
718
  let selectedProject = project;
686
719
  if (!selectedProject) {
687
- const { select, isCancel } = await import("./0~9744.js").then((mod)=>({
688
- select: mod.Jt,
689
- isCancel: mod.Ct
690
- }));
720
+ const { select, isCancel } = await import("./0~dist.js");
691
721
  console.log();
692
722
  const selected = await select({
693
723
  message: 'What would you like to initialize?',
@@ -700,15 +730,13 @@ function setupCommands() {
700
730
  ]
701
731
  });
702
732
  if (isCancel(selected)) {
703
- console.log(color.yellow('Operation cancelled.'));
733
+ console.log(logger_color.yellow('Operation cancelled.'));
704
734
  process.exit(0);
705
735
  }
706
736
  selectedProject = selected;
707
737
  }
708
738
  if ('browser' === selectedProject) {
709
- const { create } = await import("./0~7882.js").then((mod)=>({
710
- create: mod.create
711
- }));
739
+ const { create } = await import("./0~browser~1.js");
712
740
  await create({
713
741
  yes: options.yes
714
742
  });
@@ -724,342 +752,18 @@ function setupCommands() {
724
752
  });
725
753
  cli.parse();
726
754
  }
727
- const dist_r = Object.create(null), dist_i = (e)=>globalThis.process?.env || {
728
- MODE: "production",
729
- DEV: false,
730
- PROD: true,
731
- BASE_URL: "/",
732
- ASSET_PREFIX: "auto"
733
- }, dist_o = new Proxy(dist_r, {
734
- get (e, s) {
735
- return dist_i()[s] ?? dist_r[s];
736
- },
737
- has (e, s) {
738
- const E = dist_i();
739
- return s in E || s in dist_r;
740
- },
741
- set (e, s, E) {
742
- const B = dist_i(!0);
743
- return B[s] = E, !0;
744
- },
745
- deleteProperty (e, s) {
746
- if (!s) return !1;
747
- const E = dist_i(!0);
748
- return delete E[s], !0;
749
- },
750
- ownKeys () {
751
- const e = dist_i(!0);
752
- return Object.keys(e);
753
- }
754
- }), dist_t = typeof process < "u" && process.env && process.env.NODE_ENV || "", f = [
755
- [
756
- "APPVEYOR"
757
- ],
758
- [
759
- "AWS_AMPLIFY",
760
- "AWS_APP_ID",
761
- {
762
- ci: !0
763
- }
764
- ],
765
- [
766
- "AZURE_PIPELINES",
767
- "SYSTEM_TEAMFOUNDATIONCOLLECTIONURI"
768
- ],
769
- [
770
- "AZURE_STATIC",
771
- "INPUT_AZURE_STATIC_WEB_APPS_API_TOKEN"
772
- ],
773
- [
774
- "APPCIRCLE",
775
- "AC_APPCIRCLE"
776
- ],
777
- [
778
- "BAMBOO",
779
- "bamboo_planKey"
780
- ],
781
- [
782
- "BITBUCKET",
783
- "BITBUCKET_COMMIT"
784
- ],
785
- [
786
- "BITRISE",
787
- "BITRISE_IO"
788
- ],
789
- [
790
- "BUDDY",
791
- "BUDDY_WORKSPACE_ID"
792
- ],
793
- [
794
- "BUILDKITE"
795
- ],
796
- [
797
- "CIRCLE",
798
- "CIRCLECI"
799
- ],
800
- [
801
- "CIRRUS",
802
- "CIRRUS_CI"
803
- ],
804
- [
805
- "CLOUDFLARE_PAGES",
806
- "CF_PAGES",
807
- {
808
- ci: !0
809
- }
810
- ],
811
- [
812
- "CLOUDFLARE_WORKERS",
813
- "WORKERS_CI",
814
- {
815
- ci: !0
816
- }
817
- ],
818
- [
819
- "CODEBUILD",
820
- "CODEBUILD_BUILD_ARN"
821
- ],
822
- [
823
- "CODEFRESH",
824
- "CF_BUILD_ID"
825
- ],
826
- [
827
- "DRONE"
828
- ],
829
- [
830
- "DRONE",
831
- "DRONE_BUILD_EVENT"
832
- ],
833
- [
834
- "DSARI"
835
- ],
836
- [
837
- "GITHUB_ACTIONS"
838
- ],
839
- [
840
- "GITLAB",
841
- "GITLAB_CI"
842
- ],
843
- [
844
- "GITLAB",
845
- "CI_MERGE_REQUEST_ID"
846
- ],
847
- [
848
- "GOCD",
849
- "GO_PIPELINE_LABEL"
850
- ],
851
- [
852
- "LAYERCI"
853
- ],
854
- [
855
- "HUDSON",
856
- "HUDSON_URL"
857
- ],
858
- [
859
- "JENKINS",
860
- "JENKINS_URL"
861
- ],
862
- [
863
- "MAGNUM"
864
- ],
865
- [
866
- "NETLIFY"
867
- ],
868
- [
869
- "NETLIFY",
870
- "NETLIFY_LOCAL",
871
- {
872
- ci: !1
873
- }
874
- ],
875
- [
876
- "NEVERCODE"
877
- ],
878
- [
879
- "RENDER"
880
- ],
881
- [
882
- "SAIL",
883
- "SAILCI"
884
- ],
885
- [
886
- "SEMAPHORE"
887
- ],
888
- [
889
- "SCREWDRIVER"
890
- ],
891
- [
892
- "SHIPPABLE"
893
- ],
894
- [
895
- "SOLANO",
896
- "TDDIUM"
897
- ],
898
- [
899
- "STRIDER"
900
- ],
901
- [
902
- "TEAMCITY",
903
- "TEAMCITY_VERSION"
904
- ],
905
- [
906
- "TRAVIS"
907
- ],
908
- [
909
- "VERCEL",
910
- "NOW_BUILDER"
911
- ],
912
- [
913
- "VERCEL",
914
- "VERCEL",
915
- {
916
- ci: !1
917
- }
918
- ],
919
- [
920
- "VERCEL",
921
- "VERCEL_ENV",
922
- {
923
- ci: !1
924
- }
925
- ],
926
- [
927
- "APPCENTER",
928
- "APPCENTER_BUILD_ID"
929
- ],
930
- [
931
- "CODESANDBOX",
932
- "CODESANDBOX_SSE",
933
- {
934
- ci: !1
935
- }
936
- ],
937
- [
938
- "CODESANDBOX",
939
- "CODESANDBOX_HOST",
940
- {
941
- ci: !1
942
- }
943
- ],
944
- [
945
- "STACKBLITZ"
946
- ],
947
- [
948
- "STORMKIT"
949
- ],
950
- [
951
- "CLEAVR"
952
- ],
953
- [
954
- "ZEABUR"
955
- ],
956
- [
957
- "CODESPHERE",
958
- "CODESPHERE_APP_ID",
959
- {
960
- ci: !0
961
- }
962
- ],
963
- [
964
- "RAILWAY",
965
- "RAILWAY_PROJECT_ID"
966
- ],
967
- [
968
- "RAILWAY",
969
- "RAILWAY_SERVICE_ID"
970
- ],
971
- [
972
- "DENO-DEPLOY",
973
- "DENO_DEPLOYMENT_ID"
974
- ],
975
- [
976
- "FIREBASE_APP_HOSTING",
977
- "FIREBASE_APP_HOSTING",
978
- {
979
- ci: !0
980
- }
981
- ]
982
- ];
983
- function dist_b() {
984
- if (globalThis.process?.env) for (const e of f){
985
- const s = e[1] || e[0];
986
- if (globalThis.process?.env[s]) return {
987
- name: e[0].toLowerCase(),
988
- ...e[2]
989
- };
990
- }
991
- return globalThis.process?.env?.SHELL === "/bin/jsh" && globalThis.process?.versions?.webcontainer ? {
992
- name: "stackblitz",
993
- ci: !1
994
- } : {
995
- name: "",
996
- ci: !1
997
- };
998
- }
999
- const l = dist_b();
1000
- l.name;
1001
- function n(e) {
1002
- return e ? "false" !== e : !1;
1003
- }
1004
- const I = globalThis.process?.platform || "", T = n(dist_o.CI) || !1 !== l.ci, R = n(globalThis.process?.stdout && globalThis.process?.stdout.isTTY), A = (n(dist_o.DEBUG), "test" === dist_t || n(dist_o.TEST), n(dist_o.MINIMAL), /^win/i.test(I)), C = (/^linux/i.test(I), /^darwin/i.test(I), !n(dist_o.NO_COLOR) && (n(dist_o.FORCE_COLOR) || (R || A) && dist_o.TERM), (globalThis.process?.versions?.node || "").replace(/^v/, "") || null), W = (Number(C?.split(".")[0]), globalThis.process || Object.create(null)), dist_ = {
1005
- versions: {}
1006
- }, O = (new Proxy(W, {
1007
- get (e, s) {
1008
- if ("env" === s) return dist_o;
1009
- if (s in e) return e[s];
1010
- if (s in dist_) return dist_[s];
1011
- }
1012
- }), globalThis.process?.release?.name === "node"), c = !!globalThis.Bun || !!globalThis.process?.versions?.bun, D = !!globalThis.Deno, L = !!globalThis.fastly, S = !!globalThis.Netlify, u = !!globalThis.EdgeRuntime, N = globalThis.navigator?.userAgent === "Cloudflare-Workers", F = [
1013
- [
1014
- S,
1015
- "netlify"
1016
- ],
1017
- [
1018
- u,
1019
- "edge-light"
1020
- ],
1021
- [
1022
- N,
1023
- "workerd"
1024
- ],
1025
- [
1026
- L,
1027
- "fastly"
1028
- ],
1029
- [
1030
- D,
1031
- "deno"
1032
- ],
1033
- [
1034
- c,
1035
- "bun"
1036
- ],
1037
- [
1038
- O,
1039
- "node"
1040
- ]
1041
- ];
1042
- function G() {
1043
- const e = F.find((s)=>s[0]);
1044
- if (e) return {
1045
- name: e[1]
1046
- };
1047
- }
1048
- const P = G();
1049
- P?.name;
1050
- const external_node_fs_ = __webpack_require__("node:fs");
1051
- const findConfig = (basePath)=>DEFAULT_CONFIG_EXTENSIONS.map((ext)=>basePath + ext).find(external_node_fs_["default"].existsSync);
755
+ const findConfig = (basePath)=>DEFAULT_CONFIG_EXTENSIONS.map((ext)=>basePath + ext).find(node_fs.existsSync);
1052
756
  const resolveConfigPath = (root, customConfig)=>{
1053
757
  if (customConfig) {
1054
758
  const customConfigPath = isAbsolute(customConfig) ? customConfig : join(root, customConfig);
1055
- if (external_node_fs_["default"].existsSync(customConfigPath)) return customConfigPath;
1056
- throw `Cannot find config file: ${color.dim(customConfigPath)}`;
759
+ if (node_fs.existsSync(customConfigPath)) return customConfigPath;
760
+ throw `Cannot find config file: ${logger_color.dim(customConfigPath)}`;
1057
761
  }
1058
762
  const configFilePath = findConfig(join(root, DEFAULT_CONFIG_NAME));
1059
763
  if (configFilePath) return configFilePath;
1060
764
  return null;
1061
765
  };
1062
- async function loadConfig({ cwd = process.cwd(), path, envMode, configLoader }) {
766
+ async function config_loadConfig({ cwd = process.cwd(), path, envMode, configLoader }) {
1063
767
  const configFilePath = resolveConfigPath(cwd, path);
1064
768
  if (!configFilePath) {
1065
769
  logger_logger.debug('no rstest config file found');
@@ -1068,28 +772,39 @@ async function loadConfig({ cwd = process.cwd(), path, envMode, configLoader })
1068
772
  filePath: configFilePath
1069
773
  };
1070
774
  }
1071
- const { content } = await (0, __rspack_external__rsbuild_core_1b356efc.loadConfig)({
775
+ const { content } = await loadConfig({
1072
776
  cwd: pathe_M_eThtNZ_dirname(configFilePath),
1073
777
  path: configFilePath,
1074
778
  envMode,
1075
779
  loader: configLoader
1076
780
  });
1077
781
  let config = content;
1078
- if (config.extends) {
1079
- const extendsConfig = 'function' == typeof config.extends ? await config.extends(Object.freeze({
1080
- ...config
1081
- })) : config.extends;
1082
- delete extendsConfig.projects;
1083
- config = mergeRstestConfig(extendsConfig, config);
1084
- }
782
+ config = await resolveExtends(config);
1085
783
  return {
1086
784
  content: config,
1087
785
  filePath: configFilePath
1088
786
  };
1089
787
  }
788
+ const resolveExtendEntry = async (entry, userConfig)=>{
789
+ const resolved = 'function' == typeof entry ? await entry(userConfig) : entry;
790
+ if ('projects' in resolved) {
791
+ const { projects: _projects, ...rest } = resolved;
792
+ return rest;
793
+ }
794
+ return resolved;
795
+ };
796
+ const resolveExtends = async (config)=>{
797
+ if (!config.extends) return config;
798
+ const userConfig = Object.freeze({
799
+ ...config
800
+ });
801
+ const extendsEntries = castArray(config.extends);
802
+ const resolvedExtends = await Promise.all(extendsEntries.map((entry)=>resolveExtendEntry(entry, userConfig)));
803
+ return mergeRstestConfig(...resolvedExtends, config);
804
+ };
1090
805
  const mergeProjectConfig = (...configs)=>mergeRstestConfig(...configs);
1091
806
  const mergeRstestConfig = (...configs)=>configs.reduce((result, config)=>{
1092
- const merged = (0, __rspack_external__rsbuild_core_1b356efc.mergeRsbuildConfig)(result, {
807
+ const merged = mergeRsbuildConfig(result, {
1093
808
  ...config,
1094
809
  exclude: Array.isArray(config.exclude) ? {
1095
810
  patterns: config.exclude,
@@ -1164,8 +879,9 @@ const createDefaultConfig = ()=>({
1164
879
  enabled: false,
1165
880
  provider: 'playwright',
1166
881
  browser: 'chromium',
1167
- headless: T,
1168
- strictPort: false
882
+ headless: dist_m,
883
+ strictPort: false,
884
+ providerOptions: {}
1169
885
  },
1170
886
  coverage: {
1171
887
  exclude: [
@@ -1189,7 +905,8 @@ const createDefaultConfig = ()=>({
1189
905
  ],
1190
906
  reportsDirectory: './coverage',
1191
907
  clean: true,
1192
- reportOnFailure: false
908
+ reportOnFailure: false,
909
+ allowExternal: false
1193
910
  }
1194
911
  });
1195
912
  const withDefaultConfig = (config)=>{
@@ -1209,10 +926,11 @@ const withDefaultConfig = (config)=>{
1209
926
  enabled: merged.browser?.enabled ?? false,
1210
927
  provider: merged.browser?.provider ?? 'playwright',
1211
928
  browser: merged.browser?.browser ?? 'chromium',
1212
- headless: merged.browser?.headless ?? T,
929
+ headless: merged.browser?.headless ?? dist_m,
1213
930
  port: merged.browser?.port,
1214
931
  strictPort: merged.browser?.strictPort ?? false,
1215
- viewport: merged.browser?.viewport
932
+ viewport: merged.browser?.viewport,
933
+ providerOptions: merged.browser?.providerOptions ?? {}
1216
934
  };
1217
935
  return {
1218
936
  ...merged,
@@ -1264,7 +982,11 @@ function mergeWithCLIOptions(config, options) {
1264
982
  if (void 0 !== options.bail && ('number' == typeof options.bail || 'boolean' == typeof options.bail)) config.bail = Number(options.bail);
1265
983
  if (void 0 !== options.coverage) {
1266
984
  config.coverage ??= {};
1267
- config.coverage.enabled = options.coverage;
985
+ if ('boolean' == typeof options.coverage) config.coverage.enabled = options.coverage;
986
+ else {
987
+ if (void 0 !== options.coverage.enabled) config.coverage.enabled = options.coverage.enabled;
988
+ if (void 0 !== options.coverage.allowExternal) config.coverage.allowExternal = options.coverage.allowExternal;
989
+ }
1268
990
  }
1269
991
  if (options.exclude) config.exclude = castArray(options.exclude);
1270
992
  if (options.include) config.include = castArray(options.include);
@@ -1307,7 +1029,7 @@ function mergeWithCLIOptions(config, options) {
1307
1029
  return config;
1308
1030
  }
1309
1031
  async function resolveConfig(options) {
1310
- const { content: config, filePath: configFilePath } = await loadConfig({
1032
+ const { content: config, filePath: configFilePath } = await config_loadConfig({
1311
1033
  cwd: options.cwd,
1312
1034
  path: options.config,
1313
1035
  configLoader: options.configLoader
@@ -1323,7 +1045,7 @@ async function resolveProjects({ config, root, options }) {
1323
1045
  if (!config.projects) return [];
1324
1046
  const getDefaultProjectName = (dir)=>{
1325
1047
  const pkgJsonPath = pathe_M_eThtNZ_resolve(dir, 'package.json');
1326
- const name = (0, external_node_fs_.existsSync)(pkgJsonPath) ? JSON.parse((0, external_node_fs_.readFileSync)(pkgJsonPath, 'utf-8')).name : '';
1048
+ const name = existsSync(pkgJsonPath) ? JSON.parse(readFileSync(pkgJsonPath, 'utf-8')).name : '';
1327
1049
  if ('string' != typeof name || !name) return basename(dir);
1328
1050
  return name;
1329
1051
  };
@@ -1349,16 +1071,9 @@ async function resolveProjects({ config, root, options }) {
1349
1071
  await Promise.all((rstestConfig.projects || []).map(async (p)=>{
1350
1072
  if ('object' == typeof p) {
1351
1073
  const projectRoot = p.root ? formatRootStr(p.root, root) : root;
1352
- let projectConfig = {
1074
+ const projectConfig = await resolveExtends({
1353
1075
  ...p
1354
- };
1355
- if (projectConfig.extends) {
1356
- const extendsConfig = 'function' == typeof projectConfig.extends ? await projectConfig.extends(Object.freeze({
1357
- ...projectConfig
1358
- })) : projectConfig.extends;
1359
- delete extendsConfig.projects;
1360
- projectConfig = mergeRstestConfig(extendsConfig, projectConfig);
1361
- }
1076
+ });
1362
1077
  projectConfigs.push({
1363
1078
  config: mergeWithCLIOptions({
1364
1079
  root: projectRoot,
@@ -1373,14 +1088,14 @@ async function resolveProjects({ config, root, options }) {
1373
1088
  if (isDynamicPattern(projectStr)) projectPatterns.push(projectStr);
1374
1089
  else {
1375
1090
  const absolutePath = getAbsolutePath(root, projectStr);
1376
- if (!(0, external_node_fs_.existsSync)(absolutePath)) throw `Can't resolve project "${p}", please make sure "${p}" is a existing file or a directory.`;
1091
+ if (!existsSync(absolutePath)) throw `Can't resolve project "${p}", please make sure "${p}" is a existing file or a directory.`;
1377
1092
  projectPaths.push(absolutePath);
1378
1093
  }
1379
1094
  }));
1380
1095
  projectPaths.push(...await globProjects(projectPatterns, root));
1381
1096
  const projects = [];
1382
1097
  await Promise.all(projectPaths.map(async (project)=>{
1383
- const isDirectory = (0, external_node_fs_.statSync)(project).isDirectory();
1098
+ const isDirectory = statSync(project).isDirectory();
1384
1099
  const projectRoot = isDirectory ? project : pathe_M_eThtNZ_dirname(project);
1385
1100
  const { config, configFilePath } = await resolveConfig({
1386
1101
  ...options,
@@ -1405,8 +1120,8 @@ async function resolveProjects({ config, root, options }) {
1405
1120
  const projects = await getProjects(config, root).then((p)=>filterProjects(p, options));
1406
1121
  if (!projects.length) {
1407
1122
  let errorMsg = `No projects found, please make sure you have at least one valid project.
1408
- ${color.gray('projects:')} ${JSON.stringify(config.projects, null, 2)}`;
1409
- if (options.project) errorMsg += `\n${color.gray('projectName filter:')} ${JSON.stringify(options.project, null, 2)}`;
1123
+ ${logger_color.gray('projects:')} ${JSON.stringify(config.projects, null, 2)}`;
1124
+ if (options.project) errorMsg += `\n${logger_color.gray('projectName filter:')} ${JSON.stringify(options.project, null, 2)}`;
1410
1125
  throw errorMsg;
1411
1126
  }
1412
1127
  const names = new Set();
@@ -1512,53 +1227,53 @@ function addSnapshotResult(summary, result) {
1512
1227
  summary.total += result.added + result.matched + result.unmatched + result.updated;
1513
1228
  }
1514
1229
  const getSummaryStatusString = (tasks, name = 'tests', showTotal = true)=>{
1515
- if (0 === tasks.length) return color.dim(`no ${name}`);
1230
+ if (0 === tasks.length) return logger_color.dim(`no ${name}`);
1516
1231
  const passed = tasks.filter((result)=>'pass' === result.status);
1517
1232
  const failed = tasks.filter((result)=>'fail' === result.status);
1518
1233
  const skipped = tasks.filter((result)=>'skip' === result.status);
1519
1234
  const todo = tasks.filter((result)=>'todo' === result.status);
1520
1235
  const status = [
1521
- failed.length ? color.bold(color.red(`${failed.length} failed`)) : null,
1522
- passed.length ? color.bold(color.green(`${passed.length} passed`)) : null,
1523
- skipped.length ? color.yellow(`${skipped.length} skipped`) : null,
1524
- todo.length ? color.gray(`${todo.length} todo`) : null
1236
+ failed.length ? logger_color.bold(logger_color.red(`${failed.length} failed`)) : null,
1237
+ passed.length ? logger_color.bold(logger_color.green(`${passed.length} passed`)) : null,
1238
+ skipped.length ? logger_color.yellow(`${skipped.length} skipped`) : null,
1239
+ todo.length ? logger_color.gray(`${todo.length} todo`) : null
1525
1240
  ].filter(Boolean);
1526
- return status.join(color.dim(' | ')) + (showTotal && status.length > 1 ? color.gray(` (${tasks.length})`) : '');
1241
+ return status.join(logger_color.dim(' | ')) + (showTotal && status.length > 1 ? logger_color.gray(` (${tasks.length})`) : '');
1527
1242
  };
1528
1243
  const printSnapshotSummaryLog = (snapshots, rootDir)=>{
1529
1244
  const summary = [];
1530
- if (snapshots.added) summary.push(color.bold(color.green(`${snapshots.added} written`)));
1531
- if (snapshots.unmatched) summary.push(color.bold(color.red(`${snapshots.unmatched} failed`)));
1532
- if (snapshots.updated) summary.push(color.bold(color.green(`${snapshots.updated} updated `)));
1533
- if (snapshots.filesRemoved) if (snapshots.didUpdate) summary.push(color.bold(color.green(`${snapshots.filesRemoved} files removed `)));
1534
- else summary.push(color.bold(color.yellow(`${snapshots.filesRemoved} files obsolete `)));
1245
+ if (snapshots.added) summary.push(logger_color.bold(logger_color.green(`${snapshots.added} written`)));
1246
+ if (snapshots.unmatched) summary.push(logger_color.bold(logger_color.red(`${snapshots.unmatched} failed`)));
1247
+ if (snapshots.updated) summary.push(logger_color.bold(logger_color.green(`${snapshots.updated} updated `)));
1248
+ if (snapshots.filesRemoved) if (snapshots.didUpdate) summary.push(logger_color.bold(logger_color.green(`${snapshots.filesRemoved} files removed `)));
1249
+ else summary.push(logger_color.bold(logger_color.yellow(`${snapshots.filesRemoved} files obsolete `)));
1535
1250
  if (snapshots.filesRemovedList?.length) {
1536
1251
  const [head, ...tail] = snapshots.filesRemovedList;
1537
- summary.push(`${color.gray("➜")} ${formatTestPath(rootDir, head)}`);
1252
+ summary.push(`${logger_color.gray("➜")} ${formatTestPath(rootDir, head)}`);
1538
1253
  for (const key of tail)summary.push(` ${formatTestPath(rootDir, key)}`);
1539
1254
  }
1540
1255
  if (snapshots.unchecked) {
1541
- if (snapshots.didUpdate) summary.push(color.bold(color.green(`${snapshots.unchecked} removed`)));
1542
- else summary.push(color.bold(color.yellow(`${snapshots.unchecked} obsolete`)));
1256
+ if (snapshots.didUpdate) summary.push(logger_color.bold(logger_color.green(`${snapshots.unchecked} removed`)));
1257
+ else summary.push(logger_color.bold(logger_color.yellow(`${snapshots.unchecked} obsolete`)));
1543
1258
  for (const uncheckedFile of snapshots.uncheckedKeysByFile){
1544
- summary.push(`${color.gray("➜")} ${formatTestPath(rootDir, uncheckedFile.filePath)}`);
1259
+ summary.push(`${logger_color.gray("➜")} ${formatTestPath(rootDir, uncheckedFile.filePath)}`);
1545
1260
  for (const key of uncheckedFile.keys)summary.push(` ${key}`);
1546
1261
  }
1547
1262
  }
1548
1263
  for (const [index, snapshot] of summary.entries()){
1549
1264
  const title = 0 === index ? 'Snapshots' : '';
1550
- logger_logger.log(`${color.gray(title.padStart(12))} ${snapshot}`);
1265
+ logger_logger.log(`${logger_color.gray(title.padStart(12))} ${snapshot}`);
1551
1266
  }
1552
1267
  };
1553
- const TestFileSummaryLabel = color.gray('Test Files'.padStart(11));
1554
- const TestSummaryLabel = color.gray('Tests'.padStart(11));
1555
- const DurationLabel = color.gray('Duration'.padStart(11));
1268
+ const TestFileSummaryLabel = logger_color.gray('Test Files'.padStart(11));
1269
+ const TestSummaryLabel = logger_color.gray('Tests'.padStart(11));
1270
+ const DurationLabel = logger_color.gray('Duration'.padStart(11));
1556
1271
  const printSummaryLog = ({ results, testResults, snapshotSummary, duration, rootPath })=>{
1557
1272
  logger_logger.log('');
1558
1273
  printSnapshotSummaryLog(snapshotSummary, rootPath);
1559
1274
  logger_logger.log(`${TestFileSummaryLabel} ${getSummaryStatusString(results)}`);
1560
1275
  logger_logger.log(`${TestSummaryLabel} ${getSummaryStatusString(testResults)}`);
1561
- logger_logger.log(`${DurationLabel} ${prettyTime(duration.totalTime)} ${color.gray(`(build ${prettyTime(duration.buildTime)}, tests ${prettyTime(duration.testTime)})`)}`);
1276
+ logger_logger.log(`${DurationLabel} ${prettyTime(duration.totalTime)} ${logger_color.gray(`(build ${prettyTime(duration.buildTime)}, tests ${prettyTime(duration.testTime)})`)}`);
1562
1277
  logger_logger.log('');
1563
1278
  };
1564
1279
  const printSummaryErrorLogs = async ({ testResults, results, rootPath, unhandledErrors, getSourcemap, filterRerunTestPaths })=>{
@@ -1568,11 +1283,9 @@ const printSummaryErrorLogs = async ({ testResults, results, rootPath, unhandled
1568
1283
  ];
1569
1284
  if (0 === failedTests.length && !unhandledErrors?.length) return;
1570
1285
  logger_logger.stderr('');
1571
- logger_logger.stderr(color.bold('Summary of all failing tests:'));
1286
+ logger_logger.stderr(logger_color.bold('Summary of all failing tests:'));
1572
1287
  logger_logger.stderr('');
1573
- const { printError } = await Promise.resolve().then(()=>({
1574
- printError: error_printError
1575
- }));
1288
+ const { printError } = await Promise.resolve(error_namespaceObject);
1576
1289
  for (const error of unhandledErrors || []){
1577
1290
  logger_logger.stderr(bgColor('bgRed', ' Unhandled Error '));
1578
1291
  await printError(error, getSourcemap, rootPath);
@@ -1580,16 +1293,13 @@ const printSummaryErrorLogs = async ({ testResults, results, rootPath, unhandled
1580
1293
  for (const test of failedTests){
1581
1294
  const relativePath = posix.relative(rootPath, test.testPath);
1582
1295
  const nameStr = getTaskNameWithPrefix(test);
1583
- logger_logger.stderr(`${bgColor('bgRed', ' FAIL ')} ${prettyTestPath(relativePath)} ${nameStr.length ? `${color.dim(">")} ${nameStr}` : ''}`);
1296
+ logger_logger.stderr(`${bgColor('bgRed', ' FAIL ')} ${prettyTestPath(relativePath)} ${nameStr.length ? `${logger_color.dim(">")} ${nameStr}` : ''}`);
1584
1297
  if (test.errors) {
1585
- const { printError } = await Promise.resolve().then(()=>({
1586
- printError: error_printError
1587
- }));
1298
+ const { printError } = await Promise.resolve(error_namespaceObject);
1588
1299
  for (const error of test.errors)await printError(error, getSourcemap, rootPath);
1589
1300
  }
1590
1301
  }
1591
1302
  };
1592
- const external_node_util_ = __webpack_require__("node:util");
1593
1303
  const DEFAULT_RENDER_INTERVAL_MS = 1000;
1594
1304
  const ESC = '\x1B[';
1595
1305
  const CLEAR_LINE = `${ESC}K`;
@@ -1707,7 +1417,7 @@ class WindowRenderer {
1707
1417
  function getRenderedRowCount(rows, columns) {
1708
1418
  let count = 0;
1709
1419
  for (const row of rows){
1710
- const text = (0, external_node_util_.stripVTControlCharacters)(row);
1420
+ const text = stripVTControlCharacters(row);
1711
1421
  count += Math.max(1, Math.ceil(text.length / columns));
1712
1422
  }
1713
1423
  return count;
@@ -1740,14 +1450,14 @@ class StatusRenderer {
1740
1450
  const relativePath = relative(this.rootPath, module);
1741
1451
  summary.push(`${bgColor('bgYellow', ' RUNS ')} ${prettyTestPath(relativePath)}`);
1742
1452
  if (runningTests.length && shouldDisplayRunningTests(runningTests)) {
1743
- let caseLog = ` ${color.gray("➜")} ${getTaskNameWithPrefix(runningTests[0])} ${color.magenta(prettyTime(now - runningTests[0].startTime))}`;
1744
- if (runningTests.length > 1) caseLog += color.gray(` and ${runningTests.length - 1} more cases`);
1453
+ let caseLog = ` ${logger_color.gray("➜")} ${getTaskNameWithPrefix(runningTests[0])} ${logger_color.magenta(prettyTime(now - runningTests[0].startTime))}`;
1454
+ if (runningTests.length > 1) caseLog += logger_color.gray(` and ${runningTests.length - 1} more cases`);
1745
1455
  summary.push(caseLog);
1746
1456
  }
1747
1457
  }
1748
1458
  summary.push('');
1749
1459
  if (0 === testModules.length) summary.push(`${TestFileSummaryLabel} ${runningModules.size} total`);
1750
- else summary.push(`${TestFileSummaryLabel} ${getSummaryStatusString(testModules, '', false)} ${color.dim('|')} ${runningModules.size + testModules.length} total`);
1460
+ else summary.push(`${TestFileSummaryLabel} ${getSummaryStatusString(testModules, '', false)} ${logger_color.dim('|')} ${runningModules.size + testModules.length} total`);
1751
1461
  const testResults = Array.from(runningModules.values()).flatMap(({ results })=>results).concat(testModules.flatMap((mod)=>mod.results));
1752
1462
  if (testResults.length) summary.push(`${TestSummaryLabel} ${getSummaryStatusString(testResults, '', false)}`);
1753
1463
  summary.push(`${DurationLabel} ${prettyTime(Date.now() - this.startTime)}`);
@@ -1775,10 +1485,10 @@ const statusStr = {
1775
1485
  skip: '-'
1776
1486
  };
1777
1487
  const statusColor = {
1778
- fail: color.red,
1779
- pass: color.green,
1780
- todo: color.gray,
1781
- skip: color.gray
1488
+ fail: logger_color.red,
1489
+ pass: logger_color.green,
1490
+ todo: logger_color.gray,
1491
+ skip: logger_color.gray
1782
1492
  };
1783
1493
  const statusColorfulStr = {
1784
1494
  fail: statusColor.fail(statusStr.fail),
@@ -1789,23 +1499,23 @@ const statusColorfulStr = {
1789
1499
  const logCase = (result, options)=>{
1790
1500
  const isSlowCase = (result.duration || 0) > options.slowTestThreshold;
1791
1501
  if (options.hideSkippedTests && 'skip' === result.status) return;
1792
- const icon = isSlowCase && 'pass' === result.status ? color.yellow(statusStr[result.status]) : statusColorfulStr[result.status];
1502
+ const icon = isSlowCase && 'pass' === result.status ? logger_color.yellow(statusStr[result.status]) : statusColorfulStr[result.status];
1793
1503
  const nameStr = getTaskNameWithPrefix(result);
1794
1504
  const duration = void 0 !== result.duration ? ` (${prettyTime(result.duration)})` : '';
1795
- const retry = result.retryCount ? color.yellow(` (retry x${result.retryCount})`) : '';
1796
- const heap = result.heap ? ` ${color.magenta(formatHeapUsed(result.heap))}` : '';
1797
- logger_logger.log(` ${icon} ${nameStr}${color.gray(duration)}${retry}${heap}`);
1798
- if (result.errors) for (const error of result.errors)logger_logger.log(color.red(` ${error.message}`));
1505
+ const retry = result.retryCount ? logger_color.yellow(` (retry x${result.retryCount})`) : '';
1506
+ const heap = result.heap ? ` ${logger_color.magenta(formatHeapUsed(result.heap))}` : '';
1507
+ logger_logger.log(` ${icon} ${nameStr}${logger_color.gray(duration)}${retry}${heap}`);
1508
+ if (result.errors) for (const error of result.errors)logger_logger.log(logger_color.red(` ${error.message}`));
1799
1509
  };
1800
1510
  const formatHeapUsed = (heap)=>`${Math.floor(heap / 1024 / 1024)} MB heap used`;
1801
1511
  const logFileTitle = (test, relativePath, alwaysShowTime = false, showProjectName = false)=>{
1802
- let title = ` ${color.bold(statusColorfulStr[test.status])}`;
1512
+ let title = ` ${logger_color.bold(statusColorfulStr[test.status])}`;
1803
1513
  if (showProjectName && test.project) title += ` ${statusColor[test.status](`[${test.project}]`)}`;
1804
1514
  title += ` ${prettyTestPath(relativePath)}`;
1805
- const formatDuration = (duration)=>color.green(prettyTime(duration));
1806
- title += ` ${color.gray(`(${test.results.length})`)}`;
1515
+ const formatDuration = (duration)=>logger_color.green(prettyTime(duration));
1516
+ title += ` ${logger_color.gray(`(${test.results.length})`)}`;
1807
1517
  if (alwaysShowTime) title += ` ${formatDuration(test.duration)}`;
1808
- if (test.heap) title += ` ${color.magenta(formatHeapUsed(test.heap))}`;
1518
+ if (test.heap) title += ` ${logger_color.magenta(formatHeapUsed(test.heap))}`;
1809
1519
  logger_logger.log(title);
1810
1520
  };
1811
1521
  class DefaultReporter {
@@ -1860,7 +1570,7 @@ class DefaultReporter {
1860
1570
  } else titles.push(testPath);
1861
1571
  const logOutput = 'stdout' === log.type ? logger_logger.log : logger_logger.stderr;
1862
1572
  logOutput('');
1863
- logOutput(`${log.name}${color.gray(color.dim(` | ${titles.join(color.gray(color.dim(' | ')))}`))}`);
1573
+ logOutput(`${log.name}${logger_color.gray(logger_color.dim(` | ${titles.join(logger_color.gray(logger_color.dim(' | ')))}`))}`);
1864
1574
  logOutput(log.content);
1865
1575
  logOutput('');
1866
1576
  }
@@ -1887,6 +1597,44 @@ class DefaultReporter {
1887
1597
  });
1888
1598
  }
1889
1599
  }
1600
+ const DEFAULT_OUTPUT_DIR = '.rstest-reports';
1601
+ class BlobReporter {
1602
+ config;
1603
+ outputDir;
1604
+ consoleLogs = [];
1605
+ constructor({ rootPath, config, options }){
1606
+ this.config = config;
1607
+ this.outputDir = options?.outputDir ? join(rootPath, options.outputDir) : join(rootPath, DEFAULT_OUTPUT_DIR);
1608
+ }
1609
+ onUserConsoleLog(log) {
1610
+ this.consoleLogs.push(log);
1611
+ }
1612
+ async onTestRunEnd({ results, testResults, duration, snapshotSummary, unhandledErrors }) {
1613
+ const shard = this.config.shard;
1614
+ const fileName = shard ? `blob-${shard.index}-${shard.count}.json` : 'blob.json';
1615
+ const blobData = {
1616
+ version: "0.9.3",
1617
+ shard: shard ? {
1618
+ index: shard.index,
1619
+ count: shard.count
1620
+ } : void 0,
1621
+ results,
1622
+ testResults,
1623
+ duration,
1624
+ snapshotSummary,
1625
+ unhandledErrors: unhandledErrors?.map((e)=>({
1626
+ message: e.message,
1627
+ stack: e.stack,
1628
+ name: e.name
1629
+ })),
1630
+ consoleLogs: this.consoleLogs.length > 0 ? this.consoleLogs : void 0
1631
+ };
1632
+ mkdirSync(this.outputDir, {
1633
+ recursive: true
1634
+ });
1635
+ writeFileSync(join(this.outputDir, fileName), JSON.stringify(blobData), 'utf-8');
1636
+ }
1637
+ }
1890
1638
  class GithubActionsReporter {
1891
1639
  onWritePath;
1892
1640
  rootPath;
@@ -1903,9 +1651,7 @@ class GithubActionsReporter {
1903
1651
  ...testResults.filter((i)=>'fail' === i.status)
1904
1652
  ];
1905
1653
  if (0 === failedTests.length) return;
1906
- const { parseErrorStacktrace } = await Promise.resolve().then(()=>({
1907
- parseErrorStacktrace: error_parseErrorStacktrace
1908
- }));
1654
+ const { parseErrorStacktrace } = await Promise.resolve(error_namespaceObject);
1909
1655
  const logs = [];
1910
1656
  for (const test of failedTests){
1911
1657
  const { testPath } = test;
@@ -1943,15 +1689,15 @@ function escapeData(s) {
1943
1689
  }
1944
1690
  function ansiRegex({ onlyFirst = false } = {}) {
1945
1691
  const ST = '(?:\\u0007|\\u001B\\u005C|\\u009C)';
1946
- const pattern = [
1947
- `[\\u001B\\u009B][[\\]()#;?]*(?:(?:(?:(?:;[-a-zA-Z\\d\\/#&.:=?%@~_]+)*|[a-zA-Z\\d]+(?:;[-a-zA-Z\\d\\/#&.:=?%@~_]*)*)?${ST})`,
1948
- '(?:(?:\\d{1,4}(?:;\\d{0,4})*)?[\\dA-PR-TZcf-nq-uy=><~]))'
1949
- ].join('|');
1692
+ const osc = `(?:\\u001B\\][\\s\\S]*?${ST})`;
1693
+ const csi = '[\\u001B\\u009B][[\\]()#;?]*(?:\\d{1,4}(?:[;:]\\d{0,4})*)?[\\dA-PR-TZcf-nq-uy=><~]';
1694
+ const pattern = `${osc}|${csi}`;
1950
1695
  return new RegExp(pattern, onlyFirst ? void 0 : 'g');
1951
1696
  }
1952
1697
  const regex = ansiRegex();
1953
1698
  function stripAnsi(string) {
1954
1699
  if ('string' != typeof string) throw new TypeError(`Expected a \`string\`, got \`${typeof string}\``);
1700
+ if (!string.includes('\u001B') && !string.includes('\u009B')) return string;
1955
1701
  return string.replace(regex, '');
1956
1702
  }
1957
1703
  const schemeRegex = /^[\w+.-]+:\/\//;
@@ -2255,7 +2001,6 @@ function traceSegmentInternal(segments, memo, line, column, bias) {
2255
2001
  if (-1 === index || index === segments.length) return -1;
2256
2002
  return index;
2257
2003
  }
2258
- const external_node_path_ = __webpack_require__("path");
2259
2004
  const isRelativePath = (p)=>/^\.\.?\//.test(p);
2260
2005
  const isHttpLikeFile = (file)=>/^https?:\/\//.test(file);
2261
2006
  const hintNotDefinedError = (message)=>{
@@ -2266,7 +2011,7 @@ const hintNotDefinedError = (message)=>{
2266
2011
  'jest',
2267
2012
  'vitest'
2268
2013
  ].includes(varName)) return message.replace(`${varName} is not defined`, `${varName} is not defined. Did you mean rstest?`);
2269
- if ('React' === varName) return message.replace(`${varName} is not defined`, `${varName} is not defined. Did you forget to install "${color.yellow('@rsbuild/plugin-react')}" plugin?`);
2014
+ if ('React' === varName) return message.replace(`${varName} is not defined`, `${varName} is not defined. Did you forget to install "${logger_color.yellow('@rsbuild/plugin-react')}" plugin?`);
2270
2015
  }
2271
2016
  return message;
2272
2017
  };
@@ -2276,14 +2021,14 @@ async function error_printError(error, getSourcemap, rootPath) {
2276
2021
  const tips = [
2277
2022
  'Error: not support import `vitest` in Rstest test environment.\n',
2278
2023
  'Solution:',
2279
- ` - Update your code to use imports from "${color.yellow('@rstest/core')}" instead of "${color.yellow('vitest')}".`,
2024
+ ` - Update your code to use imports from "${logger_color.yellow('@rstest/core')}" instead of "${logger_color.yellow('vitest')}".`,
2280
2025
  ' - Enable `globals` configuration and use global API.'
2281
2026
  ];
2282
- logger_logger.stderr(`${color.red(tips.join('\n'))}\n`);
2027
+ logger_logger.stderr(`${logger_color.red(tips.join('\n'))}\n`);
2283
2028
  return;
2284
2029
  }
2285
2030
  if (error.message.includes('is not defined')) error.message = hintNotDefinedError(error.message);
2286
- logger_logger.stderr(`${color.red(color.bold(errorName))}${color.red(`: ${error.message}`)}\n`);
2031
+ logger_logger.stderr(`${logger_color.red(logger_color.bold(errorName))}${logger_color.red(`: ${error.message}`)}\n`);
2287
2032
  if (error.diff) {
2288
2033
  logger_logger.stderr(error.diff);
2289
2034
  logger_logger.stderr('');
@@ -2294,7 +2039,7 @@ async function error_printError(error, getSourcemap, rootPath) {
2294
2039
  fullStack: error.fullStack,
2295
2040
  getSourcemap
2296
2041
  });
2297
- if (!stackFrames.length && !(error.fullStack || isDebug()) && !error.stack.endsWith(error.message)) logger_logger.stderr(color.gray("No error stack found, set 'DEBUG=rstest' to show fullStack."));
2042
+ if (!stackFrames.length && !(error.fullStack || isDebug()) && !error.stack.endsWith(error.message)) logger_logger.stderr(logger_color.gray("No error stack found, set 'DEBUG=rstest' to show fullStack."));
2298
2043
  if (stackFrames[0]) await printCodeFrame(stackFrames[0]);
2299
2044
  printStack(stackFrames, rootPath);
2300
2045
  }
@@ -2302,9 +2047,9 @@ async function error_printError(error, getSourcemap, rootPath) {
2302
2047
  async function printCodeFrame(frame) {
2303
2048
  const filePath = frame.file?.startsWith('file') ? new URL(frame.file) : frame.file;
2304
2049
  if (!filePath) return;
2305
- const source = external_node_fs_["default"].existsSync(filePath) ? external_node_fs_["default"].readFileSync(filePath, 'utf-8') : void 0;
2050
+ const source = node_fs.existsSync(filePath) ? node_fs.readFileSync(filePath, 'utf-8') : void 0;
2306
2051
  if (!source) return;
2307
- const { codeFrameColumns } = await import("./0~262.js").then(__webpack_require__.bind(__webpack_require__, "../../node_modules/.pnpm/@babel+code-frame@7.29.0/node_modules/@babel/code-frame/lib/index.js"));
2052
+ const { codeFrameColumns } = await import("./0~lib.js").then(__webpack_require__.bind(__webpack_require__, "../../node_modules/.pnpm/@babel+code-frame@7.29.0/node_modules/@babel/code-frame/lib/index.js"));
2308
2053
  const result = codeFrameColumns(source, {
2309
2054
  start: {
2310
2055
  line: frame.lineNumber,
@@ -2321,7 +2066,7 @@ function formatStack(frame, rootPath) {
2321
2066
  return '<unknown>' !== frame.methodName ? `at ${frame.methodName} (${formatTestPath(rootPath, frame.file)}:${frame.lineNumber}:${frame.column})` : `at ${formatTestPath(rootPath, frame.file)}:${frame.lineNumber}:${frame.column}`;
2322
2067
  }
2323
2068
  function printStack(stackFrames, rootPath) {
2324
- for (const frame of stackFrames)logger_logger.stderr(color.gray(` ${formatStack(frame, rootPath)}`));
2069
+ for (const frame of stackFrames)logger_logger.stderr(logger_color.gray(` ${formatStack(frame, rootPath)}`));
2325
2070
  stackFrames.length && logger_logger.stderr('');
2326
2071
  }
2327
2072
  const stackIgnores = [
@@ -2349,7 +2094,7 @@ async function error_parseErrorStacktrace({ stack, getSourcemap, fullStack = isD
2349
2094
  if (!source) return null;
2350
2095
  return {
2351
2096
  ...frame,
2352
- file: isRelativePath(source) ? (0, external_node_path_.resolve)(frame.file, '../', source) : (()=>{
2097
+ file: isRelativePath(source) ? external_node_path_resolve(frame.file, '../', source) : (()=>{
2353
2098
  try {
2354
2099
  return new URL(source).pathname;
2355
2100
  } catch {
@@ -2490,7 +2235,7 @@ class JUnitReporter {
2490
2235
  };
2491
2236
  const xmlContent = this.generateJUnitXml(report);
2492
2237
  if (this.outputPath) try {
2493
- const dirname = external_node_path_["default"].dirname(this.outputPath);
2238
+ const dirname = node_path.dirname(this.outputPath);
2494
2239
  await this.tryMkdir(dirname);
2495
2240
  await promises.writeFile(this.outputPath, xmlContent, 'utf-8');
2496
2241
  logger_logger.log(`JUnit XML report written to: ${this.outputPath}`);
@@ -2959,11 +2704,11 @@ async function pathExists(path2, type) {
2959
2704
  }
2960
2705
  }
2961
2706
  function* lookup(cwd = node_process.cwd()) {
2962
- let directory = external_node_path_["default"].resolve(cwd);
2963
- const { root } = external_node_path_["default"].parse(directory);
2707
+ let directory = node_path.resolve(cwd);
2708
+ const { root } = node_path.parse(directory);
2964
2709
  while(directory && directory !== root){
2965
2710
  yield directory;
2966
- directory = external_node_path_["default"].dirname(directory);
2711
+ directory = node_path.dirname(directory);
2967
2712
  }
2968
2713
  }
2969
2714
  async function parsePackageJson(filepath, options) {
@@ -2978,15 +2723,15 @@ async function detect(options = {}) {
2978
2723
  ] } = options;
2979
2724
  let stopDir;
2980
2725
  if ("string" == typeof options.stopDir) {
2981
- const resolved = external_node_path_["default"].resolve(options.stopDir);
2726
+ const resolved = node_path.resolve(options.stopDir);
2982
2727
  stopDir = (dir)=>dir === resolved;
2983
2728
  } else stopDir = options.stopDir;
2984
2729
  for (const directory of lookup(cwd)){
2985
2730
  for (const strategy of strategies)switch(strategy){
2986
2731
  case "lockfile":
2987
- for (const lock of Object.keys(LOCKS))if (await pathExists(external_node_path_["default"].join(directory, lock), "file")) {
2732
+ for (const lock of Object.keys(LOCKS))if (await pathExists(node_path.join(directory, lock), "file")) {
2988
2733
  const name = LOCKS[lock];
2989
- const result = await parsePackageJson(external_node_path_["default"].join(directory, "package.json"), options);
2734
+ const result = await parsePackageJson(node_path.join(directory, "package.json"), options);
2990
2735
  if (result) return result;
2991
2736
  return {
2992
2737
  name,
@@ -2997,14 +2742,14 @@ async function detect(options = {}) {
2997
2742
  case "packageManager-field":
2998
2743
  case "devEngines-field":
2999
2744
  {
3000
- const result = await parsePackageJson(external_node_path_["default"].join(directory, "package.json"), options);
2745
+ const result = await parsePackageJson(node_path.join(directory, "package.json"), options);
3001
2746
  if (result) return result;
3002
2747
  break;
3003
2748
  }
3004
2749
  case "install-metadata":
3005
2750
  for (const metadata of Object.keys(INSTALL_METADATA)){
3006
2751
  const fileOrDir = metadata.endsWith("/") ? "dir" : "file";
3007
- if (await pathExists(external_node_path_["default"].join(directory, metadata), fileOrDir)) {
2752
+ if (await pathExists(node_path.join(directory, metadata), fileOrDir)) {
3008
2753
  const name = INSTALL_METADATA[metadata];
3009
2754
  const agent = "yarn" === name ? isMetadataYarnClassic(metadata) ? "yarn" : "yarn@berry" : name;
3010
2755
  return {
@@ -3399,11 +3144,11 @@ const resolveModuleRoot = (spec)=>{
3399
3144
  if ('function' == typeof import.meta.resolve) {
3400
3145
  const resolved = import.meta.resolve(`${spec}/package.json`);
3401
3146
  const filePath = resolved.startsWith('file://') ? new URL(resolved).pathname : resolved;
3402
- return (0, external_node_path_.dirname)(filePath);
3147
+ return external_node_path_dirname(filePath);
3403
3148
  }
3404
3149
  } catch {}
3405
3150
  try {
3406
- return (0, external_node_path_.dirname)(md_require.resolve(`${spec}/package.json`));
3151
+ return external_node_path_dirname(md_require.resolve(`${spec}/package.json`));
3407
3152
  } catch {
3408
3153
  return null;
3409
3154
  }
@@ -3443,7 +3188,7 @@ const md_parseErrorStacktrace = async ({ stack, getSourcemap, fullStack = false
3443
3188
  column: frame.column || 1
3444
3189
  });
3445
3190
  if (!source) return null;
3446
- const mappedFile = md_isRelativePath(source) ? (0, external_node_path_.resolve)(file || '', '../', source) : (()=>{
3191
+ const mappedFile = md_isRelativePath(source) ? external_node_path_resolve(file || '', '../', source) : (()=>{
3447
3192
  try {
3448
3193
  return new URL(source).pathname;
3449
3194
  } catch {
@@ -3463,8 +3208,8 @@ const md_parseErrorStacktrace = async ({ stack, getSourcemap, fullStack = false
3463
3208
  return dropNodeFrames(trimLeadingNodeFrames(filteredFrames));
3464
3209
  };
3465
3210
  const createCodeFrame = (filePath, { linesAbove, linesBelow, line, column })=>{
3466
- if (!filePath || !external_node_fs_["default"].existsSync(filePath)) return null;
3467
- const source = external_node_fs_["default"].readFileSync(filePath, 'utf-8');
3211
+ if (!filePath || !node_fs.existsSync(filePath)) return null;
3212
+ const source = node_fs.readFileSync(filePath, 'utf-8');
3468
3213
  const sourceLines = source.split(/\r?\n/);
3469
3214
  const lineNumber = Math.max(1, line || 1);
3470
3215
  const columnNumber = Math.max(1, column || 1);
@@ -3526,7 +3271,7 @@ class MdReporter {
3526
3271
  }
3527
3272
  renderFrontMatter(lines) {
3528
3273
  const frontMatter = {
3529
- tool: "@rstest/core@0.9.1",
3274
+ tool: "@rstest/core@0.9.3",
3530
3275
  timestamp: new Date().toISOString()
3531
3276
  };
3532
3277
  if (this.options.header.env) frontMatter.runtime = {
@@ -3897,10 +3642,10 @@ class Rstest {
3897
3642
  process.exit(1);
3898
3643
  }
3899
3644
  const snapshotManager = new SnapshotManager({
3900
- updateSnapshot: rstestConfig.update ? 'all' : T ? 'none' : 'new'
3645
+ updateSnapshot: rstestConfig.update ? 'all' : dist_m ? 'none' : 'new'
3901
3646
  });
3902
3647
  this.snapshotManager = snapshotManager;
3903
- this.version = "0.9.1";
3648
+ this.version = "0.9.3";
3904
3649
  this.rootPath = rootPath;
3905
3650
  this.originalConfig = userConfig;
3906
3651
  this.normalizedConfig = rstestConfig;
@@ -3918,7 +3663,7 @@ class Rstest {
3918
3663
  if (config.source.tsconfigPath) config.source.tsconfigPath = getAbsolutePath(config.root, config.source.tsconfigPath);
3919
3664
  else {
3920
3665
  const tsconfigPath = join(config.root, TS_CONFIG_FILE);
3921
- if ((0, external_node_fs_.existsSync)(tsconfigPath)) config.source.tsconfigPath = tsconfigPath;
3666
+ if (existsSync(tsconfigPath)) config.source.tsconfigPath = tsconfigPath;
3922
3667
  }
3923
3668
  return {
3924
3669
  configFilePath: project.configFilePath,
@@ -3953,6 +3698,9 @@ class Rstest {
3953
3698
  options: {
3954
3699
  showProjectName: projects.length > 1
3955
3700
  }
3701
+ }).filter((r)=>{
3702
+ if ('merge-reports' === command && r instanceof BlobReporter) return false;
3703
+ return true;
3956
3704
  }) : [];
3957
3705
  this.reporters = reporters;
3958
3706
  }
@@ -3977,7 +3725,8 @@ const reportersMap = {
3977
3725
  verbose: VerboseReporter,
3978
3726
  'github-actions': GithubActionsReporter,
3979
3727
  junit: JUnitReporter,
3980
- md: MdReporter
3728
+ md: MdReporter,
3729
+ blob: BlobReporter
3981
3730
  };
3982
3731
  function createReporters(reporters, initConfig = {}) {
3983
3732
  const result = castArray(reporters).map((reporter)=>{
@@ -4011,21 +3760,22 @@ function core_createRstest({ config, projects, configFilePath }, command, fileFi
4011
3760
  projects
4012
3761
  }, config);
4013
3762
  const runTests = async ()=>{
4014
- const { runTests } = await import("./0~2173.js").then((mod)=>({
4015
- runTests: mod.runTests
4016
- }));
3763
+ const { runTests } = await import("./0~runTests.js");
4017
3764
  await runTests(context);
4018
3765
  };
4019
3766
  const listTests = async (options)=>{
4020
- const { listTests } = await import("./0~9634.js").then((mod)=>({
4021
- listTests: mod.listTests
4022
- }));
3767
+ const { listTests } = await import("./0~listTests.js");
4023
3768
  return listTests(context, options);
4024
3769
  };
3770
+ const mergeReports = async (options)=>{
3771
+ const { mergeReports } = await import("./0~mergeReports.js");
3772
+ await mergeReports(context, options);
3773
+ };
4025
3774
  return {
4026
3775
  context,
4027
3776
  runTests,
4028
- listTests
3777
+ listTests,
3778
+ mergeReports
4029
3779
  };
4030
3780
  }
4031
3781
  function defineConfig(config) {
@@ -4034,4 +3784,4 @@ function defineConfig(config) {
4034
3784
  function defineProject(config) {
4035
3785
  return config;
4036
3786
  }
4037
- export { core_createRstest as createRstest, defineConfig, defineProject, detect, error_printError, init_initCli as initCli, loadConfig, mergeProjectConfig, mergeRstestConfig, resolveCommand, runCLI, runRest };
3787
+ export { config_loadConfig as loadConfig, core_createRstest as createRstest, defineConfig, defineProject, detect, error_parseErrorStacktrace as parseErrorStacktrace, error_printError as printError, formatStack, init_initCli as initCli, mergeProjectConfig, mergeRstestConfig, resolveCommand, runCLI, runRest };