<commit_before>from copy import deepcopy
import re

from sublime_plugin import WindowCommand
import sublime

from ...common import util
from ..git_command import GitCommand
from ..ui_mixins.quick_panel import PanelActionMixin, PanelCommandMixin, show_log_panel


class LogMixin(object):
    """
    Display git log in a quick panel for given file and branch. Upon selection
    of a commit, displays an "action menu" via the ``GsLogActionCommand``.

    Supports paginated fetching of log (defaults to 6000 entries per "page").

    This mixin can be used with both ``WindowCommand`` and ``TextCommand``,
    but the subclass must also inherit fro GitCommand (for the `git()` method)
    """

    def run(self, *args, file_path=None, **kwargs):
        sublime.set_timeout_async(lambda: self.run_async(file_path=file_path, **kwargs), 0)

    def run_async(self, file_path=None, **kwargs):
        show_log_panel(
            self.log_generator(file_path=file_path, **kwargs),
            lambda commit: self.on_done(commit, file_path=file_path, **kwargs)
        )

    def on_done(self, commit, **kwargs):
        if commit:
            self.do_action(commit, **kwargs)

    def do_action(self, commit_hash, **kwargs):
        if hasattr(self, 'window'):
            window = self.window
        else:
            window = self.view.window()
        window.run_command("gs_log_action", {
            "commit_hash": commit_hash,
            "file_path": kwargs.get("file_path")
        })


class GsLogCurrentBranchCommand(LogMixin, WindowCommand, GitCommand):
    pass


class GsLogAllBranchesCommand(LogMixin, WindowCommand, GitCommand):

    def log(self, **kwargs):
        return super().log(all_branches=True, **kwargs)


class GsLogByAuthorCommand(LogMixin, WindowCommand, GitCommand):

    """
    Open a quick panel containing all committers for the active
    repository, ordered by most commits, Git name, and email.
    Once selected, display a quick panel with all commits made
    by the specified author.
    """

    def run_async(self, **kwargs):
        email = self.git("config", "user.email").strip()
        self._entries = []

        commiter_str = self.git("shortlog", "-sne", "HEAD")
        for line in commiter_str.split('\n'):
            m = re.search('\s*(\d*)\s*(.*)\s<(.*)>', line)
            if m is None:
                continue
            commit_count, author_name, author_email = m.groups()
            author_text = "{} <{}>".format(author_name, author_email)
            self._entries.append((commit_count, author_name, author_email, author_text))

        self.window.show_quick_panel(
            [entry[3] for entry in self._entries],
            self.on_author_selection,
            flags=sublime.MONOSPACE_FONT,
            selected_index=(list(line[2] for line in self._entries)).index(email)
        )

    def on_author_selection(self, index):
        if index == -1:
            return
        self._selected_author = self._entries[index][3]
        super().run_async()

    def log(self, **kwargs):
        return super().log(author=self._selected_author, **kwargs)


class GsLogByBranchCommand(LogMixin, WindowCommand, GitCommand):

    def run_async(self, **kwargs):
        self.all_branches = [b.name_with_remote for b in self.get_branches()]

        if hasattr(self, '_selected_branch') and self._selected_branch in self.all_branches:
            pre_selected_index = self.all_branches.index(self._selected_branch)
        else:
            pre_selected_index = self.all_branches.index(self.get_current_branch_name())

        self.window.show_quick_panel(
            self.all_branches,
            self.on_branch_selection,
            flags=sublime.MONOSPACE_FONT,
            selected_index=pre_selected_index
        )

    def on_branch_selection(self, index):
        if index == -1:
            return
        super().run_async(branch=self.all_branches[index])


class GsLogCommand(PanelCommandMixin, WindowCommand, GitCommand):
    default_actions = [
        ["gs_log_current_branch", "For current branch"],
        ["gs_log_all_branches", "For all branches"],
        ["gs_log_by_author", "Filtered by author"],
        ["gs_log_by_branch", "Filtered by branch"],
    ]

    def run(self, file_path=None, current_file=False):
        self._file_path = self.file_path if current_file else file_path
        super().run()

    def update_actions(self):
        # deep copy list to avoid duplication via mutable lists
        self.actions = deepcopy(self.default_actions)
        for action in self.actions:
            # append a tuple to pass an argument<commit_msg>Enhancement: improve GsLogByAuthorCommand and GsLogByBranchCommand<commit_after>from copy import deepcopy
import re

from sublime_plugin import WindowCommand
import sublime

from ...common import util
from ..git_command import GitCommand
from ..ui_mixins.quick_panel import PanelActionMixin, PanelCommandMixin
from ..ui_mixins.quick_panel import show_log_panel, show_branch_panel


class LogMixin(object):
    """
    Display git log in a quick panel for given file and branch. Upon selection
    of a commit, displays an "action menu" via the ``GsLogActionCommand``.

    Supports paginated fetching of log (defaults to 6000 entries per "page").

    This mixin can be used with both ``WindowCommand`` and ``TextCommand``,
    but the subclass must also inherit fro GitCommand (for the `git()` method)
    """

    def run(self, *args, file_path=None, **kwargs):
        sublime.set_timeout_async(lambda: self.run_async(file_path=file_path, **kwargs), 0)

    def run_async(self, file_path=None, **kwargs):
        show_log_panel(
            self.log_generator(file_path=file_path, **kwargs),
            lambda commit: self.on_done(commit, file_path=file_path, **kwargs)
        )

    def on_done(self, commit, **kwargs):
        if commit:
            self.do_action(commit, **kwargs)

    def do_action(self, commit_hash, **kwargs):
        if hasattr(self, 'window'):
            window = self.window
        else:
            window = self.view.window()
        window.run_command("gs_log_action", {
            "commit_hash": commit_hash,
            "file_path": kwargs.get("file_path")
        })


class GsLogCurrentBranchCommand(LogMixin, WindowCommand, GitCommand):
    pass


class GsLogAllBranchesCommand(LogMixin, WindowCommand, GitCommand):

    def log(self, **kwargs):
        return super().log(all_branches=True, **kwargs)


class GsLogByAuthorCommand(LogMixin, WindowCommand, GitCommand):

    """
    Open a quick panel containing all committers for the active
    repository, ordered by most commits, Git name, and email.
    Once selected, display a quick panel with all commits made
    by the specified author.
    """

    def run_async(self, **kwargs):
        email = self.git("config", "user.email").strip()
        self._entries = []

        commiter_str = self.git("shortlog", "-sne", "HEAD")
        for line in commiter_str.split('\n'):
            m = re.search('\s*(\d*)\s*(.*)\s<(.*)>', line)
            if m is None:
                continue
            commit_count, author_name, author_email = m.groups()
            author_text = "{} <{}>".format(author_name, author_email)
            self._entries.append((commit_count, author_name, author_email, author_text))

        self.window.show_quick_panel(
            [entry[3] for entry in self._entries],
            lambda index: self.on_author_selection(index, **kwargs),
            flags=sublime.MONOSPACE_FONT,
            selected_index=(list(line[2] for line in self._entries)).index(email)
        )

    def on_author_selection(self, index, **kwargs):
        if index == -1:
            return
        self._selected_author = self._entries[index][3]
        super().run_async(**kwargs)

    def log(self, **kwargs):
        return super().log(author=self._selected_author, **kwargs)


class GsLogByBranchCommand(LogMixin, WindowCommand, GitCommand):

    def run_async(self, **kwargs):
        show_branch_panel(lambda branch: self.on_branch_selection(branch, **kwargs))

    def on_branch_selection(self, branch, **kwargs):
        if branch:
            super().run_async(branch=branch, **kwargs)


class GsLogCommand(PanelCommandMixin, WindowCommand, GitCommand):
    default_actions = [
        ["gs_log_current_branch", "For current branch"],
        ["gs_log_all_branches", "For all branches"],
        ["gs_log_by_author", "Filtered by author"],
        ["gs_log_by_branch", "Filtered by branch"],
    ]

    def run(self, file_path=None, current_file=False):
        self._file_path = self.file_path if current_file else file_path
        super().run()

    def update_actions(self):
        # deep copy list to avoid duplication via mutable lists
        self.actions = deepcopy(self.default_actions)
        for action in self.actions:
            # append a tuple to pass an argument
{'fraction_non_alphanumeric': 0.10872242749972008, 'fraction_numerical': 0.0021274213413951405, 'mean_word_length': 2.9750778816199377, 'pattern_counts': {'":': 4, '<': 7, '<?xml version=': 0, '>': 7, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, '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': '2600388', 'n_tokens_mistral': 2659, 'n_tokens_neox': 2594, 'n_words': 672}