playwright-test-explorer 0.0.3 → 0.0.6

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.
@@ -722,6 +722,18 @@ var PlaywrightTestServer = class {
722
722
  for (const message of report) teleReceiver.dispatch(message);
723
723
  return result;
724
724
  }
725
+ /**
726
+ * Get raw test report without processing through TeleReporterReceiver
727
+ * This preserves the complete test.describe hierarchy
728
+ */
729
+ async getRawTestReport(locations, token) {
730
+ const { connection } = await this._testServer();
731
+ if (token?.isCancellationRequested) return [];
732
+ if (!connection) return [];
733
+ const escapedLocations = locations.map(escapeRegex);
734
+ const { report } = await connection.listTests({ locations: escapedLocations });
735
+ return report;
736
+ }
725
737
  async listTests(locations, reporter, token) {
726
738
  const { connection } = await this._testServer();
727
739
  if (token?.isCancellationRequested) return;
@@ -857,7 +869,7 @@ async function listTestFile(workspaceFolder = process.cwd(), configFile = "playw
857
869
  try {
858
870
  const output = { projects: (await testServer.listFiles()).projects.map((project) => ({
859
871
  ...project,
860
- files: project.files.map((filePath) => path.relative(workspaceFolder, filePath))
872
+ files: project.files.map((filePath) => path.relative(workspaceFolder, filePath).replace(/\\/g, "/"))
861
873
  })) };
862
874
  const jsonString = JSON.stringify(output, null, 2);
863
875
  if (outputFile) {
@@ -875,37 +887,6 @@ async function listTestCase(workspaceFolder = process.cwd(), configFile = "playw
875
887
  workspaceFolder,
876
888
  configFile: path.join(workspaceFolder, configFile)
877
889
  });
878
- const reporter = { async onBegin(suite) {
879
- function buildTree(s) {
880
- const node = {
881
- type: "suite",
882
- title: s.title || "Root",
883
- file: s.location ? path.relative(workspaceFolder, s.location.file) : void 0,
884
- children: []
885
- };
886
- if (s.tests) for (const test of s.tests) node.children.push({
887
- type: "test",
888
- title: test.title,
889
- location: {
890
- file: path.relative(workspaceFolder, test.location.file),
891
- line: test.location.line,
892
- column: test.location.column
893
- },
894
- tags: test.tags || [],
895
- annotations: test.annotations || [],
896
- expectedStatus: test.expectedStatus,
897
- timeout: test.timeout
898
- });
899
- if (s.suites) for (const child of s.suites) node.children.push(buildTree(child));
900
- return node;
901
- }
902
- const tree = buildTree(suite);
903
- const jsonString = JSON.stringify(tree, null, 2);
904
- if (outputFile) {
905
- await fs.writeFile(outputFile, jsonString, "utf-8");
906
- console.log(`Results saved to: ${outputFile}`);
907
- } else console.log(jsonString);
908
- } };
909
890
  try {
910
891
  const token = new CancellationToken();
911
892
  const expandedPaths = [];
@@ -916,16 +897,77 @@ async function listTestCase(workspaceFolder = process.cwd(), configFile = "playw
916
897
  if ((await fs.stat(absolutePath)).isDirectory()) {
917
898
  const files = await testServer.listFiles();
918
899
  for (const project of files.projects) for (const file of project.files) {
919
- const relativeFile = path.relative(workspaceFolder, file);
920
- const normalizedFile = relativeFile.replace(/\\/g, "/");
921
- if (normalizedFile.startsWith(normalizedInputPath + "/") || normalizedFile === normalizedInputPath) expandedPaths.push(relativeFile);
900
+ const relativeFile = path.relative(workspaceFolder, file).replace(/\\/g, "/");
901
+ if (relativeFile.startsWith(normalizedInputPath + "/") || relativeFile === normalizedInputPath) expandedPaths.push(relativeFile);
922
902
  }
923
903
  } else expandedPaths.push(relativePath);
924
904
  } catch {
925
905
  expandedPaths.push(relativePath);
926
906
  }
927
907
  }
928
- if (expandedPaths.length > 0) await testServer.listTests(expandedPaths, reporter, token);
908
+ if (expandedPaths.length === 0) {
909
+ testServer.close();
910
+ return;
911
+ }
912
+ const report = await testServer.getRawTestReport(expandedPaths, token);
913
+ function parseEntry(entry, testDir) {
914
+ if (entry.testId) {
915
+ const filePath = testDir ? path.join(testDir, entry.location.file).replace(/\\/g, "/") : entry.location.file.replace(/\\/g, "/");
916
+ return {
917
+ type: "test",
918
+ title: entry.title,
919
+ location: {
920
+ file: filePath,
921
+ line: entry.location.line,
922
+ column: entry.location.column
923
+ },
924
+ tags: entry.tags || [],
925
+ annotations: entry.annotations || [],
926
+ expectedStatus: "passed",
927
+ timeout: 0
928
+ };
929
+ } else {
930
+ const filePath = entry.location && testDir ? path.join(testDir, entry.location.file).replace(/\\/g, "/") : entry.location?.file.replace(/\\/g, "/");
931
+ const node = {
932
+ type: "suite",
933
+ title: entry.title,
934
+ file: filePath,
935
+ children: []
936
+ };
937
+ if (entry.entries && Array.isArray(entry.entries)) for (const childEntry of entry.entries) node.children.push(parseEntry(childEntry, testDir));
938
+ return node;
939
+ }
940
+ }
941
+ const rootNode = {
942
+ type: "suite",
943
+ title: "Root",
944
+ children: []
945
+ };
946
+ let rootDir = "";
947
+ for (const message of report) if (message.method === "onConfigure") {
948
+ rootDir = message.params.config.rootDir || "";
949
+ break;
950
+ }
951
+ for (const message of report) if (message.method === "onProject") {
952
+ const project = message.params.project;
953
+ const projectNode = {
954
+ type: "suite",
955
+ title: project.name,
956
+ children: []
957
+ };
958
+ const relativeRootDir = rootDir ? path.relative(workspaceFolder, rootDir).replace(/\\/g, "/") : "";
959
+ const testDir = project.testDir ? path.join(relativeRootDir, project.testDir).replace(/\\/g, "/") : relativeRootDir;
960
+ if (project.suites && Array.isArray(project.suites)) for (const suite of project.suites) {
961
+ const suiteNode = parseEntry(suite, testDir);
962
+ projectNode.children.push(suiteNode);
963
+ }
964
+ rootNode.children.push(projectNode);
965
+ }
966
+ const jsonString = JSON.stringify(rootNode, null, 2);
967
+ if (outputFile) {
968
+ await fs.writeFile(outputFile, jsonString, "utf-8");
969
+ console.log(`Results saved to: ${outputFile}`);
970
+ } else console.log(jsonString);
929
971
  testServer.close();
930
972
  } catch (error) {
931
973
  console.error("Error:", error);
@@ -937,50 +979,83 @@ async function treeStructure(workspaceFolder = process.cwd(), configFile = "play
937
979
  workspaceFolder,
938
980
  configFile: path.join(workspaceFolder, configFile)
939
981
  });
940
- const reporter = { async onBegin(suite) {
941
- function buildTree(s) {
942
- const node = {
982
+ try {
983
+ const token = cancellationToken || new CancellationToken();
984
+ const files = await testServer.listFiles();
985
+ if (files.projects.length === 0) {
986
+ testServer.close();
987
+ return;
988
+ }
989
+ const allRelativePaths = [];
990
+ for (const project of files.projects) if (project.files.length > 0) {
991
+ const relativePaths = project.files.map((absolutePath) => {
992
+ return path.relative(workspaceFolder, absolutePath).replace(/\\/g, "/");
993
+ });
994
+ allRelativePaths.push(...relativePaths);
995
+ }
996
+ if (allRelativePaths.length === 0) {
997
+ testServer.close();
998
+ return;
999
+ }
1000
+ const report = await testServer.getRawTestReport(allRelativePaths, token);
1001
+ function parseEntry(entry, testDir) {
1002
+ if (entry.testId) {
1003
+ const filePath = testDir ? path.join(testDir, entry.location.file).replace(/\\/g, "/") : entry.location.file.replace(/\\/g, "/");
1004
+ return {
1005
+ type: "test",
1006
+ title: entry.title,
1007
+ location: {
1008
+ file: filePath,
1009
+ line: entry.location.line,
1010
+ column: entry.location.column
1011
+ },
1012
+ tags: entry.tags || [],
1013
+ annotations: entry.annotations || [],
1014
+ expectedStatus: "passed",
1015
+ timeout: 0
1016
+ };
1017
+ } else {
1018
+ const filePath = entry.location && testDir ? path.join(testDir, entry.location.file).replace(/\\/g, "/") : entry.location?.file.replace(/\\/g, "/");
1019
+ const node = {
1020
+ type: "suite",
1021
+ title: entry.title,
1022
+ file: filePath,
1023
+ children: []
1024
+ };
1025
+ if (entry.entries && Array.isArray(entry.entries)) for (const childEntry of entry.entries) node.children.push(parseEntry(childEntry, testDir));
1026
+ return node;
1027
+ }
1028
+ }
1029
+ const rootNode = {
1030
+ type: "suite",
1031
+ title: "Root",
1032
+ children: []
1033
+ };
1034
+ let rootDir = "";
1035
+ for (const message of report) if (message.method === "onConfigure") {
1036
+ rootDir = message.params.config.rootDir || "";
1037
+ break;
1038
+ }
1039
+ for (const message of report) if (message.method === "onProject") {
1040
+ const project = message.params.project;
1041
+ const projectNode = {
943
1042
  type: "suite",
944
- title: s.title || "Root",
945
- file: s.location ? path.relative(workspaceFolder, s.location.file) : void 0,
1043
+ title: project.name,
946
1044
  children: []
947
1045
  };
948
- if (s.tests) for (const test of s.tests) node.children.push({
949
- type: "test",
950
- title: test.title,
951
- location: {
952
- file: path.relative(workspaceFolder, test.location.file),
953
- line: test.location.line,
954
- column: test.location.column
955
- },
956
- tags: test.tags || [],
957
- annotations: test.annotations || [],
958
- expectedStatus: test.expectedStatus,
959
- timeout: test.timeout
960
- });
961
- if (s.suites) for (const child of s.suites) node.children.push(buildTree(child));
962
- return node;
1046
+ const relativeRootDir = rootDir ? path.relative(workspaceFolder, rootDir).replace(/\\/g, "/") : "";
1047
+ const testDir = project.testDir ? path.join(relativeRootDir, project.testDir).replace(/\\/g, "/") : relativeRootDir;
1048
+ if (project.suites && Array.isArray(project.suites)) for (const suite of project.suites) {
1049
+ const suiteNode = parseEntry(suite, testDir);
1050
+ projectNode.children.push(suiteNode);
1051
+ }
1052
+ rootNode.children.push(projectNode);
963
1053
  }
964
- const tree = buildTree(suite);
965
- const jsonString = JSON.stringify(tree, null, 2);
1054
+ const jsonString = JSON.stringify(rootNode, null, 2);
966
1055
  if (outputFile) {
967
1056
  await fs.writeFile(outputFile, jsonString, "utf-8");
968
1057
  console.log(`Results saved to: ${outputFile}`);
969
1058
  } else console.log(jsonString);
970
- } };
971
- try {
972
- const token = cancellationToken || new CancellationToken();
973
- const files = await testServer.listFiles();
974
- if (files.projects.length > 0) {
975
- const allRelativePaths = [];
976
- for (const project of files.projects) if (project.files.length > 0) {
977
- const relativePaths = project.files.map((absolutePath) => {
978
- return path.relative(workspaceFolder, absolutePath);
979
- });
980
- allRelativePaths.push(...relativePaths);
981
- }
982
- if (allRelativePaths.length > 0) await testServer.listTests(allRelativePaths, reporter, token);
983
- }
984
1059
  testServer.close();
985
1060
  } catch (error) {
986
1061
  console.error("Error:", error);
package/dist/cli.js CHANGED
@@ -1,5 +1,5 @@
1
1
  #!/usr/bin/env node
2
- import { i as CancellationToken, n as listTestFile, r as treeStructure, t as listTestCase } from "./api-CyzEW-tV.js";
2
+ import { i as CancellationToken, n as listTestFile, r as treeStructure, t as listTestCase } from "./api-CPNS0jOv.js";
3
3
  import { program } from "commander";
4
4
  import chalk from "chalk";
5
5
  import ora from "ora";
package/dist/index.js CHANGED
@@ -1,3 +1,3 @@
1
- import { n as listTestFile, r as treeStructure, t as listTestCase } from "./api-CyzEW-tV.js";
1
+ import { n as listTestFile, r as treeStructure, t as listTestCase } from "./api-CPNS0jOv.js";
2
2
 
3
3
  export { listTestCase, listTestFile, treeStructure };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "playwright-test-explorer",
3
- "version": "0.0.3",
3
+ "version": "0.0.6",
4
4
  "description": "A CLI tool and library for exploring Playwright tests",
5
5
  "type": "module",
6
6
  "license": "MIT",