snapdragon 1.0.0 → 2.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitmodules +0 -3
- data/.ruby-version +1 -1
- data/ChangeLog.markdown +7 -2
- data/lib/jasmine/MIT.LICENSE +20 -0
- data/lib/jasmine/boot.js +181 -0
- data/lib/jasmine/console.js +160 -0
- data/lib/jasmine/jasmine-html.js +359 -0
- data/lib/jasmine/jasmine.css +55 -0
- data/lib/jasmine/jasmine.js +2402 -0
- data/lib/jasmine/jasmine_favicon.png +0 -0
- data/lib/jasmine_v1/MIT.LICENSE +20 -0
- data/lib/{jasmine/lib/jasmine-core → jasmine_v1}/jasmine-html.js +0 -0
- data/lib/{jasmine/lib/jasmine-core → jasmine_v1}/jasmine.css +0 -0
- data/lib/{jasmine/lib/jasmine-core → jasmine_v1}/jasmine.js +0 -0
- data/lib/snapdragon/command_line_parser.rb +7 -3
- data/lib/snapdragon/resources/SnapdragonConsoleReporter.js +129 -128
- data/lib/snapdragon/resources/SnapdragonConsoleReporter_v1.js +162 -0
- data/lib/snapdragon/resources/SnapdragonJUnitReporter.js +142 -131
- data/lib/snapdragon/resources/SnapdragonJUnitReporter_v1.js +158 -0
- data/lib/snapdragon/suite.rb +4 -0
- data/lib/snapdragon/version.rb +1 -1
- data/lib/snapdragon/views/run.erb +21 -44
- data/lib/snapdragon/views/run_v1.erb +60 -0
- data/lib/snapdragon/web_application.rb +11 -3
- data/snapdragon.gemspec +7 -7
- data/spec/lib/snapdragon/cli_application_spec.rb +20 -19
- data/spec/lib/snapdragon/command_line_parser_spec.rb +44 -20
- data/spec/lib/snapdragon/path_spec.rb +21 -20
- data/spec/lib/snapdragon/spec_directory_spec.rb +2 -1
- data/spec/lib/snapdragon/spec_file_spec.rb +2 -1
- data/spec/lib/snapdragon/suite_spec.rb +54 -44
- data/spec/spec_helper.rb +7 -0
- metadata +51 -48
- data/lib/jasmine/lib/jasmine-core/example/SpecRunner.html +0 -54
- data/lib/jasmine/lib/jasmine-core/example/spec/PlayerSpec.js +0 -58
- data/lib/jasmine/lib/jasmine-core/example/spec/SpecHelper.js +0 -9
- data/lib/jasmine/lib/jasmine-core/example/src/Player.js +0 -22
- data/lib/jasmine/lib/jasmine-core/example/src/Song.js +0 -7
- data/lib/jasmine/lib/jasmine-core/json2.js +0 -478
- data/lib/jasmine/lib/jasmine-core/version.rb +0 -6
- data/lib/snapdragon/resources/.gitkeep +0 -0
@@ -1,158 +1,169 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
if (typeof jasmine == 'undefined') {
|
8
|
-
throw new Error("jasmine library does not exist in global namespace!");
|
1
|
+
function getJasmineRequireObj() {
|
2
|
+
if (typeof module !== "undefined" && module.exports) {
|
3
|
+
return exports;
|
4
|
+
} else {
|
5
|
+
window.jasmineRequire = window.jasmineRequire || {};
|
6
|
+
return window.jasmineRequire;
|
9
7
|
}
|
8
|
+
}
|
10
9
|
|
11
|
-
|
12
|
-
|
13
|
-
|
10
|
+
getJasmineRequireObj().console = function(jRequire, j$) {
|
11
|
+
j$.SnapdragonJUnitReporter = jRequire.SnapdragonJUnitReporter();
|
12
|
+
};
|
14
13
|
|
15
|
-
|
16
|
-
function pad(n) { return n < 10 ? '0'+n : n; }
|
14
|
+
getJasmineRequireObj().SnapdragonJUnitReporter = function() {
|
17
15
|
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
pad(d.getMinutes()) + ':' +
|
23
|
-
pad(d.getSeconds());
|
24
|
-
}
|
16
|
+
var noopTimer = {
|
17
|
+
start: function(){},
|
18
|
+
elapsed: function(){ return 0; }
|
19
|
+
};
|
25
20
|
|
26
|
-
function
|
27
|
-
|
28
|
-
|
21
|
+
return function(options) {
|
22
|
+
var print = options.print || function(msg) {console.log(msg);},
|
23
|
+
onComplete = options.onComplete || function() {},
|
24
|
+
timer = options.timer || new jasmine.Timer() || noopTimer,
|
25
|
+
suites = {},
|
26
|
+
specs = [],
|
27
|
+
specStartTime;
|
29
28
|
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
.replace(/\>/g, ">")
|
34
|
-
.replace(/\"/g, """)
|
35
|
-
.replace(/\'/g, "'");
|
36
|
-
}
|
29
|
+
this.jasmineStarted = function() {
|
30
|
+
timer.start();
|
31
|
+
};
|
37
32
|
|
38
|
-
|
39
|
-
|
40
|
-
|
33
|
+
this.jasmineDone = function() {
|
34
|
+
outputToXml();
|
35
|
+
signalCapybaraTestsFinishedRunning();
|
36
|
+
};
|
41
37
|
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
this.print("<testsuites>");
|
46
|
-
},
|
38
|
+
this.suiteStarted = function(result) {
|
39
|
+
specs = [];
|
40
|
+
suites[result.id] = {suite: result, timestamp: new Date(), duration: 0, specs: specs};
|
47
41
|
|
48
|
-
|
49
|
-
spec.startTime = new Date();
|
42
|
+
};
|
50
43
|
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
44
|
+
this.suiteDone = function(result) {
|
45
|
+
suites[result.id].duration = (new Date() - suites[result.id].timestamp) / 1000;
|
46
|
+
};
|
47
|
+
|
48
|
+
this.specStarted = function(result) {
|
49
|
+
specStartTime = new Date();
|
50
|
+
};
|
51
|
+
|
52
|
+
this.specDone = function(result) {
|
53
|
+
var elapsedTime = (new Date() - specStartTime) / 1000;
|
54
|
+
specs.push({spec: result, duration: elapsedTime});
|
55
|
+
};
|
56
|
+
|
57
|
+
return this;
|
58
|
+
|
59
|
+
function outputToXml() {
|
60
|
+
var output = [];
|
61
|
+
|
62
|
+
output.push("<?xml version=\"1.0\" encoding=\"UTF-8\" ?>");
|
63
|
+
output.push("<testsuites>");
|
64
|
+
|
65
|
+
for (var suiteId in suites) {
|
66
|
+
output.push(getOutputForEachSuite(suites[suiteId]));
|
64
67
|
}
|
65
68
|
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
69
|
+
output.push("</testsuites>");
|
70
|
+
|
71
|
+
print(output.join(getNewLine()));
|
72
|
+
}
|
73
|
+
|
74
|
+
function getOutputForEachSuite(data) {
|
75
|
+
var suite = data.suite,
|
76
|
+
specs = data.specs,
|
77
|
+
failedSpecsCount = 0,
|
78
|
+
newLineChar = "",
|
79
|
+
output = [];
|
80
|
+
|
81
|
+
if (specs.length > 0) {
|
82
|
+
failedSpecsCount = getFailedSpecsCount(specs);
|
83
|
+
newLineChar = getNewLine();
|
84
|
+
|
85
|
+
for (var i = 0, length = specs.length; i < length; i++) {
|
86
|
+
output.push(getOutputForEachSpec(specs[i]));
|
77
87
|
}
|
78
88
|
}
|
79
|
-
if (failure) {
|
80
|
-
spec.output += failure;
|
81
|
-
}
|
82
|
-
spec.output += "</testcase>";
|
83
|
-
},
|
84
|
-
|
85
|
-
reportSuiteResults: function(suite) {
|
86
|
-
var results = suite.results();
|
87
|
-
var specs = suite.specs();
|
88
|
-
// for JUnit results, let's only include directly failed tests (not nested suites')
|
89
|
-
var failedCount = 0;
|
90
|
-
|
91
|
-
suite.status = results.passed() ? 'Passed.' : 'Failed.';
|
92
|
-
if (results.totalCount === 0) { // todo: change this to check results.skipped
|
93
|
-
suite.status = 'Skipped.';
|
94
|
-
}
|
95
89
|
|
96
|
-
|
97
|
-
|
98
|
-
suite.startTime = suite.startTime || new Date();
|
99
|
-
suite.duration = elapsed(suite.startTime, new Date());
|
90
|
+
output.unshift(["<testsuite name=\"", escapeInvalidXmlChars(suite.fullName), "\" errors=\"0\" tests=\"", specs.length, "\" failures=\"", failedSpecsCount, "\" time=\"", data.duration, "\" timestamp=\"", dateToISOString(data.timestamp), "\">"].join(""));
|
91
|
+
output.push("</testsuite>");
|
100
92
|
|
101
|
-
|
102
|
-
|
103
|
-
}
|
104
|
-
this.print('<testsuite name="' + this.getFullName(suite) +
|
105
|
-
'" errors="0" tests="' + specs.length + '" failures="' + failedCount +
|
106
|
-
'" time="' + suite.duration + '" timestamp="' + ISODateString(suite.startTime) + '">');
|
107
|
-
for (var i = 0; i < specs.length; i++) {
|
108
|
-
this.print(specs[i].output);
|
109
|
-
}
|
110
|
-
this.print("</testsuite>");
|
111
|
-
},
|
93
|
+
return output.join(newLineChar);
|
94
|
+
}
|
112
95
|
|
113
|
-
|
114
|
-
|
115
|
-
|
116
|
-
|
96
|
+
function getOutputForEachSpec(data) {
|
97
|
+
var spec = data.spec,
|
98
|
+
newLineChar = "",
|
99
|
+
output = [];
|
117
100
|
|
118
|
-
|
119
|
-
|
120
|
-
|
121
|
-
|
122
|
-
|
123
|
-
|
124
|
-
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
|
129
|
-
|
101
|
+
if (spec.status === "pending") {
|
102
|
+
output.push("<skipped />");
|
103
|
+
newLineChar = getNewLine();
|
104
|
+
} else if (spec.status === "failed") {
|
105
|
+
var failures = spec.failedExpectations;
|
106
|
+
|
107
|
+
for (var i = 0, length = failures.length; i < length; i++) {
|
108
|
+
var failure = failures[i];
|
109
|
+
|
110
|
+
output.push(["<failure type=\"expect\" message=\"", escapeInvalidXmlChars(failure.message), "\">"].join(""));
|
111
|
+
output.push(escapeInvalidXmlChars(trimStackTrace(failure.stack)));
|
112
|
+
output.push("</failure>");
|
130
113
|
}
|
131
|
-
}
|
132
|
-
else {
|
133
|
-
fullName = suite.getFullName();
|
134
|
-
}
|
135
114
|
|
136
|
-
|
137
|
-
if (isFilename) {
|
138
|
-
return fullName.replace(/[^\w]/g, "");
|
115
|
+
newLineChar = getNewLine();
|
139
116
|
}
|
140
|
-
return escapeInvalidXmlChars(fullName);
|
141
|
-
},
|
142
117
|
|
143
|
-
|
144
|
-
|
145
|
-
|
118
|
+
output.unshift(["<testcase classname=\"", escapeInvalidXmlChars(spec.fullName), "\" name=\"", escapeInvalidXmlChars(spec.description), "\" time=\"", data.duration, "\">"].join(""));
|
119
|
+
output.push("</testcase>");
|
120
|
+
|
121
|
+
return output.join(newLineChar);
|
122
|
+
}
|
123
|
+
|
124
|
+
function getNewLine() {
|
125
|
+
return "\n";
|
126
|
+
}
|
146
127
|
|
147
|
-
|
148
|
-
var
|
128
|
+
function getFailedSpecsCount(specs) {
|
129
|
+
var counter = 0;
|
149
130
|
|
150
|
-
|
151
|
-
|
131
|
+
for (var i = 0, length = specs.length; i < length; i++) {
|
132
|
+
if (specs[i].spec.status === "failed") {
|
133
|
+
counter++;
|
134
|
+
}
|
152
135
|
}
|
136
|
+
|
137
|
+
return counter;
|
153
138
|
}
|
154
|
-
};
|
155
139
|
|
156
|
-
|
157
|
-
|
158
|
-
|
140
|
+
function dateToISOString(d) {
|
141
|
+
function pad(n) {return n < 10 ? "0"+n : n;}
|
142
|
+
|
143
|
+
return d.getFullYear() + "-" +
|
144
|
+
pad(d.getMonth()+1) + "-" +
|
145
|
+
pad(d.getDate()) + "T" +
|
146
|
+
pad(d.getHours()) + ":" +
|
147
|
+
pad(d.getMinutes()) + ":" +
|
148
|
+
pad(d.getSeconds());
|
149
|
+
}
|
150
|
+
|
151
|
+
function escapeInvalidXmlChars(str) {
|
152
|
+
return str.replace(/\&/g, "&")
|
153
|
+
.replace(/</g, "<")
|
154
|
+
.replace(/\>/g, ">")
|
155
|
+
.replace(/\"/g, """)
|
156
|
+
.replace(/\"/g, "'");
|
157
|
+
}
|
158
|
+
|
159
|
+
function trimStackTrace(stackTraceString) {
|
160
|
+
return stackTraceString.replace(/\s*at\s(?:\w+\s)?\(?http:\/\/127.0.0.1:\d+\/jasmine\/(?:jasmine|boot)\.js:\d+\)?/g, "");
|
161
|
+
}
|
162
|
+
|
163
|
+
function signalCapybaraTestsFinishedRunning() {
|
164
|
+
var div = document.createElement('div');
|
165
|
+
div.id = 'testscomplete';
|
166
|
+
document.body.appendChild(div);
|
167
|
+
}
|
168
|
+
}
|
169
|
+
};
|
@@ -0,0 +1,158 @@
|
|
1
|
+
/*
|
2
|
+
* This is the junit reporter provided in the jasmine-reporters project
|
3
|
+
* available at https://github.com/larrymyers/jasmine-reporters
|
4
|
+
*/
|
5
|
+
(function() {
|
6
|
+
|
7
|
+
if (typeof jasmine == 'undefined') {
|
8
|
+
throw new Error("jasmine library does not exist in global namespace!");
|
9
|
+
}
|
10
|
+
|
11
|
+
function elapsed(startTime, endTime) {
|
12
|
+
return (endTime - startTime)/1000;
|
13
|
+
}
|
14
|
+
|
15
|
+
function ISODateString(d) {
|
16
|
+
function pad(n) { return n < 10 ? '0'+n : n; }
|
17
|
+
|
18
|
+
return d.getFullYear() + '-' +
|
19
|
+
pad(d.getMonth()+1) + '-' +
|
20
|
+
pad(d.getDate()) + 'T' +
|
21
|
+
pad(d.getHours()) + ':' +
|
22
|
+
pad(d.getMinutes()) + ':' +
|
23
|
+
pad(d.getSeconds());
|
24
|
+
}
|
25
|
+
|
26
|
+
function trim(str) {
|
27
|
+
return str.replace(/^\s+/, "" ).replace(/\s+$/, "" );
|
28
|
+
}
|
29
|
+
|
30
|
+
function escapeInvalidXmlChars(str) {
|
31
|
+
return str.replace(/\&/g, "&")
|
32
|
+
.replace(/</g, "<")
|
33
|
+
.replace(/\>/g, ">")
|
34
|
+
.replace(/\"/g, """)
|
35
|
+
.replace(/\'/g, "'");
|
36
|
+
}
|
37
|
+
|
38
|
+
var JUnitXmlReporter = function() {
|
39
|
+
this.useDotNotation = true;
|
40
|
+
};
|
41
|
+
|
42
|
+
JUnitXmlReporter.prototype = {
|
43
|
+
reportRunnerStarting: function() {
|
44
|
+
this.print('<?xml version="1.0" encoding="UTF-8" ?>');
|
45
|
+
this.print("<testsuites>");
|
46
|
+
},
|
47
|
+
|
48
|
+
reportSpecStarting: function(spec) {
|
49
|
+
spec.startTime = new Date();
|
50
|
+
|
51
|
+
if (!spec.suite.startTime) {
|
52
|
+
spec.suite.startTime = spec.startTime;
|
53
|
+
}
|
54
|
+
},
|
55
|
+
|
56
|
+
reportSpecResults: function(spec) {
|
57
|
+
var results = spec.results();
|
58
|
+
spec.didFail = !results.passed();
|
59
|
+
spec.duration = elapsed(spec.startTime, new Date());
|
60
|
+
spec.output = '<testcase classname="' + this.getFullName(spec.suite) +
|
61
|
+
'" name="' + escapeInvalidXmlChars(spec.description) + '" time="' + spec.duration + '">';
|
62
|
+
if(results.skipped) {
|
63
|
+
spec.output = spec.output + "<skipped />";
|
64
|
+
}
|
65
|
+
|
66
|
+
var failure = "";
|
67
|
+
var failures = 0;
|
68
|
+
var resultItems = results.getItems();
|
69
|
+
for (var i = 0; i < resultItems.length; i++) {
|
70
|
+
var result = resultItems[i];
|
71
|
+
|
72
|
+
if (result.type == 'expect' && result.passed && !result.passed()) {
|
73
|
+
failures += 1;
|
74
|
+
failure += '<failure type="' + result.type + '" message="' + trim(escapeInvalidXmlChars(result.message)) + '">';
|
75
|
+
failure += escapeInvalidXmlChars(result.trace.stack || result.message);
|
76
|
+
failure += "</failure>";
|
77
|
+
}
|
78
|
+
}
|
79
|
+
if (failure) {
|
80
|
+
spec.output += failure;
|
81
|
+
}
|
82
|
+
spec.output += "</testcase>";
|
83
|
+
},
|
84
|
+
|
85
|
+
reportSuiteResults: function(suite) {
|
86
|
+
var results = suite.results();
|
87
|
+
var specs = suite.specs();
|
88
|
+
// for JUnit results, let's only include directly failed tests (not nested suites')
|
89
|
+
var failedCount = 0;
|
90
|
+
|
91
|
+
suite.status = results.passed() ? 'Passed.' : 'Failed.';
|
92
|
+
if (results.totalCount === 0) { // todo: change this to check results.skipped
|
93
|
+
suite.status = 'Skipped.';
|
94
|
+
}
|
95
|
+
|
96
|
+
// if a suite has no (active?) specs, reportSpecStarting is never called
|
97
|
+
// and thus the suite has no startTime -- account for that here
|
98
|
+
suite.startTime = suite.startTime || new Date();
|
99
|
+
suite.duration = elapsed(suite.startTime, new Date());
|
100
|
+
|
101
|
+
for (var i = 0; i < specs.length; i++) {
|
102
|
+
failedCount += specs[i].didFail ? 1 : 0;
|
103
|
+
}
|
104
|
+
this.print('<testsuite name="' + this.getFullName(suite) +
|
105
|
+
'" errors="0" tests="' + specs.length + '" failures="' + failedCount +
|
106
|
+
'" time="' + suite.duration + '" timestamp="' + ISODateString(suite.startTime) + '">');
|
107
|
+
for (var i = 0; i < specs.length; i++) {
|
108
|
+
this.print(specs[i].output);
|
109
|
+
}
|
110
|
+
this.print("</testsuite>");
|
111
|
+
},
|
112
|
+
|
113
|
+
reportRunnerResults: function(runner) {
|
114
|
+
this.print("</testsuites>");
|
115
|
+
this.signalCapybaraTestsFinishedRunning();
|
116
|
+
},
|
117
|
+
|
118
|
+
signalCapybaraTestsFinishedRunning: function() {
|
119
|
+
var div = document.createElement('div');
|
120
|
+
div.id = 'testscomplete';
|
121
|
+
document.body.appendChild(div);
|
122
|
+
},
|
123
|
+
|
124
|
+
getFullName: function(suite, isFilename) {
|
125
|
+
var fullName;
|
126
|
+
if (this.useDotNotation) {
|
127
|
+
fullName = suite.description;
|
128
|
+
for (var parentSuite = suite.parentSuite; parentSuite; parentSuite = parentSuite.parentSuite) {
|
129
|
+
fullName = parentSuite.description + '.' + fullName;
|
130
|
+
}
|
131
|
+
}
|
132
|
+
else {
|
133
|
+
fullName = suite.getFullName();
|
134
|
+
}
|
135
|
+
|
136
|
+
// Either remove or escape invalid XML characters
|
137
|
+
if (isFilename) {
|
138
|
+
return fullName.replace(/[^\w]/g, "");
|
139
|
+
}
|
140
|
+
return escapeInvalidXmlChars(fullName);
|
141
|
+
},
|
142
|
+
|
143
|
+
print: function(str) {
|
144
|
+
this.log(str);
|
145
|
+
},
|
146
|
+
|
147
|
+
log: function(str) {
|
148
|
+
var console = jasmine.getGlobal().console;
|
149
|
+
|
150
|
+
if (console && console.log) {
|
151
|
+
console.log(str);
|
152
|
+
}
|
153
|
+
}
|
154
|
+
};
|
155
|
+
|
156
|
+
// export public
|
157
|
+
jasmine.SnapdragonJUnitReporter = JUnitXmlReporter;
|
158
|
+
})();
|