1 | var tape = require('../');
|
2 | var tap = require('tap');
|
3 | var concat = require('concat-stream');
|
4 | var tapParser = require('tap-parser');
|
5 | var yaml = require('js-yaml');
|
6 |
|
7 | tap.test('preserves stack trace with newlines', function (tt) {
|
8 | tt.plan(3);
|
9 |
|
10 | var test = tape.createHarness();
|
11 | var stream = test.createStream();
|
12 | var parser = stream.pipe(tapParser());
|
13 | var stackTrace = 'foo\n bar';
|
14 |
|
15 | parser.once('assert', function (data) {
|
16 | delete data.diag.at;
|
17 | tt.deepEqual(data, {
|
18 | ok: false,
|
19 | id: 1,
|
20 | name: 'Error: Preserve stack',
|
21 | diag: {
|
22 | stack: stackTrace,
|
23 | operator: 'error',
|
24 | expected: 'undefined',
|
25 | actual: '[Error: Preserve stack]'
|
26 | }
|
27 | });
|
28 | });
|
29 |
|
30 | stream.pipe(concat(function (body) {
|
31 | var body = body.toString('utf8');
|
32 | body = stripAt(body);
|
33 | tt.equal(
|
34 | body,
|
35 | 'TAP version 13\n'
|
36 | + '# multiline stack trace\n'
|
37 | + 'not ok 1 Error: Preserve stack\n'
|
38 | + ' ---\n'
|
39 | + ' operator: error\n'
|
40 | + ' expected: |-\n'
|
41 | + ' undefined\n'
|
42 | + ' actual: |-\n'
|
43 | + ' [Error: Preserve stack]\n'
|
44 | + ' stack: |-\n'
|
45 | + ' foo\n'
|
46 | + ' bar\n'
|
47 | + ' ...\n'
|
48 | + '\n'
|
49 | + '1..1\n'
|
50 | + '# tests 1\n'
|
51 | + '# pass 0\n'
|
52 | + '# fail 1\n'
|
53 | );
|
54 |
|
55 | tt.deepEqual(getDiag(body), {
|
56 | stack: stackTrace,
|
57 | operator: 'error',
|
58 | expected: 'undefined',
|
59 | actual: '[Error: Preserve stack]'
|
60 | });
|
61 | }));
|
62 |
|
63 | test('multiline stack trace', function (t) {
|
64 | t.plan(1);
|
65 | var err = new Error('Preserve stack');
|
66 | err.stack = stackTrace;
|
67 | t.error(err);
|
68 | });
|
69 | });
|
70 |
|
71 | tap.test('parses function name from original stack', function (tt) {
|
72 | tt.plan(1);
|
73 |
|
74 | var test = tape.createHarness();
|
75 | test.createStream();
|
76 |
|
77 | test._results._watch = function (t) {
|
78 | t.on('result', function (res) {
|
79 | tt.equal('Test.testFunctionNameParsing', res.functionName);
|
80 | });
|
81 | };
|
82 |
|
83 | test('t.equal stack trace', function testFunctionNameParsing(t) {
|
84 | t.equal(true, false, 'true should be false');
|
85 | t.end();
|
86 | });
|
87 | });
|
88 |
|
89 | tap.test('parses function name from original stack for anonymous function', function (tt) {
|
90 | tt.plan(1);
|
91 |
|
92 | var test = tape.createHarness();
|
93 | test.createStream();
|
94 |
|
95 | test._results._watch = function (t) {
|
96 | t.on('result', function (res) {
|
97 | tt.equal('Test.<anonymous>', res.functionName);
|
98 | });
|
99 | };
|
100 |
|
101 | test('t.equal stack trace', function (t) {
|
102 | t.equal(true, false, 'true should be false');
|
103 | t.end();
|
104 | });
|
105 | });
|
106 |
|
107 | tap.test('preserves stack trace for failed assertions', function (tt) {
|
108 | tt.plan(6);
|
109 |
|
110 | var test = tape.createHarness();
|
111 | var stream = test.createStream();
|
112 | var parser = stream.pipe(tapParser());
|
113 |
|
114 | var stack = '';
|
115 | parser.once('assert', function (data) {
|
116 | tt.equal(typeof data.diag.at, 'string');
|
117 | tt.equal(typeof data.diag.stack, 'string');
|
118 | at = data.diag.at || '';
|
119 | stack = data.diag.stack || '';
|
120 | tt.ok(/^Error: true should be false(\n at .+)+/.exec(stack), 'stack should be a stack');
|
121 | tt.deepEqual(data, {
|
122 | ok: false,
|
123 | id: 1,
|
124 | name: 'true should be false',
|
125 | diag: {
|
126 | at: at,
|
127 | stack: stack,
|
128 | operator: 'equal',
|
129 | expected: false,
|
130 | actual: true
|
131 | }
|
132 | });
|
133 | });
|
134 |
|
135 | stream.pipe(concat(function (body) {
|
136 | var body = body.toString('utf8');
|
137 | body = stripAt(body);
|
138 | tt.equal(
|
139 | body,
|
140 | 'TAP version 13\n'
|
141 | + '# t.equal stack trace\n'
|
142 | + 'not ok 1 true should be false\n'
|
143 | + ' ---\n'
|
144 | + ' operator: equal\n'
|
145 | + ' expected: false\n'
|
146 | + ' actual: true\n'
|
147 | + ' stack: |-\n'
|
148 | + ' '
|
149 | + stack.replace(/\n/g, '\n ') + '\n'
|
150 | + ' ...\n'
|
151 | + '\n'
|
152 | + '1..1\n'
|
153 | + '# tests 1\n'
|
154 | + '# pass 0\n'
|
155 | + '# fail 1\n'
|
156 | );
|
157 |
|
158 | tt.deepEqual(getDiag(body), {
|
159 | stack: stack,
|
160 | operator: 'equal',
|
161 | expected: false,
|
162 | actual: true
|
163 | });
|
164 | }));
|
165 |
|
166 | test('t.equal stack trace', function (t) {
|
167 | t.plan(1);
|
168 | t.equal(true, false, 'true should be false');
|
169 | });
|
170 | });
|
171 |
|
172 | tap.test('preserves stack trace for failed assertions where actual===falsy', function (tt) {
|
173 | tt.plan(6);
|
174 |
|
175 | var test = tape.createHarness();
|
176 | var stream = test.createStream();
|
177 | var parser = stream.pipe(tapParser());
|
178 |
|
179 | var stack = '';
|
180 | parser.once('assert', function (data) {
|
181 | tt.equal(typeof data.diag.at, 'string');
|
182 | tt.equal(typeof data.diag.stack, 'string');
|
183 | at = data.diag.at || '';
|
184 | stack = data.diag.stack || '';
|
185 | tt.ok(/^Error: false should be true(\n at .+)+/.exec(stack), 'stack should be a stack');
|
186 | tt.deepEqual(data, {
|
187 | ok: false,
|
188 | id: 1,
|
189 | name: 'false should be true',
|
190 | diag: {
|
191 | at: at,
|
192 | stack: stack,
|
193 | operator: 'equal',
|
194 | expected: true,
|
195 | actual: false
|
196 | }
|
197 | });
|
198 | });
|
199 |
|
200 | stream.pipe(concat(function (body) {
|
201 | var body = body.toString('utf8');
|
202 | body = stripAt(body);
|
203 | tt.equal(
|
204 | body,
|
205 | 'TAP version 13\n'
|
206 | + '# t.equal stack trace\n'
|
207 | + 'not ok 1 false should be true\n'
|
208 | + ' ---\n'
|
209 | + ' operator: equal\n'
|
210 | + ' expected: true\n'
|
211 | + ' actual: false\n'
|
212 | + ' stack: |-\n'
|
213 | + ' '
|
214 | + stack.replace(/\n/g, '\n ') + '\n'
|
215 | + ' ...\n'
|
216 | + '\n'
|
217 | + '1..1\n'
|
218 | + '# tests 1\n'
|
219 | + '# pass 0\n'
|
220 | + '# fail 1\n'
|
221 | );
|
222 |
|
223 | tt.deepEqual(getDiag(body), {
|
224 | stack: stack,
|
225 | operator: 'equal',
|
226 | expected: true,
|
227 | actual: false
|
228 | });
|
229 | }));
|
230 |
|
231 | test('t.equal stack trace', function (t) {
|
232 | t.plan(1);
|
233 | t.equal(false, true, 'false should be true');
|
234 | });
|
235 | });
|
236 |
|
237 | function getDiag(body) {
|
238 | var yamlStart = body.indexOf(' ---');
|
239 | var yamlEnd = body.indexOf(' ...\n');
|
240 | var diag = body.slice(yamlStart, yamlEnd).split('\n').map(function (line) {
|
241 | return line.slice(2);
|
242 | }).join('\n');
|
243 |
|
244 |
|
245 |
|
246 | var withStack = yaml.safeLoad(diag);
|
247 | delete withStack.at;
|
248 | return withStack;
|
249 | }
|
250 |
|
251 | function stripAt(body) {
|
252 | return body.replace(/^\s*at:\s+Test.*$\n/m, '');
|
253 | }
|