Commit 51cd8724 authored by Christof Schulze's avatar Christof Schulze 😎
Browse files

added some new display options, wrapping unsafe parameters, Copyright and License information added

parent 7c3842f2
Loading
Loading
Loading
Loading
+17 −1
Original line number Diff line number Diff line
#!/usr/bin/env python3
 No newline at end of file
# GNU Lesser General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/lgpl-3.0.txt)
# (c) 2019, Christof Schulze <christof.schulze@fau.de>
#
# This file is part of Ammsml
#
# Ammsml is free software: you can redistribute it and/or modify it
# under the terms of the GNU Lesser General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ammsml is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU Lesser General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public License
# along with Ammsml.  If not, see <http://www.gnu.org/licenses/>.
+17 −1
Original line number Diff line number Diff line
#!/usr/bin/env python3
# GNU Lesser General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/lgpl-3.0.txt)
# (c) 2019, Christof Schulze <christof.schulze@fau.de>
#
# This file is part of Ammsml
#
# Ammsml is free software: you can redistribute it and/or modify it
# under the terms of the GNU Lesser General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ammsml is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU Lesser General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public License
# along with Ammsml.  If not, see <http://www.gnu.org/licenses/>.

import sys
import re
+131 −3
Original line number Diff line number Diff line
#!/usr/bin/env python3
# (c) 2019, Christof Schulze <christof.schulze@fau.de>
#
# This file is part of Ammsml
#
# Ammsml is free software: you can redistribute it and/or modify it
# under the terms of the GNU Lesser General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ammsml is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU Lesser General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public License
# along with Ammsml.  If not, see <http://www.gnu.org/licenses/>.


import os
import sys
import locale
import errno
import fcntl
import time
import textwrap
import subprocess

from struct import unpack, pack
from termios import TIOCGWINSZ

from utils.color import stringc
from utils.color import BColors
from utils.parsing import to_text
from utils.errors import AMMSMLError
from utils.singleton import Singleton
from config import constants as C
from utils.six import with_metaclass
from utils.wrap import wrap_var


b_COW_PATHS = (
@@ -22,6 +44,7 @@ b_COW_PATHS = (
    b"/opt/local/bin/cowsay",  # MacPorts path for cowsay
)


class Display(with_metaclass(Singleton, object)):

    def __init__(self, verbosity: int=0):
@@ -34,6 +57,35 @@ class Display(with_metaclass(Singleton, object)):
        self._warns = {}
        self._errors = {}

        self.b_cowsay = None
        self.noncow = C.AMMSML_COW_SELECTION

        self.set_cowsay_info()

        if self.b_cowsay:
            try:
                cmd = subprocess.Popen([self.b_cowsay, "-l"], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
                (out, err) = cmd.communicate()
                self.cows_available = set([to_text(c) for c in out.split()])
                if C.AMMSML_COW_WHITELIST and any(C.AMMSML_COW_WHITELIST):
                    self.cows_available = set(C.AMNMSML_COW_WHITELIST).intersection(self.cows_available)
            except Exception:
                # could not execute cowsay for some reason
                self.b_cowsay = False

        self._set_column_width()

    def set_cowsay_info(self):
        if C.AMMSML_NOCOWS:
            return

        if C.AMMSML_COW_PATH:
            self.b_cowsay = C.AMMSML_COW_PATH
        else:
            for b_cow_path in b_COW_PATHS:
                if os.path.exists(b_cow_path):
                    self.b_cowsay = b_cow_path

    def display(self, msg, color=None, stderr=False, screen_only=False, log_only=False):
        """ Display a message to the user
        Note: msg *must* be a unicode string to prevent UnicodeError tracebacks.
@@ -158,3 +210,79 @@ class Display(with_metaclass(Singleton, object)):
            star_len = 3
        stars = u"*" * star_len
        self.display(u"\n%s %s" % (msg, stars), color=color)

    def error(self, msg, wrap_text=True):
        if wrap_text:
            new_msg = "\n[ERROR]: %s" % msg
            wrapped = textwrap.wrap(new_msg, self.columns)
            new_msg = "\n".join(wrapped) + "\n"
        else:
            new_msg = "ERROR! %s" % msg
        if new_msg not in self._errors:
            self.display(new_msg, color=C.COLOR_ERROR, stderr=True)
            self._errors[new_msg] = 1

    @staticmethod
    def prompt(msg):
        prompt_string = to_text(msg, encoding=Display._output_encoding())
        if sys.version_info >= (3,):
            # Convert back into text on python3.  We do this double conversion
            # to get rid of characters that are illegal in the user's locale
            prompt_string = to_text(prompt_string)

        return input(prompt_string)

    def do_var_prompt(self, varname, private=True, prompt=None, confirm=False, default=None, unsafe=None):

        result = None
        if sys.__stdin__.isatty():

            do_prompt = self.prompt

            if prompt and default is not None:
                msg = "%s [%s]: " % (prompt, default)
            elif prompt:
                msg = "%s: " % prompt
            else:
                msg = 'input for %s: ' % varname

            if confirm:
                while True:
                    result = do_prompt(msg, private)
                    second = do_prompt("confirm " + msg, private)
                    if result == second:
                        break
                    self.display("***** VALUES ENTERED DO NOT MATCH ****")
            else:
                result = do_prompt(msg, private)
        else:
            result = None
            self.warning("Not prompting as we are not in interactive mode")

        # if result is false and default is not None
        if not result and default is not None:
            result = default

        # handle utf-8 chars
        result = to_text(result, errors='surrogate_or_strict')

        if unsafe:
            result = wrap_var(result)
        return result

    @staticmethod
    def _output_encoding(stderr=False):
        encoding = locale.getpreferredencoding()
        # https://bugs.python.org/issue6202
        # Python2 hardcodes an obsolete value on Mac.  Use MacOSX defaults
        # instead.
        if encoding in ('mac-roman',):
            encoding = 'utf-8'
        return encoding

    def _set_column_width(self):
        if os.isatty(0):
            tty_size = unpack('HHHH', fcntl.ioctl(0, TIOCGWINSZ, pack('HHHH', 0, 0, 0, 0)))[1]
        else:
            tty_size = 0
        self.columns = max(79, tty_size - 1)
 No newline at end of file
+17 −2
Original line number Diff line number Diff line
#!/usr/bin/env python3
# GNU Lesser General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/lgpl-3.0.txt)
# (c) 2019, Christof Schulze <christof.schulze@fau.de>
#
# This file is part of Ammsml
#
# Ammsml is free software: you can redistribute it and/or modify it
# under the terms of the GNU Lesser General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ammsml is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU Lesser General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public License
# along with Ammsml.  If not, see <http://www.gnu.org/licenses/>.


class AMMSMLError(Exception):
@@ -19,4 +35,3 @@ class TemplateParsingError(AMMSMLError):
class AMMSMLOptionsError(AMMSMLError):

    pass
+18 −0
Original line number Diff line number Diff line
# GNU Lesser General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/lgpl-3.0.txt)
# (c) 2019, Christof Schulze <christof.schulze@fau.de>
#
# This file is part of Ammsml
#
# Ammsml is free software: you can redistribute it and/or modify it
# under the terms of the GNU Lesser General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ammsml is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU Lesser General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public License
# along with Ammsml.  If not, see <http://www.gnu.org/licenses/>.

import yaml

from utils.parsing import to_text
Loading