cucumber-html
Advanced tools
Comparing version 0.0.0 to 0.1.0
@@ -6,3 +6,3 @@ { | ||
"description": "Cross platform HTML formatter for all implementations of Cucumber", | ||
"version": "0.0.0", | ||
"version": "0.1.0", | ||
"homepage": "https://github.com/cucumber/cucumber-html", | ||
@@ -9,0 +9,0 @@ "repository": { |
var Cucumber = {}; | ||
//See http://www.w3.org/TR/html4/types.html#type-id | ||
/** | ||
* Generates an unique id so we can find statements and mark them after execution | ||
*/ | ||
Cucumber.encodeId = function(uri, line) { | ||
return 'id_' + uri.replace(/(:|\.|\/)/g,'_') + '_' + line; | ||
} | ||
Cucumber.DOMFormatter = function(rootNode) { | ||
var rootNode = rootNode; | ||
var featureElementsNode; | ||
var scenarioElementsNode; | ||
var currentNode; | ||
var currentUri; | ||
var currentFeature; | ||
var currentElement; | ||
var currentSteps; | ||
var currentStepIndex; | ||
var currentStep; | ||
this.uri = function(uri) { | ||
currentUri = uri; | ||
} | ||
}; | ||
this.feature = function(feature) { | ||
prepareAndPrintCurrentNode(feature, {parentNode: rootNode, className: 'feature', heading: '<h1>'}); | ||
featureElementsNode = currentNode.find('.childrenElements'); | ||
featureElementsNode.addClass('featureElements'); | ||
} | ||
currentFeature = blockElement(rootNode, feature, 'feature'); | ||
}; | ||
this.background = function(background) { | ||
prepareAndPrintCurrentNode(background, {parentNode: featureElementsNode, className: 'background', heading: '<h2>'}); | ||
prepareScenarioElementsNode(); | ||
} | ||
currentElement = featureElement(background, 'background'); | ||
currentStepIndex = 1; | ||
}; | ||
this.scenario = function(scenario) { | ||
prepareAndPrintCurrentNode(scenario, {parentNode: featureElementsNode, className: 'scenario', heading: '<h2>'}); | ||
prepareScenarioElementsNode(); | ||
} | ||
currentElement = featureElement(scenario, 'scenario'); | ||
currentStepIndex = 1; | ||
}; | ||
this.scenarioOutline = function(outline) { | ||
this.scenario(outline); | ||
currentNode.addClass('outline'); | ||
} | ||
this.scenarioOutline = function(scenarioOutline) { | ||
currentElement = featureElement(scenarioOutline, 'scenario_outline'); | ||
currentStepIndex = 1; | ||
}; | ||
this.step = function(step) { | ||
prepareAndPrintCurrentNode(step, {parentNode: scenarioElementsNode, className: 'step', heading: '<h3>'}); | ||
currentNode.attr('id', step.id); | ||
if (hasExamples(step)) { | ||
printExamples(step.multiline_arg.value, false); | ||
var stepElement = $('#cucumber-templates .step').clone(); | ||
stepElement.appendTo(currentSteps); | ||
populate(stepElement, step, 'step'); | ||
if (step.doc_string) { | ||
docString = $('#cucumber-templates .doc_string').clone(); | ||
docString.appendTo(stepElement); | ||
// TODO: use a syntax highlighter based on the content_type | ||
docString.text(step.doc_string.value); | ||
} | ||
} | ||
if (step.rows) { | ||
dataTable = $('#cucumber-templates .data_table').clone(); | ||
dataTable.appendTo(stepElement); | ||
var tBody = dataTable.find('tbody'); | ||
$.each(step.rows, function(index, row) { | ||
var tr = $('<tr></tr>').appendTo(tBody); | ||
$.each(row.cells, function(index, cell) { | ||
var td = $('<td>' + cell + '</td>').appendTo(tBody); | ||
}); | ||
}); | ||
} | ||
}; | ||
this.examples = function(examples) { | ||
prepareAndPrintCurrentNode(examples, {parentNode: featureElementsNode, className: 'exampleBlock', heading: '<h2>'}); | ||
printExamples(examples.rows, true); | ||
} | ||
var examplesElement = blockElement(currentElement.children('details'), examples, 'examples'); | ||
var examplesTable = $('#cucumber-templates .examples_table').clone(); | ||
examplesTable.appendTo(examplesElement.children('details')); | ||
var prepareScenarioElementsNode = function() { | ||
scenarioElementsNode = currentNode.find('.childrenElements'); | ||
scenarioElementsNode.addClass('steps'); | ||
} | ||
$.each(examples.rows, function(index, row) { | ||
var parent = index == 0 ? examplesTable.find('thead') : examplesTable.find('tbody'); | ||
var tr = $('<tr></tr>').appendTo(parent); | ||
$.each(row.cells, function(index, cell) { | ||
var td = $('<td>' + cell + '</td>').appendTo(tr); | ||
}); | ||
}); | ||
}; | ||
var prepareAndPrintCurrentNode = function(statement, nodeInfo) { | ||
currentNode = $('#templates .blockelement').clone().appendTo(nodeInfo.parentNode); | ||
currentNode.addClass(nodeInfo.className); | ||
printStatement(statement, nodeInfo.heading); | ||
this.match = function(match) { | ||
currentStep = currentSteps.find('li:nth-child(' + currentStepIndex + ')'); | ||
currentStepIndex++; | ||
}; | ||
this.result = function(result) { | ||
currentStep.addClass(result.status); | ||
currentElement.addClass(result.status); | ||
var isLastStep = currentSteps.find('li:nth-child(' + currentStepIndex + ')').length == 0; | ||
if(isLastStep) { | ||
if(currentSteps.find('.failed').length == 0) { | ||
// No failed steps. Collapse it. | ||
currentElement.find('details').removeAttr('open'); | ||
} | ||
} | ||
}; | ||
this.embedding = function(mimeType, data) { | ||
if(mimeType.match(/^image\//)) { | ||
currentStep.append("<div><img src='" + data + "'></div>"); | ||
} | ||
} | ||
var hasExamples = function(step) { | ||
return step.multiline_arg !== undefined && step.multiline_arg.type === 'table'; | ||
function featureElement(statement, itemtype) { | ||
var e = blockElement(currentFeature.children('details'), statement, itemtype); | ||
currentSteps = $('#cucumber-templates .steps').clone(); | ||
currentSteps.appendTo(e.children('details')); | ||
return e; | ||
} | ||
var printExamples = function(examples, hasHeader) { | ||
var table = $('#templates .examples').clone().appendTo(currentNode.find('.childrenElements')); | ||
$.each(examples, function(index, example) { | ||
if (index === 0 && hasHeader) { | ||
node = table.find('thead'); | ||
} else { | ||
node = table.find('tbody'); | ||
} | ||
printExampleRow(node, example); | ||
}); | ||
function blockElement(parent, statement, itemtype) { | ||
var e = $('#cucumber-templates .blockelement').clone(); | ||
e.appendTo(parent); | ||
return populate(e, statement, itemtype); | ||
} | ||
var printExampleRow = function(node, example) { | ||
var tr = $('<tr>').appendTo(node); | ||
tr.attr('id', Cucumber.encodeId(currentUri, example.line)); | ||
tr.addClass('exampleRow'); | ||
$.each(example.cells,function(index, cell) { | ||
var td = $('<td>').appendTo(tr); | ||
td.addClass('exampleCell'); | ||
td.text(cell); | ||
}); | ||
function populate(e, statement, itemtype) { | ||
populateTags(e, statement.tags); | ||
populateComments(e, statement.comments); | ||
e.find('.keyword').text(statement.keyword); | ||
e.find('.name').text(statement.name); | ||
e.find('.description').text(statement.description); | ||
e.attr('itemtype', 'http://cukes.info/microformat/' + itemtype); | ||
e.addClass(itemtype); | ||
return e; | ||
} | ||
var printStatement = function(statement, heading) { | ||
currentNode.attr('id', Cucumber.encodeId(currentUri, statement.line)); | ||
currentNode.find('.keyword').text(statement.keyword); | ||
currentNode.find('.name').text(statement.name); | ||
if (statement.description !== undefined && $.trim(statement.description) !== '') { | ||
currentNode.find('.description').text(statement.description); | ||
} else { | ||
currentNode.find('.description').remove(); | ||
function populateComments(e, comments) { | ||
if (comments !== undefined) { | ||
var commentsNode = $('#cucumber-templates .comments').clone().prependTo(e.find('.header')); | ||
$.each(comments, function(index, comment) { | ||
var commentNode = $('#cucumber-templates .comment').clone().appendTo(commentsNode); | ||
commentNode.text(comment.value); | ||
}); | ||
} | ||
currentNode.find('header').wrapInner(heading); | ||
} | ||
} | ||
Cucumber.Reporter = function() { | ||
var idMatched; | ||
this.result = function(result) { | ||
$('#'+idMatched).addClass(result.status); | ||
if (result.error_message !== undefined) { | ||
$('<pre>').appendTo($('#'+idMatched)).text(result.error_message); | ||
function populateTags(e, tags) { | ||
if (tags !== undefined) { | ||
var tagsNode = $('#cucumber-templates .tags').clone().prependTo(e.find('.header')); | ||
$.each(tags, function(index, tag) { | ||
var tagNode = $('#cucumber-templates .tag').clone().appendTo(tagsNode); | ||
tagNode.text(tag.name); | ||
}); | ||
} | ||
} | ||
this.match = function(match) { | ||
idMatched = Cucumber.encodeId(match.uri, match.step.line); | ||
} | ||
} | ||
}; | ||
@@ -120,0 +143,0 @@ if (typeof module !== 'undefined') { |
$(document).ready(function() { | ||
var formatter = new Cucumber.DOMFormatter($('body')); | ||
var formatter = new Cucumber.DOMFormatter($('.cucumber-report')); | ||
formatter.uri('report.feature'); | ||
formatter.feature({keyword:'Feature', name:'Generating html report', line:2, description: 'It could be useful to have an html report to facilitate documentation reading.'}); | ||
formatter.background({keyword:'Background', name:'Setting up the context', line:3, description: 'These steps will be executed before each scenario.'}); | ||
formatter.step({keyword:'Given', name:'I have a background', line:4}); | ||
formatter.step({keyword:'And', name:'I set some context', line: 5}); | ||
formatter.scenario({keyword:'Scenario', name: 'Creating a simple report', line: 6}); | ||
formatter.step({keyword:'Given', name:'I have a feature', line: 7}); | ||
formatter.step({keyword:'When', name:'I format it', line: 8}); | ||
formatter.step({keyword:'Then', name:'It should look pretty', line: 9}); | ||
formatter.step({keyword:'And', name:'It should show tables', line: 10, multiline_arg:{type:'table', value: [{cells:['name', 'price'], line: 11}, {cells:['milk', '9'], line: 12}]}}); | ||
formatter.scenarioOutline({keyword:'Scenario Outline', name: 'Scenario with examples', description:'It should be good to format outlined arguments.', line: 13}); | ||
formatter.step({keyword:'Given', name:'I have a <name> which costs <price>', line: 14}); | ||
formatter.examples({description:'', name:'Some good examples', keyword:'Examples', line: 15, rows:[{cells:['name', 'price'], line:16}, {cells:['milk', '9'], line:17}, {cells:['bread', '7'], line:18}, {cells:['soap', '5'], line:19}]}) | ||
var reporter = new Cucumber.Reporter(); | ||
reporter.match({uri:'report.feature', step:{line:4}}); | ||
reporter.result({status:'passed', duration: 0}); | ||
reporter.match({uri:'report.feature', step:{line:5}}); | ||
reporter.result({status:'passed', duration: 0}); | ||
reporter.match({uri:'report.feature', step:{line:7}}); | ||
reporter.result({status:'passed', duration: 0}); | ||
reporter.match({uri:'report.feature', step:{line:8}}); | ||
reporter.result({status:'failed', error_message:'something went wrong...', duration: 0}); | ||
reporter.match({uri:'report.feature', step:{line:9}}); | ||
reporter.result({status:'skipped', duration: 0}); | ||
reporter.match({uri:'report.feature', step:{line:10}}); | ||
reporter.result({status:'passed', duration: 0}); | ||
reporter.match({uri:'report.feature', step:{line:17}}); | ||
reporter.result({status:'passed', duration: 0}); | ||
reporter.match({uri:'report.feature', step:{line:18}}); | ||
reporter.result({status:'passed', duration: 0}); | ||
reporter.match({uri:'report.feature', step:{line:19}}); | ||
reporter.result({status:'failed', error_message:'I didn\'t do it.', duration: 0}); | ||
formatter.feature({ | ||
comments: [ | ||
{value: "# A comment"}, | ||
{value: "# Another comment"}, | ||
], | ||
keyword:'Feature', | ||
name:'Generating html report', | ||
description: 'It could be useful to have an html report to facilitate documentation reading.', | ||
line:2 | ||
}); | ||
formatter.background({ | ||
comments: [ | ||
{value: "# Background comment"} | ||
], | ||
keyword:'Background', | ||
name:'Setting up the context', | ||
line:3, | ||
description: 'These steps will be executed before each scenario.' | ||
}); | ||
formatter.step({keyword:'Given ', name:'I have a background', line:4}); | ||
formatter.step({keyword:'And ', name:'I set some context', line: 5}); | ||
formatter.match({uri:'report.feature'}); | ||
formatter.result({status:'passed', duration: 0}); | ||
formatter.match({uri:'report.feature'}); | ||
formatter.result({status:'passed', duration: 0}); | ||
formatter.scenario({"tags":[{"name":"@foo","line":3},{"name":"@bar","line":4},{"name":"@doh","line":5}], keyword:'Scenario', name: 'Creating a simple report', line: 6}); | ||
formatter.step({keyword:'Given ', name:'I have a feature', line: 7, doc_string:{value: "A\ndoc string\non several lines", content_type:"text/plain", line:8}}); | ||
formatter.step({keyword:'When ', name:'I format it', line: 11}); | ||
formatter.step({keyword:'Then ', name:'It should look pretty', line: 12}); | ||
formatter.step({keyword:'And ', name:'It should show tables', line: 13, rows: [{cells:['name', 'price'], line: 14}, {cells:['milk', '9'], line: 15}]}); | ||
formatter.match({uri:'report.feature'}); | ||
formatter.result({status:'passed', duration: 0}); | ||
formatter.match({uri:'report.feature'}); | ||
formatter.result({status:'failed', error_message:'something went wrong...', duration: 0}); | ||
formatter.embedding('image/png', 'bubble_256x256.png'); | ||
formatter.match({uri:'report.feature'}); | ||
formatter.result({status:'undefined', duration: 0}); | ||
formatter.match({uri:'report.feature'}); | ||
formatter.result({status:'skipped', duration: 0}); | ||
formatter.scenarioOutline({keyword:'Scenario Outline', name: 'Scenario with examples', description:'It should be good to format outlined arguments.', line: 16}); | ||
formatter.step({keyword:'Given ', name:'I have a <name> which costs <price>', line: 17}); | ||
formatter.examples({description:'', name:'Some good examples', keyword:'Examples', line: 18, rows:[{cells:['name', 'price'], line:19}, {cells:['milk', '9'], line:20}, {cells:['bread', '7'], line:21}, {cells:['soap', '5'], line:22}]}) | ||
formatter.match({uri:'report.feature'}); | ||
formatter.result({status:'passed', duration: 0}); | ||
formatter.match({uri:'report.feature'}); | ||
formatter.result({status:'passed', duration: 0}); | ||
formatter.match({uri:'report.feature'}); | ||
formatter.result({status:'failed', error_message:'I didn\'t do it.', duration: 0}); | ||
}); |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
121335
11
493