# Path: valohai_cli/utils/levenshtein.py
# def levenshtein(a: str, b: str) -> int:
#     "Calculates the Levenshtein distance between a and b."
#     n, m = len(a), len(b)
#     if n > m:
#         # Make sure n <= m, to use O(min(n,m)) space
#         a, b = b, a
#         n, m = m, n
# 
#     current = list(range(n + 1))
#     for i in range(1, m + 1):
#         previous, current = current, [i] + [0] * n
#         for j in range(1, n + 1):
#             add, delete = previous[j] + 1, current[j - 1] + 1
#             change = previous[j - 1]
#             if a[j - 1] != b[i - 1]:
#                 change = change + 1
#             current[j] = min(add, delete, change)
# 
#     return current[n]


from typing import Optional
from click import NoSuchOption, OptionParser
from click.parser import ParsingState
from .levenshtein import levenshtein




class FriendlyOptionParser(OptionParser):
    """
    A friendlier version of OptionParser that uses Levenshtein distances to figure out
    if the user has just misspelled an option name.
    """

    def _match_long_opt(self, opt: str, explicit_value: Optional[str], state: ParsingState) -> None:
        try:
            super()._match_long_opt(opt, explicit_value, state)
        except NoSuchOption as nse:
            if not nse.possibilities:
                # No possibilities were guessed, so attempt some deeper magic
                nse.possibilities = [
                    word
                    for word
                    in self._long_opt

# Path: valohai_cli/utils/levenshtein.py
# def levenshtein(a: str, b: str) -> int:
#     "Calculates the Levenshtein distance between a and b."
#     n, m = len(a), len(b)
#     if n > m:
#         # Make sure n <= m, to use O(min(n,m)) space
#         a, b = b, a
#         n, m = m, n
# 
#     current = list(range(n + 1))
#     for i in range(1, m + 1):
#         previous, current = current, [i] + [0] * n
#         for j in range(1, n + 1):
#             add, delete = previous[j] + 1, current[j - 1] + 1
#             change = previous[j - 1]
#             if a[j - 1] != b[i - 1]:
#                 change = change + 1
#             current[j] = min(add, delete, change)
# 
#     return current[n]


# Path: valohai_cli/utils/friendly_option_parser.py
from typing import Optional
from click import NoSuchOption, OptionParser
from click.parser import ParsingState
from .levenshtein import levenshtein





class FriendlyOptionParser(OptionParser):
    """
    A friendlier version of OptionParser that uses Levenshtein distances to figure out
    if the user has just misspelled an option name.
    """

    def _match_long_opt(self, opt: str, explicit_value: Optional[str], state: ParsingState) -> None:
        try:
            super()._match_long_opt(opt, explicit_value, state)
        except NoSuchOption as nse:
            if not nse.possibilities:
                # No possibilities were guessed, so attempt some deeper magic
                nse.possibilities = [
                    word
                    for word
                    in self._long_opt

                    if levenshtein(