Search code examples
pythonsmtpd

Can't find stderr print in python smtpd


I am using smtpd and its catching ValueError exceptions I raise in process_message and printing a description to stderr instead of raising the error. What it prints out is the string I construct the ValueError with.

So if I do this in process_message:

raise ValueError("550, This is the error")

I see

550, This is the error

on the console. I cannot for the life of me find what code is causing the print. Is there anyway to override stderr to show a stacktrace each time something is printed or otherwise locate what lines of code are printing out these lines?


Solution

  • You can replace one the standard output streams with something that traces invocations of write():

    import sys
    import traceback
    
    class FileTracer(object):
        def __init__(self, out):
            self.out = out
    
        def write(self, data):
            traceback.print_stack(None, None, sys.__stderr__)
            self.out.write(data)
    
        def flush(self):
            self.out.flush()
    
        def close(self):
            self.out.close()
    
    sys.stderr = FileTracer(sys.stderr)
    
    sys.stderr.write("trigger\n")
    sys.stderr.flush()
    

    Note that I'm using __stderr__ to avoid loops.