jest-html-reporter 2.6.2 → 2.8.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/README.md +1 -0
- package/dist/htmlreporter.js +373 -0
- package/dist/htmlreporter.js.map +1 -0
- package/dist/index.js +602 -0
- package/dist/index.js.map +1 -0
- package/dist/main.js +104 -18
- package/dist/main.min.js +1 -1
- package/dist/sortingMethods.js +57 -0
- package/dist/sortingMethods.js.map +1 -0
- package/package.json +5 -5
- package/style/darkTheme.css +3 -0
- package/style/defaultTheme.css +3 -0
- package/style/lightTheme.css +3 -0
package/dist/main.js
CHANGED
|
@@ -53,6 +53,55 @@ const writeFile = ({ filePath, content }) => new Promise((resolve, reject) => {
|
|
|
53
53
|
});
|
|
54
54
|
});
|
|
55
55
|
|
|
56
|
+
/**
|
|
57
|
+
* Appends a file at the given destination
|
|
58
|
+
* @param {String} filePath
|
|
59
|
+
* @param {Any} content
|
|
60
|
+
*/
|
|
61
|
+
const appendFile = ({ filePath, content }) => new Promise((resolve, reject) => {
|
|
62
|
+
mkdirp(path.dirname(filePath), (mkdirpError) => {
|
|
63
|
+
if (mkdirpError) {
|
|
64
|
+
return reject(new Error(`Something went wrong when creating the folder: ${mkdirpError}`));
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
// Check if the file exists or not
|
|
68
|
+
return fs.readFile(filePath, 'utf8', (err, existingContent) => {
|
|
69
|
+
let parsedContent = content;
|
|
70
|
+
// The file exists - we need to strip all unecessary html
|
|
71
|
+
if (!err) {
|
|
72
|
+
const contentSearch = /<body>(.*?)<\/body>/gm.exec(content);
|
|
73
|
+
if (contentSearch) {
|
|
74
|
+
const [strippedContent] = contentSearch;
|
|
75
|
+
parsedContent = strippedContent;
|
|
76
|
+
}
|
|
77
|
+
// Then we need to add the stripped content just before the </body> tag
|
|
78
|
+
if (existingContent) {
|
|
79
|
+
let newContent = existingContent;
|
|
80
|
+
const closingBodyTag = /<\/body>/gm.exec(existingContent);
|
|
81
|
+
const indexOfClosingBodyTag = closingBodyTag ? closingBodyTag.index : 0;
|
|
82
|
+
|
|
83
|
+
newContent = [existingContent.slice(0, indexOfClosingBodyTag), parsedContent, existingContent.slice(indexOfClosingBodyTag)]
|
|
84
|
+
.join('');
|
|
85
|
+
|
|
86
|
+
return fs.writeFile(filePath, newContent, (writeFileError) => {
|
|
87
|
+
if (writeFileError) {
|
|
88
|
+
return reject(new Error(`Something went wrong when creating the file: ${writeFileError}`));
|
|
89
|
+
}
|
|
90
|
+
return resolve(filePath);
|
|
91
|
+
});
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
return fs.appendFile(filePath, parsedContent, (writeFileError) => {
|
|
96
|
+
if (writeFileError) {
|
|
97
|
+
return reject(new Error(`Something went wrong when appending the file: ${writeFileError}`));
|
|
98
|
+
}
|
|
99
|
+
return resolve(filePath);
|
|
100
|
+
});
|
|
101
|
+
});
|
|
102
|
+
});
|
|
103
|
+
});
|
|
104
|
+
|
|
56
105
|
/**
|
|
57
106
|
* Reads and returns the content of a given file
|
|
58
107
|
* @param {String} filePath
|
|
@@ -101,6 +150,7 @@ const sortAlphabetically = ({ a, b, reversed }) => {
|
|
|
101
150
|
module.exports = {
|
|
102
151
|
logMessage,
|
|
103
152
|
writeFile,
|
|
153
|
+
appendFile,
|
|
104
154
|
getFileContent,
|
|
105
155
|
createHtmlBase,
|
|
106
156
|
sortAlphabetically,
|
|
@@ -109,9 +159,10 @@ module.exports = {
|
|
|
109
159
|
|
|
110
160
|
var utils_1 = utils.logMessage;
|
|
111
161
|
var utils_2 = utils.writeFile;
|
|
112
|
-
var utils_3 = utils.
|
|
113
|
-
var utils_4 = utils.
|
|
114
|
-
var utils_5 = utils.
|
|
162
|
+
var utils_3 = utils.appendFile;
|
|
163
|
+
var utils_4 = utils.getFileContent;
|
|
164
|
+
var utils_5 = utils.createHtmlBase;
|
|
165
|
+
var utils_6 = utils.sortAlphabetically;
|
|
115
166
|
|
|
116
167
|
var sorting = createCommonjsModule(function (module) {
|
|
117
168
|
/**
|
|
@@ -259,6 +310,7 @@ var sorting_1 = sorting.sortSuiteResults;
|
|
|
259
310
|
class ReportGenerator {
|
|
260
311
|
constructor(config) {
|
|
261
312
|
this.config = config;
|
|
313
|
+
this.consoleLogs = null;
|
|
262
314
|
}
|
|
263
315
|
|
|
264
316
|
/**
|
|
@@ -270,6 +322,7 @@ class ReportGenerator {
|
|
|
270
322
|
const fileDestination = this.config.getOutputFilepath();
|
|
271
323
|
const useCssFile = this.config.shouldUseCssFile();
|
|
272
324
|
const shouldGetStylesheetContent = this.config.shouldGetStylesheetContent();
|
|
325
|
+
const append = this.config.getAppend();
|
|
273
326
|
let stylesheetPath = null;
|
|
274
327
|
let stylesheetContent = null;
|
|
275
328
|
|
|
@@ -289,10 +342,13 @@ class ReportGenerator {
|
|
|
289
342
|
stylesheet,
|
|
290
343
|
stylesheetPath,
|
|
291
344
|
}))
|
|
292
|
-
.then(xmlBuilderOutput => utils.
|
|
345
|
+
.then(xmlBuilderOutput => (append ? utils.appendFile({
|
|
293
346
|
filePath: fileDestination,
|
|
294
347
|
content: xmlBuilderOutput,
|
|
295
|
-
})
|
|
348
|
+
}) : utils.writeFile({
|
|
349
|
+
filePath: fileDestination,
|
|
350
|
+
content: xmlBuilderOutput,
|
|
351
|
+
})))
|
|
296
352
|
.then(() => utils.logMessage({
|
|
297
353
|
type: 'success',
|
|
298
354
|
msg: `Report generated (${fileDestination})`,
|
|
@@ -335,7 +391,11 @@ class ReportGenerator {
|
|
|
335
391
|
* @param {String} stylesheetPath Optional path to an external stylesheet
|
|
336
392
|
* @return {xmlbuilder}
|
|
337
393
|
*/
|
|
338
|
-
renderHtmlReport({
|
|
394
|
+
renderHtmlReport({
|
|
395
|
+
data,
|
|
396
|
+
stylesheet,
|
|
397
|
+
stylesheetPath,
|
|
398
|
+
}) {
|
|
339
399
|
return new Promise((resolve, reject) => {
|
|
340
400
|
// Make sure that test data was provided
|
|
341
401
|
if (!data) { return reject(new Error('Test data missing or malformed')); }
|
|
@@ -462,18 +522,22 @@ class ReportGenerator {
|
|
|
462
522
|
testTr.ele('td', { class: 'result' }, (test.status === 'passed') ? `${test.status} in ${test.duration / 1000}s` : test.status);
|
|
463
523
|
});
|
|
464
524
|
|
|
465
|
-
//
|
|
466
|
-
if (
|
|
467
|
-
//
|
|
468
|
-
const
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
|
|
525
|
+
// All console.logs caught during the test run
|
|
526
|
+
if (this.consoleLogs && this.consoleLogs.length > 0 && (this.config.shouldIncludeConsoleLog())) {
|
|
527
|
+
// Filter out the logs for this test file path
|
|
528
|
+
const filteredConsoleLogs = this.consoleLogs.find(logs => logs.testFilePath === suite.testFilePath);
|
|
529
|
+
if (filteredConsoleLogs && filteredConsoleLogs.logs.length > 0) {
|
|
530
|
+
// Console Log Container
|
|
531
|
+
const consoleLogContainer = reportBody.ele('div', { class: 'suite-consolelog' });
|
|
532
|
+
// Console Log Header
|
|
533
|
+
consoleLogContainer.ele('div', { class: 'suite-consolelog-header' }, 'Console Log');
|
|
534
|
+
// Apply the logs to the body
|
|
535
|
+
filteredConsoleLogs.logs.forEach((log) => {
|
|
536
|
+
const logElement = consoleLogContainer.ele('div', { class: 'suite-consolelog-item' });
|
|
537
|
+
logElement.ele('pre', { class: 'suite-consolelog-item-origin' }, stripAnsi(log.origin));
|
|
538
|
+
logElement.ele('pre', { class: 'suite-consolelog-item-message' }, stripAnsi(log.message));
|
|
539
|
+
});
|
|
540
|
+
}
|
|
477
541
|
}
|
|
478
542
|
});
|
|
479
543
|
|
|
@@ -624,6 +688,13 @@ const getSort = () =>
|
|
|
624
688
|
const getStatusIgnoreFilter = () =>
|
|
625
689
|
process.env.JEST_HTML_REPORTER_STATUS_FILTER || config.statusIgnoreFilter || null;
|
|
626
690
|
|
|
691
|
+
/**
|
|
692
|
+
* Returns whether or not new reports should be Appended to existing report
|
|
693
|
+
* @return {Boolean}
|
|
694
|
+
*/
|
|
695
|
+
const getAppend = () =>
|
|
696
|
+
process.env.JEST_HTML_REPORTER_APPEND || config.append || false;
|
|
697
|
+
|
|
627
698
|
module.exports = {
|
|
628
699
|
config,
|
|
629
700
|
setup,
|
|
@@ -644,6 +715,7 @@ module.exports = {
|
|
|
644
715
|
getDateFormat,
|
|
645
716
|
getSort,
|
|
646
717
|
getStatusIgnoreFilter,
|
|
718
|
+
getAppend,
|
|
647
719
|
};
|
|
648
720
|
});
|
|
649
721
|
|
|
@@ -666,6 +738,7 @@ var config_17 = config_1.getTheme;
|
|
|
666
738
|
var config_18 = config_1.getDateFormat;
|
|
667
739
|
var config_19 = config_1.getSort;
|
|
668
740
|
var config_20 = config_1.getStatusIgnoreFilter;
|
|
741
|
+
var config_21 = config_1.getAppend;
|
|
669
742
|
|
|
670
743
|
function JestHtmlReporter(globalConfig, options) {
|
|
671
744
|
// Initiate the config and setup the Generator class
|
|
@@ -692,12 +765,25 @@ function JestHtmlReporter(globalConfig, options) {
|
|
|
692
765
|
*/
|
|
693
766
|
this.jestConfig = globalConfig;
|
|
694
767
|
this.jestOptions = options;
|
|
768
|
+
this.consoleLogs = [];
|
|
769
|
+
|
|
770
|
+
this.onTestResult = (data, result) => {
|
|
771
|
+
// Catch console logs per test
|
|
772
|
+
if (result.console) {
|
|
773
|
+
this.consoleLogs.push({
|
|
774
|
+
testFilePath: result.testFilePath,
|
|
775
|
+
logs: result.console,
|
|
776
|
+
});
|
|
777
|
+
}
|
|
778
|
+
};
|
|
695
779
|
|
|
696
780
|
this.onRunComplete = (contexts, testResult) => {
|
|
697
781
|
// Apply the configuration within jest.config.json to the current config
|
|
698
782
|
config_1.setConfigData(this.jestOptions);
|
|
699
783
|
// Apply the updated config
|
|
700
784
|
reportGenerator$$1.config = config_1;
|
|
785
|
+
// Add the console logs that we've caught
|
|
786
|
+
reportGenerator$$1.consoleLogs = this.consoleLogs;
|
|
701
787
|
// Generate Report
|
|
702
788
|
return reportGenerator$$1.generate({ data: testResult });
|
|
703
789
|
};
|
package/dist/main.min.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
"use strict";function _interopDefault(e){return e&&"object"==typeof e&&"default"in e?e.default:e}var fs=_interopDefault(require("fs")),path=_interopDefault(require("path")),mkdirp=_interopDefault(require("mkdirp")),xmlbuilder=_interopDefault(require("xmlbuilder")),dateformat=_interopDefault(require("dateformat")),stripAnsi=_interopDefault(require("strip-ansi"));function createCommonjsModule(e,t){return e(t={exports:{}},t.exports),t.exports}var utils=createCommonjsModule(function(e){e.exports={logMessage:({type:e,msg:t,ignoreConsole:s})=>{const o={default:"[37m%s[0m",success:"[32m%s[0m",error:"[31m%s[0m"},r=o[e]?o[e]:o.default,i=`jest-html-reporter >> ${t}`;return s||console.log(r,i),{logColor:r,logMsg:i}},writeFile:({filePath:e,content:t})=>new Promise((s,o)=>{mkdirp(path.dirname(e),r=>r?o(new Error(`Something went wrong when creating the folder: ${r}`)):fs.writeFile(e,t,t=>t?o(new Error(`Something went wrong when creating the file: ${t}`)):s(e)))}),getFileContent:({filePath:e})=>new Promise((t,s)=>{fs.readFile(e,"utf8",(o,r)=>o?s(new Error(`Could not locate file: '${e}': ${o}`)):t(r))}),createHtmlBase:({pageTitle:e,stylesheet:t,stylesheetPath:s})=>{const o={html:{head:{meta:{"@charset":"utf-8"},title:{"#text":e}}}};return s?o.html.head.link={"@rel":"stylesheet","@type":"text/css","@href":s}:o.html.head.style={"@type":"text/css","#text":t},xmlbuilder.create(o)},sortAlphabetically:({a:e,b:t,reversed:s})=>!s&&e<t||s&&e>t?-1:!s&&e>t||s&&e<t?1:0}}),utils_1=utils.logMessage,utils_2=utils.writeFile,utils_3=utils.getFileContent,utils_4=utils.createHtmlBase,utils_5=utils.sortAlphabetically,sorting=createCommonjsModule(function(e){e.exports={sortSuiteResults:({testData:e,sortMethod:t})=>{if(t)switch(t.toLowerCase()){case"status":return(e=>{const t=[],s=[],o=[];return e.forEach(e=>{const r=[],i=[],n=[];e.testResults.forEach(e=>{"pending"===e.status?r.push(e):"failed"===e.status?i.push(e):n.push(e)}),r.length&&t.push(Object.assign({},e,{testResults:r})),i.length&&s.push(Object.assign({},e,{testResults:i})),n.length&&o.push(Object.assign({},e,{testResults:n}))}),[].concat(t,s,o)})(e);case"executiondesc":return(e=>(e&&e.sort((e,t)=>t.perfStats.end-t.perfStats.start-(e.perfStats.end-e.perfStats.start)),e))(e);case"executionasc":return(e=>(e&&e.sort((e,t)=>e.perfStats.end-e.perfStats.start-(t.perfStats.end-t.perfStats.start)),e))(e);case"titledesc":return(e=>{if(e){const t=e.sort((e,t)=>utils.sortAlphabetically({a:e.testFilePath,b:t.testFilePath,reversed:!0}));return t.forEach(e=>{e.testResults.sort((e,t)=>utils.sortAlphabetically({a:e.ancestorTitles.join(" "),b:t.ancestorTitles.join(" "),reversed:!0}))}),t}return e})(e);case"titleasc":return(e=>{if(e){const t=e.sort((e,t)=>utils.sortAlphabetically({a:e.testFilePath,b:t.testFilePath}));return t.forEach(e=>{e.testResults.sort((e,t)=>utils.sortAlphabetically({a:e.ancestorTitles.join(" "),b:t.ancestorTitles.join(" ")}))}),t}return e})(e);default:return e}return e}}}),sorting_1=sorting.sortSuiteResults;class ReportGenerator{constructor(e){this.config=e}generate({data:e,ignoreConsole:t}){const s=this.config.getOutputFilepath(),o=this.config.shouldUseCssFile(),r=this.config.shouldGetStylesheetContent();let i=null,n=null;return o&&(i=this.config.getStylesheetFilepath()),(n=r?()=>this.getStylesheetContent():()=>Promise.resolve())().then(t=>this.renderHtmlReport({data:e,stylesheet:t,stylesheetPath:i})).then(e=>utils.writeFile({filePath:s,content:e})).then(()=>utils.logMessage({type:"success",msg:`Report generated (${s})`,ignoreConsole:t})).catch(e=>utils.logMessage({type:"error",msg:e,ignoreConsole:t}))}integrateContentIntoBoilerplate({content:e}){const t=this.config.getBoilerplatePath();return new Promise((s,o)=>utils.getFileContent({filePath:t}).then(t=>s(t.replace("{jesthtmlreporter-content}",e))).catch(e=>o(e)))}getStylesheetContent(){const e=this.config.getStylesheetFilepath();return utils.getFileContent({filePath:e})}renderHtmlReport({data:e,stylesheet:t,stylesheetPath:s}){return new Promise((o,r)=>{if(!e)return r(new Error("Test data missing or malformed"));const i=this.config.getPageTitle(),n=this.getReportBody({data:e,pageTitle:i});if(this.config.getBoilerplatePath())return this.integrateContentIntoBoilerplate({content:n}).then(e=>o(e));const l=utils.createHtmlBase({pageTitle:i,stylesheet:t,stylesheetPath:s}),a=l.ele("body");a.raw(n);const c=this.config.getCustomScriptFilepath();return c&&a.raw(`<script src="${c}"><\/script>`),o(l)})}getReportBody({data:e,pageTitle:t}){const s=xmlbuilder.begin().element("div",{id:"jesthtml-content"}),o=s.ele("header");o.ele("h1",{id:"title"},t);const r=this.config.getLogo();r&&o.ele("img",{id:"logo",src:r});const i=s.ele("div",{id:"metadata-container"}),n=new Date(e.startTime);i.ele("div",{id:"timestamp"},`Start: ${dateformat(n,this.config.getDateFormat())}`),i.ele("div",{id:"summary"},`${e.numTotalTests} tests -- ${e.numPassedTests} passed / ${e.numFailedTests} failed / ${e.numPendingTests} pending`);const l=sorting.sortSuiteResults({testData:e.testResults,sortMethod:this.config.getSort()}),a=this.config.getStatusIgnoreFilter();let c=[];return a&&(c=a.replace(/\s/g,"").toLowerCase().split(",")),l.forEach(e=>{for(let t=e.testResults.length-1;t>=0;t-=1)c.includes(e.testResults[t].status)&&e.testResults.splice(t,1);if(!e.testResults||e.testResults.length<=0)return;const t=s.ele("div",{class:"suite-info"});t.ele("div",{class:"suite-path"},e.testFilePath);const o=(e.perfStats.end-e.perfStats.start)/1e3;t.ele("div",{class:`suite-time${o>5?" warn":""}`},`${o}s`);const r=s.ele("table",{class:"suite-table",cellspacing:"0",cellpadding:"0"});if(e.testResults.forEach(e=>{const t=r.ele("tr",{class:e.status});t.ele("td",{class:"suite"},e.ancestorTitles.join(" > "));const s=t.ele("td",{class:"test"},e.title);if(e.failureMessages&&this.config.shouldIncludeFailureMessages()){const t=s.ele("div",{class:"failureMessages"});e.failureMessages.forEach(e=>{t.ele("pre",{class:"failureMsg"},stripAnsi(e))})}t.ele("td",{class:"result"},"passed"===e.status?`${e.status} in ${e.duration/1e3}s`:e.status)}),e.console&&e.console.length>0&&this.config.shouldIncludeConsoleLog()){const t=s.ele("div",{class:"suite-consolelog"});t.ele("div",{class:"suite-consolelog-header"},"Console Log"),e.console.forEach(e=>{const s=t.ele("div",{class:"suite-consolelog-item"});s.ele("pre",{class:"suite-consolelog-item-origin"},stripAnsi(e.origin)),s.ele("pre",{class:"suite-consolelog-item-message"},stripAnsi(e.message))})}}),s}}var reportGenerator=ReportGenerator,config_1=createCommonjsModule(function(e){const t={},s=e=>Object.assign(t,e),o=()=>process.env.JEST_HTML_REPORTER_THEME||t.theme||"defaultTheme",r=()=>Boolean(process.env.JEST_HTML_REPORTER_STYLE_OVERRIDE_PATH)||Boolean(t.styleOverridePath),i=()=>process.env.JEST_HTML_REPORTER_USE_CSS_FILE||t.useCssFile||!1;e.exports={config:t,setup:()=>{try{const e=fs.readFileSync(path.join(process.cwd(),"jesthtmlreporter.config.json"),"utf8");if(e)return s(JSON.parse(e))}catch(e){}try{const e=fs.readFileSync(path.join(process.cwd(),"package.json"),"utf8");if(e)return s(JSON.parse(e)["jest-html-reporter"])}catch(e){}return t},setConfigData:s,getOutputFilepath:()=>{return(process.env.JEST_HTML_REPORTER_OUTPUT_PATH||t.outputPath||path.join(process.cwd(),"test-report.html")).replace(/<rootdir>/gi,".")},getStylesheetFilepath:()=>process.env.JEST_HTML_REPORTER_STYLE_OVERRIDE_PATH||t.styleOverridePath||path.join(__dirname,`../style/${o()}.css`),getHasStyleOverridePath:r,getCustomScriptFilepath:()=>process.env.JEST_HTML_REPORTER_CUSTOM_SCRIPT_PATH||t.customScriptPath||null,getPageTitle:()=>process.env.JEST_HTML_REPORTER_PAGE_TITLE||t.pageTitle||"Test report",getLogo:()=>process.env.JEST_HTML_REPORTER_LOGO||t.logo||null,shouldIncludeFailureMessages:()=>process.env.JEST_HTML_REPORTER_INCLUDE_FAILURE_MSG||t.includeFailureMsg||!1,shouldIncludeConsoleLog:()=>process.env.JEST_HTML_REPORTER_INCLUDE_CONSOLE_LOG||t.includeConsoleLog||!1,shouldUseCssFile:i,shouldGetStylesheetContent:()=>!(r()&&i()),getExecutionTimeWarningThreshold:()=>process.env.JEST_HTML_REPORTER_EXECUTION_TIME_WARNING_THRESHOLD||t.executionTimeWarningThreshold||5,getBoilerplatePath:()=>process.env.JEST_HTML_REPORTER_BOILERPLATE||t.boilerplate||null,getTheme:o,getDateFormat:()=>process.env.JEST_HTML_REPORTER_DATE_FORMAT||t.dateFormat||"yyyy-mm-dd HH:MM:ss",getSort:()=>process.env.JEST_HTML_REPORTER_SORT||t.sort||"default",getStatusIgnoreFilter:()=>process.env.JEST_HTML_REPORTER_STATUS_FILTER||t.statusIgnoreFilter||null}}),config_2=config_1.config,config_3=config_1.setup,config_4=config_1.setConfigData,config_5=config_1.getOutputFilepath,config_6=config_1.getStylesheetFilepath,config_7=config_1.getHasStyleOverridePath,config_8=config_1.getCustomScriptFilepath,config_9=config_1.getPageTitle,config_10=config_1.getLogo,config_11=config_1.shouldIncludeFailureMessages,config_12=config_1.shouldIncludeConsoleLog,config_13=config_1.shouldUseCssFile,config_14=config_1.shouldGetStylesheetContent,config_15=config_1.getExecutionTimeWarningThreshold,config_16=config_1.getBoilerplatePath,config_17=config_1.getTheme,config_18=config_1.getDateFormat,config_19=config_1.getSort,config_20=config_1.getStatusIgnoreFilter;function JestHtmlReporter(e,t){config_1.setup();const s=new reportGenerator(config_1);if(Object.prototype.hasOwnProperty.call(e,"testResults"))return s.generate({data:e}),e;this.jestConfig=e,this.jestOptions=t,this.onRunComplete=((e,t)=>(config_1.setConfigData(this.jestOptions),s.config=config_1,s.generate({data:t})))}var src=JestHtmlReporter;module.exports=src;
|
|
1
|
+
"use strict";function _interopDefault(e){return e&&"object"==typeof e&&"default"in e?e.default:e}var fs=_interopDefault(require("fs")),path=_interopDefault(require("path")),mkdirp=_interopDefault(require("mkdirp")),xmlbuilder=_interopDefault(require("xmlbuilder")),dateformat=_interopDefault(require("dateformat")),stripAnsi=_interopDefault(require("strip-ansi"));function createCommonjsModule(e,t){return e(t={exports:{}},t.exports),t.exports}var utils=createCommonjsModule(function(e){e.exports={logMessage:({type:e,msg:t,ignoreConsole:s})=>{const o={default:"[37m%s[0m",success:"[32m%s[0m",error:"[31m%s[0m"},n=o[e]?o[e]:o.default,i=`jest-html-reporter >> ${t}`;return s||console.log(n,i),{logColor:n,logMsg:i}},writeFile:({filePath:e,content:t})=>new Promise((s,o)=>{mkdirp(path.dirname(e),n=>n?o(new Error(`Something went wrong when creating the folder: ${n}`)):fs.writeFile(e,t,t=>t?o(new Error(`Something went wrong when creating the file: ${t}`)):s(e)))}),appendFile:({filePath:e,content:t})=>new Promise((s,o)=>{mkdirp(path.dirname(e),n=>n?o(new Error(`Something went wrong when creating the folder: ${n}`)):fs.readFile(e,"utf8",(n,i)=>{let r=t;if(!n){const n=/<body>(.*?)<\/body>/gm.exec(t);if(n){const[e]=n;r=e}if(i){let t=i;const n=/<\/body>/gm.exec(i),l=n?n.index:0;return t=[i.slice(0,l),r,i.slice(l)].join(""),fs.writeFile(e,t,t=>t?o(new Error(`Something went wrong when creating the file: ${t}`)):s(e))}}return fs.appendFile(e,r,t=>t?o(new Error(`Something went wrong when appending the file: ${t}`)):s(e))}))}),getFileContent:({filePath:e})=>new Promise((t,s)=>{fs.readFile(e,"utf8",(o,n)=>o?s(new Error(`Could not locate file: '${e}': ${o}`)):t(n))}),createHtmlBase:({pageTitle:e,stylesheet:t,stylesheetPath:s})=>{const o={html:{head:{meta:{"@charset":"utf-8"},title:{"#text":e}}}};return s?o.html.head.link={"@rel":"stylesheet","@type":"text/css","@href":s}:o.html.head.style={"@type":"text/css","#text":t},xmlbuilder.create(o)},sortAlphabetically:({a:e,b:t,reversed:s})=>!s&&e<t||s&&e>t?-1:!s&&e>t||s&&e<t?1:0}}),utils_1=utils.logMessage,utils_2=utils.writeFile,utils_3=utils.appendFile,utils_4=utils.getFileContent,utils_5=utils.createHtmlBase,utils_6=utils.sortAlphabetically,sorting=createCommonjsModule(function(e){e.exports={sortSuiteResults:({testData:e,sortMethod:t})=>{if(t)switch(t.toLowerCase()){case"status":return(e=>{const t=[],s=[],o=[];return e.forEach(e=>{const n=[],i=[],r=[];e.testResults.forEach(e=>{"pending"===e.status?n.push(e):"failed"===e.status?i.push(e):r.push(e)}),n.length&&t.push(Object.assign({},e,{testResults:n})),i.length&&s.push(Object.assign({},e,{testResults:i})),r.length&&o.push(Object.assign({},e,{testResults:r}))}),[].concat(t,s,o)})(e);case"executiondesc":return(e=>(e&&e.sort((e,t)=>t.perfStats.end-t.perfStats.start-(e.perfStats.end-e.perfStats.start)),e))(e);case"executionasc":return(e=>(e&&e.sort((e,t)=>e.perfStats.end-e.perfStats.start-(t.perfStats.end-t.perfStats.start)),e))(e);case"titledesc":return(e=>{if(e){const t=e.sort((e,t)=>utils.sortAlphabetically({a:e.testFilePath,b:t.testFilePath,reversed:!0}));return t.forEach(e=>{e.testResults.sort((e,t)=>utils.sortAlphabetically({a:e.ancestorTitles.join(" "),b:t.ancestorTitles.join(" "),reversed:!0}))}),t}return e})(e);case"titleasc":return(e=>{if(e){const t=e.sort((e,t)=>utils.sortAlphabetically({a:e.testFilePath,b:t.testFilePath}));return t.forEach(e=>{e.testResults.sort((e,t)=>utils.sortAlphabetically({a:e.ancestorTitles.join(" "),b:t.ancestorTitles.join(" ")}))}),t}return e})(e);default:return e}return e}}}),sorting_1=sorting.sortSuiteResults;class ReportGenerator{constructor(e){this.config=e,this.consoleLogs=null}generate({data:e,ignoreConsole:t}){const s=this.config.getOutputFilepath(),o=this.config.shouldUseCssFile(),n=this.config.shouldGetStylesheetContent(),i=this.config.getAppend();let r=null,l=null;return o&&(r=this.config.getStylesheetFilepath()),(l=n?()=>this.getStylesheetContent():()=>Promise.resolve())().then(t=>this.renderHtmlReport({data:e,stylesheet:t,stylesheetPath:r})).then(e=>i?utils.appendFile({filePath:s,content:e}):utils.writeFile({filePath:s,content:e})).then(()=>utils.logMessage({type:"success",msg:`Report generated (${s})`,ignoreConsole:t})).catch(e=>utils.logMessage({type:"error",msg:e,ignoreConsole:t}))}integrateContentIntoBoilerplate({content:e}){const t=this.config.getBoilerplatePath();return new Promise((s,o)=>utils.getFileContent({filePath:t}).then(t=>s(t.replace("{jesthtmlreporter-content}",e))).catch(e=>o(e)))}getStylesheetContent(){const e=this.config.getStylesheetFilepath();return utils.getFileContent({filePath:e})}renderHtmlReport({data:e,stylesheet:t,stylesheetPath:s}){return new Promise((o,n)=>{if(!e)return n(new Error("Test data missing or malformed"));const i=this.config.getPageTitle(),r=this.getReportBody({data:e,pageTitle:i});if(this.config.getBoilerplatePath())return this.integrateContentIntoBoilerplate({content:r}).then(e=>o(e));const l=utils.createHtmlBase({pageTitle:i,stylesheet:t,stylesheetPath:s}),a=l.ele("body");a.raw(r);const c=this.config.getCustomScriptFilepath();return c&&a.raw(`<script src="${c}"><\/script>`),o(l)})}getReportBody({data:e,pageTitle:t}){const s=xmlbuilder.begin().element("div",{id:"jesthtml-content"}),o=s.ele("header");o.ele("h1",{id:"title"},t);const n=this.config.getLogo();n&&o.ele("img",{id:"logo",src:n});const i=s.ele("div",{id:"metadata-container"}),r=new Date(e.startTime);i.ele("div",{id:"timestamp"},`Start: ${dateformat(r,this.config.getDateFormat())}`),i.ele("div",{id:"summary"},`${e.numTotalTests} tests -- ${e.numPassedTests} passed / ${e.numFailedTests} failed / ${e.numPendingTests} pending`);const l=sorting.sortSuiteResults({testData:e.testResults,sortMethod:this.config.getSort()}),a=this.config.getStatusIgnoreFilter();let c=[];return a&&(c=a.replace(/\s/g,"").toLowerCase().split(",")),l.forEach(e=>{for(let t=e.testResults.length-1;t>=0;t-=1)c.includes(e.testResults[t].status)&&e.testResults.splice(t,1);if(!e.testResults||e.testResults.length<=0)return;const t=s.ele("div",{class:"suite-info"});t.ele("div",{class:"suite-path"},e.testFilePath);const o=(e.perfStats.end-e.perfStats.start)/1e3;t.ele("div",{class:`suite-time${o>5?" warn":""}`},`${o}s`);const n=s.ele("table",{class:"suite-table",cellspacing:"0",cellpadding:"0"});if(e.testResults.forEach(e=>{const t=n.ele("tr",{class:e.status});t.ele("td",{class:"suite"},e.ancestorTitles.join(" > "));const s=t.ele("td",{class:"test"},e.title);if(e.failureMessages&&this.config.shouldIncludeFailureMessages()){const t=s.ele("div",{class:"failureMessages"});e.failureMessages.forEach(e=>{t.ele("pre",{class:"failureMsg"},stripAnsi(e))})}t.ele("td",{class:"result"},"passed"===e.status?`${e.status} in ${e.duration/1e3}s`:e.status)}),this.consoleLogs&&this.consoleLogs.length>0&&this.config.shouldIncludeConsoleLog()){const t=this.consoleLogs.find(t=>t.testFilePath===e.testFilePath);if(t&&t.logs.length>0){const e=s.ele("div",{class:"suite-consolelog"});e.ele("div",{class:"suite-consolelog-header"},"Console Log"),t.logs.forEach(t=>{const s=e.ele("div",{class:"suite-consolelog-item"});s.ele("pre",{class:"suite-consolelog-item-origin"},stripAnsi(t.origin)),s.ele("pre",{class:"suite-consolelog-item-message"},stripAnsi(t.message))})}}}),s}}var reportGenerator=ReportGenerator,config_1=createCommonjsModule(function(e){const t={},s=e=>Object.assign(t,e),o=()=>process.env.JEST_HTML_REPORTER_THEME||t.theme||"defaultTheme",n=()=>Boolean(process.env.JEST_HTML_REPORTER_STYLE_OVERRIDE_PATH)||Boolean(t.styleOverridePath),i=()=>process.env.JEST_HTML_REPORTER_USE_CSS_FILE||t.useCssFile||!1;e.exports={config:t,setup:()=>{try{const e=fs.readFileSync(path.join(process.cwd(),"jesthtmlreporter.config.json"),"utf8");if(e)return s(JSON.parse(e))}catch(e){}try{const e=fs.readFileSync(path.join(process.cwd(),"package.json"),"utf8");if(e)return s(JSON.parse(e)["jest-html-reporter"])}catch(e){}return t},setConfigData:s,getOutputFilepath:()=>{return(process.env.JEST_HTML_REPORTER_OUTPUT_PATH||t.outputPath||path.join(process.cwd(),"test-report.html")).replace(/<rootdir>/gi,".")},getStylesheetFilepath:()=>process.env.JEST_HTML_REPORTER_STYLE_OVERRIDE_PATH||t.styleOverridePath||path.join(__dirname,`../style/${o()}.css`),getHasStyleOverridePath:n,getCustomScriptFilepath:()=>process.env.JEST_HTML_REPORTER_CUSTOM_SCRIPT_PATH||t.customScriptPath||null,getPageTitle:()=>process.env.JEST_HTML_REPORTER_PAGE_TITLE||t.pageTitle||"Test report",getLogo:()=>process.env.JEST_HTML_REPORTER_LOGO||t.logo||null,shouldIncludeFailureMessages:()=>process.env.JEST_HTML_REPORTER_INCLUDE_FAILURE_MSG||t.includeFailureMsg||!1,shouldIncludeConsoleLog:()=>process.env.JEST_HTML_REPORTER_INCLUDE_CONSOLE_LOG||t.includeConsoleLog||!1,shouldUseCssFile:i,shouldGetStylesheetContent:()=>!(n()&&i()),getExecutionTimeWarningThreshold:()=>process.env.JEST_HTML_REPORTER_EXECUTION_TIME_WARNING_THRESHOLD||t.executionTimeWarningThreshold||5,getBoilerplatePath:()=>process.env.JEST_HTML_REPORTER_BOILERPLATE||t.boilerplate||null,getTheme:o,getDateFormat:()=>process.env.JEST_HTML_REPORTER_DATE_FORMAT||t.dateFormat||"yyyy-mm-dd HH:MM:ss",getSort:()=>process.env.JEST_HTML_REPORTER_SORT||t.sort||"default",getStatusIgnoreFilter:()=>process.env.JEST_HTML_REPORTER_STATUS_FILTER||t.statusIgnoreFilter||null,getAppend:()=>process.env.JEST_HTML_REPORTER_APPEND||t.append||!1}}),config_2=config_1.config,config_3=config_1.setup,config_4=config_1.setConfigData,config_5=config_1.getOutputFilepath,config_6=config_1.getStylesheetFilepath,config_7=config_1.getHasStyleOverridePath,config_8=config_1.getCustomScriptFilepath,config_9=config_1.getPageTitle,config_10=config_1.getLogo,config_11=config_1.shouldIncludeFailureMessages,config_12=config_1.shouldIncludeConsoleLog,config_13=config_1.shouldUseCssFile,config_14=config_1.shouldGetStylesheetContent,config_15=config_1.getExecutionTimeWarningThreshold,config_16=config_1.getBoilerplatePath,config_17=config_1.getTheme,config_18=config_1.getDateFormat,config_19=config_1.getSort,config_20=config_1.getStatusIgnoreFilter,config_21=config_1.getAppend;function JestHtmlReporter(e,t){config_1.setup();const s=new reportGenerator(config_1);if(Object.prototype.hasOwnProperty.call(e,"testResults"))return s.generate({data:e}),e;this.jestConfig=e,this.jestOptions=t,this.consoleLogs=[],this.onTestResult=((e,t)=>{t.console&&this.consoleLogs.push({testFilePath:t.testFilePath,logs:t.console})}),this.onRunComplete=((e,t)=>(config_1.setConfigData(this.jestOptions),s.config=config_1,s.consoleLogs=this.consoleLogs,s.generate({data:t})))}var src=JestHtmlReporter;module.exports=src;
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.sortTestResults = (testResults, sortType) => {
|
|
4
|
+
switch (sortType) {
|
|
5
|
+
case "status":
|
|
6
|
+
return sortTestResultsByStatus(testResults);
|
|
7
|
+
default:
|
|
8
|
+
return testResults;
|
|
9
|
+
}
|
|
10
|
+
};
|
|
11
|
+
/**
|
|
12
|
+
* Splits test suites apart based on individual test status and sorts by that status:
|
|
13
|
+
* 1. Pending
|
|
14
|
+
* 2. Failed
|
|
15
|
+
* 3. Passed
|
|
16
|
+
*/
|
|
17
|
+
const sortTestResultsByStatus = (testResults) => {
|
|
18
|
+
const pendingSuites = [];
|
|
19
|
+
const failingSuites = [];
|
|
20
|
+
const passingSuites = [];
|
|
21
|
+
testResults.forEach(result => {
|
|
22
|
+
const pending = [];
|
|
23
|
+
const failed = [];
|
|
24
|
+
const passed = [];
|
|
25
|
+
result.testResults.forEach(x => {
|
|
26
|
+
if (x.status === "pending") {
|
|
27
|
+
pending.push(x);
|
|
28
|
+
}
|
|
29
|
+
else if (x.status === "failed") {
|
|
30
|
+
failed.push(x);
|
|
31
|
+
}
|
|
32
|
+
else {
|
|
33
|
+
passed.push(x);
|
|
34
|
+
}
|
|
35
|
+
});
|
|
36
|
+
if (pending.length) {
|
|
37
|
+
pendingSuites.push({
|
|
38
|
+
...result,
|
|
39
|
+
testResults: pending
|
|
40
|
+
});
|
|
41
|
+
}
|
|
42
|
+
if (failed.length) {
|
|
43
|
+
failingSuites.push({
|
|
44
|
+
...result,
|
|
45
|
+
testResults: failed
|
|
46
|
+
});
|
|
47
|
+
}
|
|
48
|
+
if (passed.length) {
|
|
49
|
+
pendingSuites.push({
|
|
50
|
+
...result,
|
|
51
|
+
testResults: failed
|
|
52
|
+
});
|
|
53
|
+
}
|
|
54
|
+
});
|
|
55
|
+
return [].concat(pendingSuites, failingSuites, passingSuites);
|
|
56
|
+
};
|
|
57
|
+
//# sourceMappingURL=sortingMethods.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sortingMethods.js","sourceRoot":"","sources":["../src/sortingMethods.ts"],"names":[],"mappings":";;AAGa,QAAA,eAAe,GAAG,CAC7B,WAA4C,EAC5C,QAAkC,EACD,EAAE;IACnC,QAAQ,QAAQ,EAAE;QAChB,KAAK,QAAQ;YACX,OAAO,uBAAuB,CAAC,WAAW,CAAC,CAAC;QAC9C;YACE,OAAO,WAAW,CAAC;KACtB;AACH,CAAC,CAAC;AAEF;;;;;GAKG;AACH,MAAM,uBAAuB,GAAG,CAC9B,WAA4C,EAC5C,EAAE;IACF,MAAM,aAAa,GAAoC,EAAE,CAAC;IAC1D,MAAM,aAAa,GAAoC,EAAE,CAAC;IAC1D,MAAM,aAAa,GAAoC,EAAE,CAAC;IAE1D,WAAW,CAAC,OAAO,CAAC,MAAM,CAAC,EAAE;QAC3B,MAAM,OAAO,GAAsB,EAAE,CAAC;QACtC,MAAM,MAAM,GAAsB,EAAE,CAAC;QACrC,MAAM,MAAM,GAAsB,EAAE,CAAC;QAErC,MAAM,CAAC,WAAW,CAAC,OAAO,CAAC,CAAC,CAAC,EAAE;YAC7B,IAAI,CAAC,CAAC,MAAM,KAAK,SAAS,EAAE;gBAC1B,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;aACjB;iBAAM,IAAI,CAAC,CAAC,MAAM,KAAK,QAAQ,EAAE;gBAChC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;aAChB;iBAAM;gBACL,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;aAChB;QACH,CAAC,CAAC,CAAC;QAEH,IAAI,OAAO,CAAC,MAAM,EAAE;YAClB,aAAa,CAAC,IAAI,CAAC;gBACjB,GAAG,MAAM;gBACT,WAAW,EAAE,OAAO;aACrB,CAAC,CAAC;SACJ;QACD,IAAI,MAAM,CAAC,MAAM,EAAE;YACjB,aAAa,CAAC,IAAI,CAAC;gBACjB,GAAG,MAAM;gBACT,WAAW,EAAE,MAAM;aACpB,CAAC,CAAC;SACJ;QACD,IAAI,MAAM,CAAC,MAAM,EAAE;YACjB,aAAa,CAAC,IAAI,CAAC;gBACjB,GAAG,MAAM;gBACT,WAAW,EAAE,MAAM;aACpB,CAAC,CAAC;SACJ;IACH,CAAC,CAAC,CAAC;IAEH,OAAO,EAAE,CAAC,MAAM,CAAC,aAAa,EAAE,aAAa,EAAE,aAAa,CAAC,CAAC;AAChE,CAAC,CAAC"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "jest-html-reporter",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.8.2",
|
|
4
4
|
"description": "Jest test results processor for generating a summary in HTML",
|
|
5
5
|
"main": "dist/main",
|
|
6
6
|
"unpkg": "dist/main.min.js",
|
|
@@ -39,20 +39,20 @@
|
|
|
39
39
|
},
|
|
40
40
|
"dependencies": {
|
|
41
41
|
"dateformat": "3.0.2",
|
|
42
|
-
"mkdirp": "0.5.
|
|
42
|
+
"mkdirp": "0.5.3",
|
|
43
43
|
"strip-ansi": "3.0.1",
|
|
44
44
|
"xmlbuilder": "13.0.2"
|
|
45
45
|
},
|
|
46
46
|
"peerDependencies": {
|
|
47
|
-
"jest": "19.x -
|
|
47
|
+
"jest": "19.x - 25.x"
|
|
48
48
|
},
|
|
49
49
|
"devDependencies": {
|
|
50
50
|
"eslint": "^4.19.1",
|
|
51
51
|
"eslint-config-airbnb-base": "^12.1.0",
|
|
52
|
-
"eslint-plugin-import": "^2.
|
|
52
|
+
"eslint-plugin-import": "^2.20.1",
|
|
53
53
|
"istanbul-api": "1.2.2",
|
|
54
54
|
"istanbul-reports": "1.1.4",
|
|
55
|
-
"jest": "^
|
|
55
|
+
"jest": "^25.1.0",
|
|
56
56
|
"rollup": "^0.55.5",
|
|
57
57
|
"rollup-plugin-commonjs": "^8.4.1",
|
|
58
58
|
"rollup-plugin-node-resolve": "^3.4.0",
|
package/style/darkTheme.css
CHANGED
package/style/defaultTheme.css
CHANGED