10
10
11
11
'use strict' ;
12
12
13
- import type { Config } from 'types/Config' ;
14
13
import type { Context } from 'types/Context' ;
15
14
import type { Glob , Path } from 'types/Config' ;
16
15
import type { ResolveModuleConfig } from 'types/Resolve' ;
16
+ import type { Test } from 'types/TestRunner' ;
17
17
18
18
const micromatch = require ( 'micromatch' ) ;
19
19
20
20
const DependencyResolver = require ( 'jest-resolve-dependencies' ) ;
21
21
22
- const chalk = require ( 'chalk' ) ;
23
22
const changedFiles = require ( 'jest-changed-files' ) ;
24
23
const path = require ( 'path' ) ;
25
24
const {
26
25
escapePathForRegex,
27
26
replacePathSepForRegex,
28
27
} = require ( 'jest-regex-util' ) ;
29
28
30
- type SearchSourceConfig = {
31
- roots : Array < Path > ,
32
- testMatch : Array < Glob > ,
33
- testRegex : string ,
34
- testPathIgnorePatterns : Array < string > ,
35
- } ;
36
-
37
29
type SearchResult = { |
38
30
noSCM ? : boolean ,
39
- paths : Array < Path > ,
40
31
stats ?: { [ key : string ] : number } ,
32
+ tests : Array < Test > ,
41
33
total ? : number ,
42
34
| } ;
43
35
@@ -47,7 +39,7 @@ type Options = {|
47
39
lastCommit ? : boolean ,
48
40
| } ;
49
41
50
- export type PatternInfo = { |
42
+ export type PathPattern = { |
51
43
input ? : string ,
52
44
findRelatedTests ? : boolean ,
53
45
lastCommit ? : boolean ,
@@ -64,16 +56,14 @@ const hg = changedFiles.hg;
64
56
const determineSCM = path =>
65
57
Promise . all ( [ git . isGitRepository ( path ) , hg . isHGRepository ( path ) ] ) ;
66
58
const pathToRegex = p => replacePathSepForRegex ( p ) ;
67
- const pluralize = ( word : string , count : number , ending : string ) =>
68
- `${ count } ${ word } ${ count === 1 ? '' : ending } ` ;
69
59
70
60
const globsToMatcher = ( globs : ?Array < Glob > ) => {
71
61
if ( globs == null || globs . length === 0 ) {
72
62
return ( ) => true ;
73
63
}
74
64
75
65
const matchers = globs . map ( each => micromatch . matcher ( each , { dot : true } ) ) ;
76
- return ( path : Path ) => matchers . some ( each => each ( path ) ) ;
66
+ return path => matchers . some ( each => each ( path ) ) ;
77
67
} ;
78
68
79
69
const regexToMatcher = ( testRegex : string ) => {
@@ -82,12 +72,18 @@ const regexToMatcher = (testRegex: string) => {
82
72
}
83
73
84
74
const regex = new RegExp ( pathToRegex ( testRegex ) ) ;
85
- return ( path : Path ) => regex . test ( path ) ;
75
+ return path => regex . test ( path ) ;
86
76
} ;
87
77
78
+ const toTests = ( context , tests ) =>
79
+ tests . map ( path => ( {
80
+ context,
81
+ duration : undefined ,
82
+ path,
83
+ } ) ) ;
84
+
88
85
class SearchSource {
89
86
_context : Context ;
90
- _config : SearchSourceConfig ;
91
87
_options : ResolveModuleConfig ;
92
88
_rootPattern : RegExp ;
93
89
_testIgnorePattern : ?RegExp ;
@@ -98,13 +94,9 @@ class SearchSource {
98
94
testPathIgnorePatterns : ( path : Path ) => boolean ,
99
95
} ;
100
96
101
- constructor (
102
- context : Context ,
103
- config : SearchSourceConfig ,
104
- options ? : ResolveModuleConfig ,
105
- ) {
97
+ constructor ( context : Context , options ? : ResolveModuleConfig ) {
98
+ const { config} = context ;
106
99
this . _context = context ;
107
- this . _config = config ;
108
100
this . _options = options || {
109
101
skipNodeResolution : false ,
110
102
} ;
@@ -128,12 +120,12 @@ class SearchSource {
128
120
}
129
121
130
122
_filterTestPathsWithStats (
131
- allPaths : Array < Path > ,
123
+ allPaths : Array < Test > ,
132
124
testPathPattern ? : StrOrRegExpPattern ,
133
125
) : SearchResult {
134
126
const data = {
135
- paths : [ ] ,
136
127
stats : { } ,
128
+ tests : [ ] ,
137
129
total : allPaths . length ,
138
130
} ;
139
131
@@ -144,11 +136,10 @@ class SearchSource {
144
136
}
145
137
146
138
const testCasesKeys = Object . keys ( testCases ) ;
147
-
148
- data . paths = allPaths . filter ( path => {
139
+ data . tests = allPaths . filter ( test => {
149
140
return testCasesKeys . reduce (
150
141
( flag , key ) => {
151
- if ( testCases [ key ] ( path ) ) {
142
+ if ( testCases [ key ] ( test . path ) ) {
152
143
data . stats [ key ] = ++ data . stats [ key ] || 1 ;
153
144
return flag && true ;
154
145
}
@@ -164,7 +155,7 @@ class SearchSource {
164
155
165
156
_getAllTestPaths ( testPathPattern : StrOrRegExpPattern ) : SearchResult {
166
157
return this . _filterTestPathsWithStats (
167
- this . _context . hasteFS . getAllFiles ( ) ,
158
+ toTests ( this . _context , this . _context . hasteFS . getAllFiles ( ) ) ,
168
159
testPathPattern ,
169
160
) ;
170
161
}
@@ -184,12 +175,15 @@ class SearchSource {
184
175
this . _context . hasteFS ,
185
176
) ;
186
177
return {
187
- paths : dependencyResolver . resolveInverse (
188
- allPaths ,
189
- this . isTestFilePath . bind ( this ) ,
190
- {
191
- skipNodeResolution : this . _options . skipNodeResolution ,
192
- } ,
178
+ tests : toTests (
179
+ this . _context ,
180
+ dependencyResolver . resolveInverse (
181
+ allPaths ,
182
+ this . isTestFilePath . bind ( this ) ,
183
+ {
184
+ skipNodeResolution : this . _options . skipNodeResolution ,
185
+ } ,
186
+ ) ,
193
187
) ,
194
188
} ;
195
189
}
@@ -199,15 +193,17 @@ class SearchSource {
199
193
const resolvedPaths = paths . map ( p => path . resolve ( process . cwd ( ) , p ) ) ;
200
194
return this . findRelatedTests ( new Set ( resolvedPaths ) ) ;
201
195
}
202
- return { paths : [ ] } ;
196
+ return { tests : [ ] } ;
203
197
}
204
198
205
199
findChangedTests ( options : Options ) : Promise < SearchResult > {
206
- return Promise . all ( this . _config . roots . map ( determineSCM ) ) . then ( repos => {
200
+ return Promise . all (
201
+ this . _context . config . roots . map ( determineSCM ) ,
202
+ ) . then ( repos => {
207
203
if ( ! repos . every ( ( [ gitRepo , hgRepo ] ) => gitRepo || hgRepo ) ) {
208
204
return {
209
205
noSCM : true ,
210
- paths : [ ] ,
206
+ tests : [ ] ,
211
207
} ;
212
208
}
213
209
return Promise . all (
@@ -223,73 +219,17 @@ class SearchSource {
223
219
} ) ;
224
220
}
225
221
226
- getNoTestsFoundMessage (
227
- patternInfo : PatternInfo ,
228
- config : Config ,
229
- data : SearchResult ,
230
- ) : string {
231
- if ( patternInfo . onlyChanged ) {
232
- return chalk . bold (
233
- 'No tests found related to files changed since last commit.\n' ,
234
- ) +
235
- chalk . dim (
236
- patternInfo . watch
237
- ? 'Press `a` to run all tests, or run Jest with `--watchAll`.'
238
- : 'Run Jest without `-o` to run all tests.' ,
239
- ) ;
240
- }
241
-
242
- const testPathPattern = SearchSource . getTestPathPattern ( patternInfo ) ;
243
- const stats = data . stats || { } ;
244
- const statsMessage = Object . keys ( stats )
245
- . map ( key => {
246
- const value = key === 'testPathPattern' ? testPathPattern : config [ key ] ;
247
- if ( value ) {
248
- const matches = pluralize ( 'match' , stats [ key ] , 'es' ) ;
249
- return ` ${ key } : ${ chalk . yellow ( value ) } - ${ matches } ` ;
250
- }
251
- return null ;
252
- } )
253
- . filter ( line => line )
254
- . join ( '\n' ) ;
255
-
256
- return chalk . bold ( 'No tests found' ) +
257
- '\n' +
258
- ( data . total
259
- ? ` ${ pluralize ( 'file' , data . total || 0 , 's' ) } checked.\n` +
260
- statsMessage
261
- : `No files found in ${ config . rootDir } .\n` +
262
- `Make sure Jest's configuration does not exclude this directory.` +
263
- `\nTo set up Jest, make sure a package.json file exists.\n` +
264
- `Jest Documentation: ` +
265
- `facebook.github.io/jest/docs/configuration.html` ) ;
266
- }
267
-
268
- getTestPaths ( patternInfo : PatternInfo ) : Promise < SearchResult > {
269
- if ( patternInfo . onlyChanged ) {
270
- return this . findChangedTests ( { lastCommit : patternInfo . lastCommit } ) ;
271
- } else if ( patternInfo . findRelatedTests && patternInfo . paths ) {
272
- return Promise . resolve (
273
- this . findRelatedTestsFromPattern ( patternInfo . paths ) ,
274
- ) ;
275
- } else if ( patternInfo . testPathPattern != null ) {
276
- return Promise . resolve (
277
- this . findMatchingTests ( patternInfo . testPathPattern ) ,
278
- ) ;
222
+ getTestPaths ( pattern : PathPattern ) : Promise < SearchResult > {
223
+ if ( pattern . onlyChanged ) {
224
+ return this . findChangedTests ( { lastCommit : pattern . lastCommit } ) ;
225
+ } else if ( pattern . findRelatedTests && pattern . paths ) {
226
+ return Promise . resolve ( this . findRelatedTestsFromPattern ( pattern . paths ) ) ;
227
+ } else if ( pattern . testPathPattern != null ) {
228
+ return Promise . resolve ( this . findMatchingTests ( pattern . testPathPattern ) ) ;
279
229
} else {
280
- return Promise . resolve ( { paths : [ ] } ) ;
230
+ return Promise . resolve ( { tests : [ ] } ) ;
281
231
}
282
232
}
283
-
284
- static getTestPathPattern ( patternInfo : PatternInfo ) : string {
285
- const pattern = patternInfo . testPathPattern ;
286
- const input = patternInfo . input ;
287
- const formattedPattern = `/${ pattern || '' } /` ;
288
- const formattedInput = patternInfo . shouldTreatInputAsPattern
289
- ? `/${ input || '' } /`
290
- : `"${ input || '' } "` ;
291
- return input === pattern ? formattedInput : formattedPattern ;
292
- }
293
233
}
294
234
295
235
module . exports = SearchSource ;
0 commit comments