Last active
October 1, 2019 12:37
-
-
Save laundmo/767877c63f31eadbcc77e40323052314 to your computer and use it in GitHub Desktop.
How to catch anything in python
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/python3 | |
from inspect import getframeinfo, stack | |
verbose = True # set to false if only the actual error should be shown, and not resulting errors | |
class Any(): | |
""" | |
Class to be used as a stand in for anything that doesn't exist. | |
""" | |
def __init__(self, func=None, name="Unknown"): | |
self.name=name | |
if func: | |
try: | |
self.name = func.__name__ | |
except: | |
pass | |
def __getattr__(self, attr): | |
"""Handle attributes of nonexistent things""" | |
if verbose: print(" {} does not exist in empty return by func: {}".format(attr, self.name)) | |
return Any(name=attr) | |
def __getitem__(self, key): | |
"""handle list/dict gets of nonexistent things""" | |
if verbose: print(" [{}] does not exist in empty return by func: {}".format(key, self.name)) | |
return Any(name=key) | |
def __str__(self): | |
return "error in func: {}".format(self.name) | |
def __repr__(self): | |
return str(self) | |
def __call__(self, *args, **kwargs): | |
"""handle calls of nonexistent things""" | |
if verbose: print(" {} is not callable".format(self.name)) | |
return Any(name="{}()".format(self.name)) | |
def trymod(base, funcname, *args, **kwargs): | |
"""wrap a function of a module in a try/except""" | |
try: | |
for e in funcname.split("."): # handle multiple | |
base = getattr(base, e) | |
return base(*args, **kwargs) | |
except Exception as e: | |
caller = getframeinfo(stack()[1][0]) | |
print("{0.filename}:{0.lineno} - {1}".format(caller, e)) # print error: never pass silently | |
return Any(name=base.__name__ + "." + funcname) # return Any object on error | |
def tryfunc(func, *args, **kwargs): | |
"""wrap a function in a try/except""" | |
try: | |
return func(*args, **kwargs) | |
except Exception as e: | |
caller = getframeinfo(stack()[1][0]) | |
print("{0.filename}:{0.lineno} - {1}".format(caller, e)) # print error: never pass silently | |
return Any(func) # return Any object on error | |
# EXAMPLE USAGE | |
def erronous_func(test): | |
print(test) | |
raise AttributeError | |
tryfunc(erronous_func, "test argument")[0].someattr.somefunc()["somekey"] | |
# test.py:65 - | |
# [0] does not exist in empty return by func: erronous_func | |
# someattr does not exist in empty return by func: 0 | |
# somefunc does not exist in empty return by func: someattr | |
# somefunc is not callable | |
# [somekey] does not exist in empty return by func: somefunc() | |
import datetime | |
trymod(datetime, "datetime.fromtimestamp") | |
# test.py:66 - fromtimestamp() missing required argument 'timestamp' (pos 1) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Tested in python 3.7.4
Any recommendations welcome!
thoughts: