I've written a class to handle my custom errors in Python. The idea is to simplify raising exception with custom messages, all you should do is raise the class and pass it a message.
Everything in the code uses only built-in Python features.
I'd like your feedback on how this implementation could be improved in terms of efficiency and best practices for Python error handling.
Also, I’d like to know if it’s okay to use this approach in my future projects, or if it’s something unnecessary or not recommended in real-world applications.
Here's the code:
import inspect
import linecache
class CustomError(Exception):
"""
msg: custom error message
info: display file/line/func info
"""
def __init__(self, msg:str, info:bool = False):
super().__init__(msg)
self.info = info
frame_current = inspect.currentframe()
frame_error = None
self.line = 0
self.file_name = "<unknown file>"
self.func_name = "<unknown func>"
if frame_current:
try:
frame_error = frame_current.f_back
code = frame_error.f_code
self.line = frame_error.f_lineno
self.file_name = code.co_filename
self.func_name = code.co_name
finally:
del frame_error
del frame_current
self.source_line = linecache.getline(self.file_name,self.line).strip()
if not self.source_line:
self.source_line = "<unavailable source>"
def __str__(self):
base_msg = super().__str__()
if self.info:
return (
f"CustomError: {base_msg}\n"
f" File {self.file_name}, line {self.line} in {self.func_name}\n"
f" {self.source_line}\n"
)
return f"CustomError: {base_msg}"
def __repr__(self):
return(
f"{self.__class__.__name__}("
f"msg={super().__str__()!r},"
f"info={self.info!r},"
f"file={self.file_name!r},"
f"line={self.line!r},"
f"func={self.func_name!r},"
f"source={self.source_line!r})"
)
# demo (err: empty string)
if __name__ == "__main__":
def demo_function():
print("Whats your Name?")
try:
user_input = input()
if user_input == "":
empty_string_err = CustomError("user input is empty!")
raise empty_string_err
except CustomError as e:
print(f"{e}")
demo_function()
True, then the line printed out is the line on which theCustomErrorwas created and not the line on which it was raised. So wouldn't it be better if those two "events" (creation and raising of theCustomerError) occurred on the same line, i.e.raise CustomError("user input is empty!", info=True)? \$\endgroup\$user_input = input()\$\endgroup\$