Skip to content

Commit 148b33e

Browse files
committed
Merge pull request #1808 from a8m/improve-grep-issue-808
feature(mocha/grep): improve grep - issue #808
2 parents 0b9876b + 194f19e commit 148b33e

File tree

6 files changed

+91
-39
lines changed

6 files changed

+91
-39
lines changed

bin/_mocha

+2-2
Original file line numberDiff line numberDiff line change
@@ -258,11 +258,11 @@ mocha.suite.bail(program.bail);
258258

259259
// --grep
260260

261-
if (program.grep) mocha.grep(new RegExp(program.grep));
261+
if (program.grep) mocha.grep(program.grep);
262262

263263
// --fgrep
264264

265-
if (program.fgrep) mocha.grep(program.fgrep);
265+
if (program.fgrep) mocha.fgrep(program.fgrep);
266266

267267
// --invert
268268

lib/mocha.js

+19-3
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,7 @@ function Mocha(options) {
7979
this.grep(new RegExp(options.grep));
8080
}
8181
if (options.fgrep) {
82-
this.grep(options.fgrep);
82+
this.fgrep(options.fgrep);
8383
}
8484
this.suite = new exports.Suite('', new exports.Context());
8585
this.ui(options.ui);
@@ -240,6 +240,17 @@ Mocha.prototype._growl = function(runner, reporter) {
240240
});
241241
};
242242

243+
/**
244+
* Escape string and add it to grep as a regexp.
245+
*
246+
* @api public
247+
* @param str
248+
* @returns {Mocha}
249+
*/
250+
Mocha.prototype.fgrep = function(str) {
251+
return this.grep(new RegExp(escapeRe(str)));
252+
};
253+
243254
/**
244255
* Add regexp to grep, if `re` is a string it is escaped.
245256
*
@@ -248,10 +259,15 @@ Mocha.prototype._growl = function(runner, reporter) {
248259
* @return {Mocha}
249260
*/
250261
Mocha.prototype.grep = function(re) {
251-
this.options.grep = typeof re === 'string' ? new RegExp(escapeRe(re)) : re;
262+
if (utils.isString(re)) {
263+
// extract args if it's regex-like, i.e: [string, pattern, flag]
264+
var arg = re.match(/^\/(.*)\/(g|i|)$|.*/);
265+
this.options.grep = new RegExp(arg[1] || arg[0], arg[2]);
266+
} else {
267+
this.options.grep = re;
268+
}
252269
return this;
253270
};
254-
255271
/**
256272
* Invert `.grep()` matches.
257273
*

support/browser-entry.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -126,8 +126,8 @@ mocha.run = function(fn){
126126
mocha.globals('location');
127127

128128
var query = Mocha.utils.parseQuery(global.location.search || '');
129-
if (query.grep) mocha.grep(new RegExp(query.grep));
130-
if (query.fgrep) mocha.grep(query.fgrep);
129+
if (query.grep) mocha.grep(query.grep);
130+
if (query.fgrep) mocha.fgrep(query.fgrep);
131131
if (query.invert) mocha.invert();
132132

133133
return Mocha.prototype.run.call(mocha, function(err){

test/grep.js

+38-21
Original file line numberDiff line numberDiff line change
@@ -5,44 +5,61 @@ describe('Mocha', function(){
55
it('should add a RegExp to the mocha.options object', function(){
66
var mocha = new Mocha({ grep: /foo.*/ });
77
mocha.options.grep.toString().should.equal('/foo.*/');
8-
})
8+
});
99

1010
it('should convert string to a RegExp', function(){
1111
var mocha = new Mocha({ grep: 'foo.*' });
1212
mocha.options.grep.toString().should.equal('/foo.*/');
13-
})
14-
})
13+
});
14+
});
1515

1616
describe('"fgrep" option', function(){
1717
it('should escape and convert string to a RegExp', function(){
1818
var mocha = new Mocha({ fgrep: 'foo.*' });
1919
mocha.options.grep.toString().should.equal('/foo\\.\\*/');
20-
})
21-
})
20+
});
21+
});
2222

23-
describe('.grep()', function(){
24-
it('should add a RegExp to the mocha.options object', function(){
25-
var mocha = new Mocha;
26-
mocha.grep(/foo/);
27-
mocha.options.grep.toString().should.equal('/foo/');
28-
})
23+
describe('.grep()', function() {
24+
// Test helper
25+
function testGrep(mocha) {
26+
return function testGrep(grep, expected) {
27+
mocha.grep(grep);
28+
mocha.options.grep.toString().should.equal(expected);
29+
}
30+
}
2931

30-
it('should convert grep string to a RegExp', function(){
31-
var mocha = new Mocha;
32-
mocha.grep('foo');
33-
mocha.options.grep.toString().should.equal('/foo/');
34-
})
32+
it('should add a RegExp to the mocha.options object', function() {
33+
var test = testGrep(new Mocha);
34+
test(/foo/, '/foo/');
35+
});
36+
37+
it('should convert grep string to a RegExp', function() {
38+
var test = testGrep(new Mocha);
39+
test('foo', '/foo/');
40+
test('^foo.*bar$', '/^foo.*bar$/');
41+
test('^@.*(?=\\(\\)$)', '/^@.*(?=\\(\\)$)/');
42+
});
43+
44+
it('should covert grep regex-like string to a RegExp', function() {
45+
var test = testGrep(new Mocha);
46+
test('/foo/', '/foo/');
47+
// Keep the flags
48+
test('/baz/i', '/baz/i');
49+
test('/bar/g', '/bar/g');
50+
test('/^foo(.*)bar/g', '/^foo(.*)bar/g');
51+
});
3552

3653
it('should return it\'s parent Mocha object for chainability', function(){
3754
var mocha = new Mocha;
3855
mocha.grep().should.equal(mocha);
39-
})
40-
})
56+
});
57+
});
4158

4259
describe('"invert" option', function(){
4360
it('should add a Boolean to the mocha.options object', function(){
4461
var mocha = new Mocha({ invert: true });
4562
mocha.options.invert.should.be.ok;
46-
})
47-
})
48-
})
63+
});
64+
});
65+
});

test/integration/fixtures/options/grep.js

+6-1
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,15 @@
11
describe('grep', function() {
2+
describe('Match', function() {
3+
it('should run', function(){});
4+
it('should also run', function() {});
5+
});
6+
27
describe('match', function() {
38
it('should run', function(){});
49
it('should also run', function() {});
510
});
611

7-
describe('fail', function(){
12+
describe('fail', function() {
813
it('should not be ran', function() {
914
throw new Error('Spec should not run');
1015
});

test/integration/options.js

+24-10
Original file line numberDiff line numberDiff line change
@@ -111,15 +111,29 @@ describe('options', function() {
111111
});
112112
});
113113

114-
it('runs specs matching a RegExp', function(done) {
115-
args = ['--grep', '.*'];
116-
run('options/grep.js', args, function(err, res) {
117-
assert(!err);
118-
assert.equal(res.stats.pending, 0);
119-
assert.equal(res.stats.passes, 2);
120-
assert.equal(res.stats.failures, 1);
121-
assert.equal(res.code, 1);
122-
done();
114+
describe('runs specs matching a RegExp', function() {
115+
it('with RegExp like strings(pattern follow by flag)', function(done) {
116+
args = ['--grep', '/match/i'];
117+
run('options/grep.js', args, function(err, res) {
118+
assert(!err);
119+
assert.equal(res.stats.pending, 0);
120+
assert.equal(res.stats.passes, 4);
121+
assert.equal(res.stats.failures, 0);
122+
assert.equal(res.code, 0);
123+
done();
124+
});
125+
});
126+
127+
it('string as pattern', function(done) {
128+
args = ['--grep', '.*'];
129+
run('options/grep.js', args, function(err, res) {
130+
assert(!err);
131+
assert.equal(res.stats.pending, 0);
132+
assert.equal(res.stats.passes, 4);
133+
assert.equal(res.stats.failures, 1);
134+
assert.equal(res.code, 1);
135+
done();
136+
});
123137
});
124138
});
125139

@@ -129,7 +143,7 @@ describe('options', function() {
129143
run('options/grep.js', args, function(err, res) {
130144
assert(!err);
131145
assert.equal(res.stats.pending, 0);
132-
assert.equal(res.stats.passes, 2);
146+
assert.equal(res.stats.passes, 4);
133147
assert.equal(res.stats.failures, 0);
134148
assert.equal(res.code, 0);
135149
done();

0 commit comments

Comments
 (0)