<commit_before>"""

:synopsis: Define the basic :mod:`parser` classes that will parse the
    data from the report file.

.. moduleauthor:: <NAME>

"""

import os
import fnmatch

from lxml import etree
from lxml.etree import LxmlError


class AbstractParser(object):

    """Abstract representation of a parser.

    .. note::

        This class will be extended for each pentesting tool. That way, each
        tool will add its own parsing specificities.

    """

    #: :class:`str` -- Name of the tool.
    __tool__ = None
    #: :class:`str` -- Format of reports it supports.
    __format__ = None
    #: :class:`list` -- Versions it can supports.
    __version__ = None

    def __init__(self, pathname='./', filename='*'):
        """Initialize :class:`AbstractParser`.

        :param str pathname: Path to the report directory.
        :param str filename: Regex matching the report file.

        """
        #: :class:`type` -- i/o stream of the report.
        self.stream = self.handle_file(pathname, filename)
        #: :class:`list` -- List of dict of the results found in the report.
        self.vulns = []
        #: :class:`dict` -- Dict of the metadata found in the report.
        self.metadata = {}

    @staticmethod
    def _recursive_find(pathname='./', file_regex='*', early_break=True):
        """Retrieve the full path to the report file(s).

        :param str pathname: The root directory where to start searching.
        :param re file_regex: The regex that will be matched against all files
            from within `pathname`.
        :param bool early_break: Stop the search as soon as a file has been
            matched.

        :return: A list of path to the matched files that have been found.
        :rtype: :class:`list`

        .. note::

            The search occurs starting from `pathname` as the root directory.

        """
        founds = []
        for base, _, files in os.walk(pathname):
            matched_files = fnmatch.filter(files, file_regex)
            founds.extend(
                os.path.join(base, matched_file)
                for matched_file in matched_files)
            if founds and early_break:
                break
        return founds


    @classmethod
    def handle_file(cls, pathname='./', filename='*'):
        """Process the report file.

        :param str pathname: Path to the report directory.
        :param str filename: Regex matching the report file.

        :raises: :class:`NotImplementedError` because this is an abstract
            method.

        """
        raise NotImplementedError(<commit_msg>[parser] Remove extra blank line.<commit_after>"""

:synopsis: Define the basic :mod:`parser` classes that will parse the
    data from the report file.

.. moduleauthor:: <NAME>

"""

import os
import fnmatch

from lxml import etree
from lxml.etree import LxmlError


class AbstractParser(object):

    """Abstract representation of a parser.

    .. note::

        This class will be extended for each pentesting tool. That way, each
        tool will add its own parsing specificities.

    """

    #: :class:`str` -- Name of the tool.
    __tool__ = None
    #: :class:`str` -- Format of reports it supports.
    __format__ = None
    #: :class:`list` -- Versions it can supports.
    __version__ = None

    def __init__(self, pathname='./', filename='*'):
        """Initialize :class:`AbstractParser`.

        :param str pathname: Path to the report directory.
        :param str filename: Regex matching the report file.

        """
        #: :class:`type` -- i/o stream of the report.
        self.stream = self.handle_file(pathname, filename)
        #: :class:`list` -- List of dict of the results found in the report.
        self.vulns = []
        #: :class:`dict` -- Dict of the metadata found in the report.
        self.metadata = {}

    @staticmethod
    def _recursive_find(pathname='./', file_regex='*', early_break=True):
        """Retrieve the full path to the report file(s).

        :param str pathname: The root directory where to start searching.
        :param re file_regex: The regex that will be matched against all files
            from within `pathname`.
        :param bool early_break: Stop the search as soon as a file has been
            matched.

        :return: A list of path to the matched files that have been found.
        :rtype: :class:`list`

        .. note::

            The search occurs starting from `pathname` as the root directory.

        """
        founds = []
        for base, _, files in os.walk(pathname):
            matched_files = fnmatch.filter(files, file_regex)
            founds.extend(
                os.path.join(base, matched_file)
                for matched_file in matched_files)
            if founds and early_break:
                break
        return founds

    @classmethod
    def handle_file(cls, pathname='./', filename='*'):
        """Process the report file.

        :param str pathname: Path to the report directory.
        :param str filename: Regex matching the report file.

        :raises: :class:`NotImplementedError` because this is an abstract
            method.

        """
        raise NotImplementedError(
{'fraction_non_alphanumeric': 0.09776162234551368, 'fraction_numerical': 0.0, 'mean_word_length': 2.2291537986411365, 'pattern_counts': {'":': 0, '<': 5, '<?xml version=': 0, '>': 5, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 6}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5070218', 'n_tokens_mistral': 1440, 'n_tokens_neox': 1376, 'n_words': 539}