Source code for erroraffirmations.affirmations

"""Affirmations.

This module adds affirmations to the end of Python error messages, so that
you feel better about your errors.
"""

# Required libraries
from typing import Iterable, Union
import sys
import random
from pkg_resources import resource_stream


# Parameters
DEFAULT_FILE = resource_stream("erroraffirmations",
                               "data/affirmations.txt")
AFFIRMATIONS = Union[str, Iterable[str]]

# Set of affirmations to choose from, users can edit this set to add their
# own or remove ones they don't like using the functions below. This set
# should not be edited directly.
_affirmations = set()


[docs]def add_affirmations(affirmations: AFFIRMATIONS) -> None: """Add affirmation(s) to the set of affirmations. Parameters ---------- affirmations: str or iterable of str An encouraging message to help you feel better about your errors. Or a collection of such messages. """ if isinstance(affirmations, str): _affirmations.add(affirmations) return elif isinstance(affirmations, Iterable): _affirmations.update(affirmations) return else: raise TypeError("affirmations must be a string or iterable of strings")
[docs]def remove_affirmations(affirmations: AFFIRMATIONS) -> None: """Remove affirmation(s) from the set of affirmations. Parameters ---------- affirmations: str or iterable of str An encouraging message to help you feel better about your errors. Or a collection of such messages. """ if isinstance(affirmations, str): _affirmations.remove(affirmations) return elif isinstance(affirmations, Iterable): _affirmations.difference_update(affirmations) return else: raise TypeError("affirmations must be a string or iterable of strings")
[docs]def clear_affirmations() -> None: """Clear the set of affirmations.""" _affirmations.clear()
[docs]def load_affirmations_from_file(file: str, append: bool = True) -> None: """Load affirmations from a file. Parameters ---------- file: str Path to file containing affirmations, one per line. append: bool, optional Whether to append affirmations to the existing set of affirmations """ with open(file, "r") as f: if not append: clear_affirmations() for line in f: add_affirmations(line.strip())
[docs]def get_affirmations() -> set: """Return a copy of the set of affirmations. Returns ------- affirmations: set A set of encouraging messages to help you feel better about your errors. """ return _affirmations.copy()
[docs]def get_random_affirmation() -> str: """Return a random affirmation. Returns ------- affirmation: str An encouraging message to help you feel better about your errors. """ return random.choice(list(_affirmations))
[docs]def reset_affirmations() -> None: """Reset affirmations to the defaults from the default file.""" load_affirmations_from_file(DEFAULT_FILE.name, append=False)
# Load default affirmations from default file reset_affirmations() # Option to turn off affirmations _affirmations_enabled = True # On by default (why else would you use this?)
[docs]def disable_affirmations() -> None: """Disable affirmations.""" global _affirmations_enabled _affirmations_enabled = False
[docs]def enable_affirmations() -> None: """Enable affirmations.""" global _affirmations_enabled _affirmations_enabled = True
[docs]def affirmations_enabled() -> bool: """Return whether affirmations are enabled. Returns ------- affirmations_enabled: bool Whether affirmations are enabled. """ return _affirmations_enabled
# Core functionality to add affirmations to error messages. This is done by # replacing the default Python excepthook with one that prints an affirmation # after the error message. sys.base_excepthook = sys.excepthook def affirming_excepthook(*args) -> None: """Print an affirmation after the standard error message. Parameters ---------- *args: tuple Arguments passed to the standard sys excepthook """ # Start with normal error message sys.base_excepthook(*args) # type: ignore # End there are no affirmations, or affirmations are disabled if (len(_affirmations) == 0) | (not _affirmations_enabled): return # Otherwise, print a random affirmation sys.stderr.write(f'\n{get_random_affirmation()}\n') # Override the default excepthook with the affirming one sys.excepthook = affirming_excepthook