SummaryReporter.js 7.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271
  1. 'use strict';
  2. Object.defineProperty(exports, '__esModule', {
  3. value: true
  4. });
  5. exports.default = void 0;
  6. function _chalk() {
  7. const data = _interopRequireDefault(require('chalk'));
  8. _chalk = function () {
  9. return data;
  10. };
  11. return data;
  12. }
  13. function _jestUtil() {
  14. const data = require('jest-util');
  15. _jestUtil = function () {
  16. return data;
  17. };
  18. return data;
  19. }
  20. var _BaseReporter = _interopRequireDefault(require('./BaseReporter'));
  21. var _getResultHeader = _interopRequireDefault(require('./getResultHeader'));
  22. var _getSnapshotSummary = _interopRequireDefault(
  23. require('./getSnapshotSummary')
  24. );
  25. var _utils = require('./utils');
  26. function _interopRequireDefault(obj) {
  27. return obj && obj.__esModule ? obj : {default: obj};
  28. }
  29. function _defineProperty(obj, key, value) {
  30. if (key in obj) {
  31. Object.defineProperty(obj, key, {
  32. value: value,
  33. enumerable: true,
  34. configurable: true,
  35. writable: true
  36. });
  37. } else {
  38. obj[key] = value;
  39. }
  40. return obj;
  41. }
  42. const TEST_SUMMARY_THRESHOLD = 20;
  43. const NPM_EVENTS = new Set([
  44. 'prepublish',
  45. 'publish',
  46. 'postpublish',
  47. 'preinstall',
  48. 'install',
  49. 'postinstall',
  50. 'preuninstall',
  51. 'uninstall',
  52. 'postuninstall',
  53. 'preversion',
  54. 'version',
  55. 'postversion',
  56. 'pretest',
  57. 'test',
  58. 'posttest',
  59. 'prestop',
  60. 'stop',
  61. 'poststop',
  62. 'prestart',
  63. 'start',
  64. 'poststart',
  65. 'prerestart',
  66. 'restart',
  67. 'postrestart'
  68. ]);
  69. const {npm_config_user_agent, npm_lifecycle_event, npm_lifecycle_script} =
  70. process.env;
  71. class SummaryReporter extends _BaseReporter.default {
  72. constructor(globalConfig) {
  73. super();
  74. _defineProperty(this, '_estimatedTime', void 0);
  75. _defineProperty(this, '_globalConfig', void 0);
  76. this._globalConfig = globalConfig;
  77. this._estimatedTime = 0;
  78. } // If we write more than one character at a time it is possible that
  79. // Node.js exits in the middle of printing the result. This was first observed
  80. // in Node.js 0.10 and still persists in Node.js 6.7+.
  81. // Let's print the test failure summary character by character which is safer
  82. // when hundreds of tests are failing.
  83. _write(string) {
  84. for (let i = 0; i < string.length; i++) {
  85. process.stderr.write(string.charAt(i));
  86. }
  87. }
  88. onRunStart(aggregatedResults, options) {
  89. super.onRunStart(aggregatedResults, options);
  90. this._estimatedTime = options.estimatedTime;
  91. }
  92. onRunComplete(contexts, aggregatedResults) {
  93. const {numTotalTestSuites, testResults, wasInterrupted} = aggregatedResults;
  94. if (numTotalTestSuites) {
  95. const lastResult = testResults[testResults.length - 1]; // Print a newline if the last test did not fail to line up newlines
  96. // similar to when an error would have been thrown in the test.
  97. if (
  98. !this._globalConfig.verbose &&
  99. lastResult &&
  100. !lastResult.numFailingTests &&
  101. !lastResult.testExecError
  102. ) {
  103. this.log('');
  104. }
  105. this._printSummary(aggregatedResults, this._globalConfig);
  106. this._printSnapshotSummary(
  107. aggregatedResults.snapshot,
  108. this._globalConfig
  109. );
  110. if (numTotalTestSuites) {
  111. let message = (0, _utils.getSummary)(aggregatedResults, {
  112. estimatedTime: this._estimatedTime
  113. });
  114. if (!this._globalConfig.silent) {
  115. message +=
  116. '\n' +
  117. (wasInterrupted
  118. ? _chalk().default.bold.red('Test run was interrupted.')
  119. : this._getTestSummary(contexts, this._globalConfig));
  120. }
  121. this.log(message);
  122. }
  123. }
  124. }
  125. _printSnapshotSummary(snapshots, globalConfig) {
  126. if (
  127. snapshots.added ||
  128. snapshots.filesRemoved ||
  129. snapshots.unchecked ||
  130. snapshots.unmatched ||
  131. snapshots.updated
  132. ) {
  133. let updateCommand;
  134. const event = npm_lifecycle_event || '';
  135. const prefix = NPM_EVENTS.has(event) ? '' : 'run ';
  136. const isYarn =
  137. typeof npm_config_user_agent === 'string' &&
  138. npm_config_user_agent.includes('yarn');
  139. const client = isYarn ? 'yarn' : 'npm';
  140. const scriptUsesJest =
  141. typeof npm_lifecycle_script === 'string' &&
  142. npm_lifecycle_script.includes('jest');
  143. if (globalConfig.watch || globalConfig.watchAll) {
  144. updateCommand = 'press `u`';
  145. } else if (event && scriptUsesJest) {
  146. updateCommand = `run \`${
  147. client + ' ' + prefix + event + (isYarn ? '' : ' --')
  148. } -u\``;
  149. } else {
  150. updateCommand = 're-run jest with `-u`';
  151. }
  152. const snapshotSummary = (0, _getSnapshotSummary.default)(
  153. snapshots,
  154. globalConfig,
  155. updateCommand
  156. );
  157. snapshotSummary.forEach(this.log);
  158. this.log(''); // print empty line
  159. }
  160. }
  161. _printSummary(aggregatedResults, globalConfig) {
  162. // If there were any failing tests and there was a large number of tests
  163. // executed, re-print the failing results at the end of execution output.
  164. const failedTests = aggregatedResults.numFailedTests;
  165. const runtimeErrors = aggregatedResults.numRuntimeErrorTestSuites;
  166. if (
  167. failedTests + runtimeErrors > 0 &&
  168. aggregatedResults.numTotalTestSuites > TEST_SUMMARY_THRESHOLD
  169. ) {
  170. this.log(_chalk().default.bold('Summary of all failing tests'));
  171. aggregatedResults.testResults.forEach(testResult => {
  172. const {failureMessage} = testResult;
  173. if (failureMessage) {
  174. this._write(
  175. (0, _getResultHeader.default)(testResult, globalConfig) +
  176. '\n' +
  177. failureMessage +
  178. '\n'
  179. );
  180. }
  181. });
  182. this.log(''); // print empty line
  183. }
  184. }
  185. _getTestSummary(contexts, globalConfig) {
  186. const getMatchingTestsInfo = () => {
  187. const prefix = globalConfig.findRelatedTests
  188. ? ' related to files matching '
  189. : ' matching ';
  190. return (
  191. _chalk().default.dim(prefix) +
  192. (0, _jestUtil().testPathPatternToRegExp)(
  193. globalConfig.testPathPattern
  194. ).toString()
  195. );
  196. };
  197. let testInfo = '';
  198. if (globalConfig.runTestsByPath) {
  199. testInfo = _chalk().default.dim(' within paths');
  200. } else if (globalConfig.onlyChanged) {
  201. testInfo = _chalk().default.dim(' related to changed files');
  202. } else if (globalConfig.testPathPattern) {
  203. testInfo = getMatchingTestsInfo();
  204. }
  205. let nameInfo = '';
  206. if (globalConfig.runTestsByPath) {
  207. nameInfo = ' ' + globalConfig.nonFlagArgs.map(p => `"${p}"`).join(', ');
  208. } else if (globalConfig.testNamePattern) {
  209. nameInfo =
  210. _chalk().default.dim(' with tests matching ') +
  211. `"${globalConfig.testNamePattern}"`;
  212. }
  213. const contextInfo =
  214. contexts.size > 1
  215. ? _chalk().default.dim(' in ') +
  216. contexts.size +
  217. _chalk().default.dim(' projects')
  218. : '';
  219. return (
  220. _chalk().default.dim('Ran all test suites') +
  221. testInfo +
  222. nameInfo +
  223. contextInfo +
  224. _chalk().default.dim('.')
  225. );
  226. }
  227. }
  228. exports.default = SummaryReporter;
  229. _defineProperty(SummaryReporter, 'filename', __filename);