MCPcopy Index your code
hub / github.com/python/cpython / recursive_selector

Method recursive_selector

Lib/glob.py:463–524  ·  view source on GitHub ↗

Returns a function that selects a given path and all its children, recursively, filtering by pattern.

(self, part, parts)

Source from the content-addressed store, hash-verified

461 return select_wildcard
462
463 def recursive_selector(self, part, parts):
464 """Returns a function that selects a given path and all its children,
465 recursively, filtering by pattern.
466 """
467 # Optimization: consume following '**' parts, which have no effect.
468 while parts and parts[-1] == '**':
469 parts.pop()
470
471 # Optimization: consume and join any following non-special parts here,
472 # rather than leaving them for the next selector. They're used to
473 # build a regular expression, which we use to filter the results of
474 # the recursive walk. As a result, non-special pattern segments
475 # following a '**' wildcard don't require additional filesystem access
476 # to expand.
477 follow_symlinks = self.recursive is not _no_recurse_symlinks
478 if follow_symlinks:
479 while parts and parts[-1] not in _special_parts:
480 part += self.sep + parts.pop()
481
482 match = None if part == '**' else self.compile(part)
483 dir_only = bool(parts)
484 select_next = self.selector(parts)
485
486 def select_recursive(path, exists=False):
487 path_str = self.stringify_path(path)
488 match_pos = len(path_str)
489 if match is None or match(path_str, match_pos):
490 yield from select_next(path, exists)
491 stack = [path]
492 while stack:
493 yield from select_recursive_step(stack, match_pos)
494
495 def select_recursive_step(stack, match_pos):
496 path = stack.pop()
497 try:
498 entries = self.scandir(path)
499 except OSError:
500 pass
501 else:
502 for entry, _entry_name, entry_path in entries:
503 is_dir = False
504 try:
505 if entry.is_dir(follow_symlinks=follow_symlinks):
506 is_dir = True
507 except OSError:
508 pass
509
510 if is_dir or not dir_only:
511 entry_path_str = self.stringify_path(entry_path)
512 if dir_only:
513 entry_path = self.concat_path(entry_path, self.sep)
514 if match is None or match(entry_path_str, match_pos):
515 if dir_only:
516 yield from select_next(entry_path, exists=True)
517 else:
518 # Optimization: directly yield the path if this is
519 # last pattern part.
520 yield entry_path

Callers

nothing calls this directly

Calls 3

compileMethod · 0.95
selectorMethod · 0.95
popMethod · 0.45

Tested by

no test coverage detected