Source code for fpf.filters

"""Extensible File Path Filters."""
import ntpath
from typing import Set

import pathspec

from .mixins import FilePathMatchCallableMixin, ReadFileMixin


[docs]class PathSpecWildcardFileFilter(FilePathMatchCallableMixin): """Filter files based on PathSpec WildMatch (`.gitignore`).""" def __init__(self, path_spec_str: str = ''): """Create a new path spec wildcard file filter. :param path_spec_str: pathspec wildcard paterns. One per line, defaults to ''. If you want to ignore all hidden files, a valid pattern would be `.*` :type path_spec_str: str, optional """ self._spec = pathspec.PathSpec.from_lines( pattern_factory=pathspec.patterns.GitWildMatchPattern, lines=path_spec_str.splitlines()) def _match(self, file_path: str) -> bool: """Filter paths based on the pathspec filter. :param file_path: a file path or filename. :type file_path: str :return: True if the filename/path passes the filter, false if not. :rtype: bool """ result = not self._spec.match_file(file_path) return result
[docs]class ExtensionFileFilter(FilePathMatchCallableMixin): """Filter files based on a match of the file extensions. You can set it to ignore cases. Make sure to start each extension with the dot (`.`).""" def __init__(self, extensions: Set[str] = set(), ignore_case: bool = True): """Create a new filter based on file extensions. :param extensions: File extensions to *whitelist*, defaults to an empty set. The extension should start with ``.``. :type extensions: Set[str], optional :param ignore_case: Ignore extension case (``.exe`` vs ``.EXE``), defaults to True :type ignore_case: bool, optional """ if ignore_case: extensions = {extension.lower() for extension in extensions} self.extensions = extensions self.ignore_case = ignore_case def _match(self, file_path: str) -> bool: basename = ntpath.basename(file_path) _, extension = ntpath.splitext(basename) if self.ignore_case: extension = extension.lower() return extension in self.extensions
[docs]class YamlPathSpecFilter(ExtensionFileFilter, PathSpecWildcardFileFilter): """Filter YAML files (.yml, .yaml) based on pathspec wildcards (gitignore style).""" def __init__(self, path_spec_str: str = '', extensions=['.yml', '.yaml'], ignore_extension_case=True): """Create a PathSpec Wildcard filter. :param path_spec_str: pathsspec multiline string, defaults to ``''`` (no spec) :type path_spec_str: str, optional :param extensions: YAML file extensions, defaults to ``['.yml', '.yaml']``. :type extensions: list, optional :param ignore_extension_case: ignore extension cases, defaults to ``True`` :type ignore_extension_case: bool, optional """ PathSpecWildcardFileFilter.__init__(self, path_spec_str=path_spec_str) ExtensionFileFilter.__init__(self, extensions=extensions, ignore_case=ignore_extension_case) def _match(self, file_path: str): return PathSpecWildcardFileFilter._match(self, file_path) and ExtensionFileFilter._match(self, file_path)
[docs]class IgnoreFileFilter(PathSpecWildcardFileFilter, ReadFileMixin): """Filter files based on an ignore file like `.gitignore`.""" def __init__(self, ignore_file_path: str): """Create a filter based on an ignore file. :param ignore_file_path: path to the ignore file. :type ignore_file_path: str """ ignore_file_content = self._read_file(ignore_file_path) PathSpecWildcardFileFilter.__init__( self, path_spec_str=ignore_file_content, )
[docs]class YamlIgnoreFileFilter(YamlPathSpecFilter, ReadFileMixin): """Filter YAML files(`.yml, .yaml`) based on pathspec wildcard file(gitignore style).""" def __init__(self, ignore_file_path: str = '.yamlignore', extensions=['.yml', '.yaml'], ignore_extension_case=True): """Create a filepath filter based on a ``.yamlignore`` file (similar to a ``.gitignore``). :param ignore_file_path: path to the yamlignore file, defaults to ``.yamlignore`` :type ignore_file_path: str, optional :param extensions: Extensions to allow, defaults to ``['.yml', '.yaml']``. :type extensions: list, optional :param ignore_extension_case: ignore cases of extensions(yml vs YML), defaults to True. :type ignore_extension_case: bool, optional """ yaml_ignore_contents = self._read_file(ignore_file_path) YamlPathSpecFilter.__init__( self, path_spec_str=yaml_ignore_contents, extensions=extensions, ignore_extension_case=ignore_extension_case )
[docs]class UnixHiddenFileFilter(FilePathMatchCallableMixin): """Filter out any hidden files (starting with a .).""" def _match(self, file_path: str): basename = ntpath.basename(file_path) return not basename.startswith('.')
[docs]class DummyFilter(FilePathMatchCallableMixin): """Do not filter out anything.""" def _match(self, file_path: str): return True
__all__ = [ 'ExtensionFileFilter', 'IgnoreFileFilter', 'PathSpecWildcardFileFilter', 'YamlIgnoreFileFilter', 'YamlPathSpecFilter', 'UnixHiddenFileFilter', 'DummyFilter', ]