@@ -39,15 +39,12 @@ public IObservable<FileSystemInfo> GetDirectoryScanner(DirectoryInfo root, Concu
3939 return Task . CompletedTask ;
4040 }
4141
42- PatternMatchingUtility . FilePatternMatcher fileIsMatch = null ;
42+ PatternMatchingUtility . CompiledMatcher fileIsMatch = null ;
43+ var patternsArray = filePatterns ? . ToArray ( ) ;
4344
44- if ( filePatterns == null || ! filePatterns . Any ( ) )
45+ if ( patternsArray is { Length : > 0 } )
4546 {
46- fileIsMatch = span => true ;
47- }
48- else
49- {
50- fileIsMatch = PatternMatchingUtility . GetFilePatternMatcher ( filePatterns ) ;
47+ fileIsMatch = PatternMatchingUtility . Compile ( patternsArray ) ;
5148 }
5249
5350 var sw = Stopwatch . StartNew ( ) ;
@@ -100,7 +97,7 @@ public IObservable<FileSystemInfo> GetDirectoryScanner(DirectoryInfo root, Concu
10097 {
10198 ShouldIncludePredicate = ( ref FileSystemEntry entry ) =>
10299 {
103- if ( ! entry . IsDirectory && fileIsMatch ( entry . FileName ) )
100+ if ( ! entry . IsDirectory && ( fileIsMatch == null || fileIsMatch . IsMatch ( entry . FileName ) ) )
104101 {
105102 return true ;
106103 }
@@ -210,46 +207,26 @@ public void Initialize(DirectoryInfo root, ExcludeDirectoryPredicate directoryEx
210207
211208 public IObservable < FileSystemInfo > Subscribe ( DirectoryInfo root , IEnumerable < string > patterns )
212209 {
213- var patternArray = patterns . ToArray ( ) ;
214-
215- if ( this . pendingScans . TryGetValue ( root , out var scannerObservable ) )
216- {
217- this . logger . LogDebug ( "Logging patterns {Patterns} for {Root}" , string . Join ( ":" , patterns ) , root . FullName ) ;
218-
219- var inner = scannerObservable . Value . Where ( fsi =>
220- {
221- if ( fsi is FileInfo fi )
222- {
223- return this . MatchesAnyPattern ( fi , patternArray ) ;
224- }
225- else
226- {
227- return true ;
228- }
229- } ) ;
230-
231- return inner ;
232- }
233-
234- throw new InvalidOperationException ( "Subscribe called without initializing scanner" ) ;
210+ var patternsArray = patterns as string [ ] ?? patterns . ToArray ( ) ;
211+ var compiled = PatternMatchingUtility . Compile ( patternsArray ) ;
212+ return this . Subscribe ( root , patternsArray , compiled ) ;
235213 }
236214
237215 public IObservable < ProcessRequest > GetFilteredComponentStreamObservable ( DirectoryInfo root , IEnumerable < string > patterns , IComponentRecorder componentRecorder )
238216 {
239- var observable = this . Subscribe ( root , patterns ) . OfType < FileInfo > ( ) . SelectMany ( f => patterns . Select ( sp => new
240- {
241- SearchPattern = sp ,
242- File = f ,
243- } ) ) . Where ( x =>
244- {
245- var searchPattern = x . SearchPattern ;
246- var fileName = x . File . Name ;
217+ var patternsArray = patterns as string [ ] ?? patterns . ToArray ( ) ;
218+ var compiled = PatternMatchingUtility . Compile ( patternsArray ) ;
247219
248- return this . pathUtilityService . MatchesPattern ( searchPattern , fileName ) ;
249- } ) . Where ( x => x . File . Exists )
220+ var observable = this . Subscribe ( root , patternsArray , compiled ) . OfType < FileInfo > ( )
221+ . Select ( f => new
222+ {
223+ File = f ,
224+ MatchedPattern = compiled . GetMatchingPattern ( f . Name ) ,
225+ } )
226+ . Where ( x => x . MatchedPattern != null && x . File . Exists )
250227 . Select ( x =>
251228 {
252- var lazyComponentStream = new LazyComponentStream ( x . File , x . SearchPattern , this . logger ) ;
229+ var lazyComponentStream = new LazyComponentStream ( x . File , x . MatchedPattern , this . logger ) ;
253230 return new ProcessRequest
254231 {
255232 ComponentStream = lazyComponentStream ,
@@ -280,14 +257,31 @@ private FileSystemInfo Transform(ref FileSystemEntry entry)
280257 return entry . ToFileSystemInfo ( ) ;
281258 }
282259
283- private IObservable < FileSystemInfo > CreateDirectoryWalker ( DirectoryInfo di , ExcludeDirectoryPredicate directoryExclusionPredicate , int minimumConnectionCount , IEnumerable < string > filePatterns )
260+ private IObservable < FileSystemInfo > Subscribe ( DirectoryInfo root , string [ ] patterns , PatternMatchingUtility . CompiledMatcher compiled )
284261 {
285- return this . GetDirectoryScanner ( di , new ConcurrentDictionary < string , bool > ( ) , directoryExclusionPredicate , filePatterns , true ) . Replay ( ) // Returns a replay subject which will republish anything found to new subscribers.
286- . AutoConnect ( minimumConnectionCount ) ; // Specifies that this connectable observable should start when minimumConnectionCount subscribe.
262+ if ( this . pendingScans . TryGetValue ( root , out var scannerObservable ) )
263+ {
264+ this . logger . LogDebug ( "Logging patterns {Patterns} for {Root}" , string . Join ( ":" , patterns ) , root . FullName ) ;
265+
266+ var inner = scannerObservable . Value . Where ( fsi =>
267+ {
268+ if ( fsi is FileInfo fi )
269+ {
270+ return compiled . IsMatch ( fi . Name . AsSpan ( ) ) ;
271+ }
272+
273+ return true ;
274+ } ) ;
275+
276+ return inner ;
277+ }
278+
279+ throw new InvalidOperationException ( "Subscribe called without initializing scanner" ) ;
287280 }
288281
289- private bool MatchesAnyPattern ( FileInfo fi , params string [ ] searchPatterns )
282+ private IObservable < FileSystemInfo > CreateDirectoryWalker ( DirectoryInfo di , ExcludeDirectoryPredicate directoryExclusionPredicate , int minimumConnectionCount , IEnumerable < string > filePatterns )
290283 {
291- return searchPatterns != null && searchPatterns . Any ( sp => this . pathUtilityService . MatchesPattern ( sp , fi . Name ) ) ;
284+ return this . GetDirectoryScanner ( di , new ConcurrentDictionary < string , bool > ( ) , directoryExclusionPredicate , filePatterns , true ) . Replay ( ) // Returns a replay subject which will republish anything found to new subscribers.
285+ . AutoConnect ( minimumConnectionCount ) ; // Specifies that this connectable observable should start when minimumConnectionCount subscribe.
292286 }
293287}
0 commit comments