Search code examples
colorspipazure-clicolorama

Can the default error color be changed in Python?


When running Python scripts or programs built using Python, errors are emitted in dark red. As I get older, this is getting harder for me to read, to the point I have to squint, magnify, or fuss with the console properties and re-run commands.

I really do not want to change the console defaults because other programs generally do not have this problem, and it just seems to be Python that does not honor the hosting console's color settings. I also do not know ahead of time which programs may have been built with python (Azure CLI for example) to set the colors ahead of time.

Is there a way to change the DarkRed that python wants to use for errors to a color that is easier to distinguish, like "regular" Red? For any py script or program that runs on my machine?

enter image description here

Edit

Here is an example of invoking a program written using Python and the dark red. My py scripts library is on my work computer.

enter image description here

Edit 2

It is pip that was the other thing that uses the dark red.

enter image description here


Solution

  • First, python is innocent. The culprit is azure-cli itself. It uses a lib named knack for configuring logging. And knack uses colorama to configure colored output.

    But the problem is, the RED in colorama is \033[31m. Which is what you see, somehow like dim red.

    So the solution is simple, we manually modify that knack package.

    Suppose your azure-cli is installed at C:\Program Files (x86)\Microsoft SDKs\Azure\CLI2.

    1. Then go to C:\Program Files (x86)\Microsoft SDKs\Azure\CLI2\Lib\site-packages, delete that knack directory or rename it.
    2. Go to https://github.com/Microsoft/knack, download the package. add one line at line 47:
    class _CustomStreamHandler(logging.StreamHandler):
        COLOR_MAP = None
    
        @classmethod
        def get_color_wrapper(cls, level):
            if not cls.COLOR_MAP:
                import colorama
    
                def _color_wrapper(color_marker):
                    def wrap_msg_with_color(msg):
                        return '{}{}{}'.format(color_marker, msg, colorama.Style.RESET_ALL)
                    return wrap_msg_with_color
    
                colorama.Fore.RED = "\033[31;1m"  # <- add this line
                cls.COLOR_MAP = {
                    logging.CRITICAL: _color_wrapper(colorama.Fore.RED),
                    logging.ERROR: _color_wrapper(colorama.Fore.RED),
                    logging.WARNING: _color_wrapper(colorama.Fore.YELLOW),
                    logging.INFO: _color_wrapper(colorama.Fore.GREEN),
                    logging.DEBUG: _color_wrapper(colorama.Fore.CYAN)
                }
    
            return cls.COLOR_MAP.get(level, None)
        ...
    
    1. Copy modifed package to corresponding location.
    2. Test it again.
    3. Bingbangba!