1

I tried to redirect the entire console output of a specific part of my python code to a textfile following the advice of this post.

According to that post, it should work with contextlib.redirect_stdout(), but when the first print()-command appears within my custom function custom_function_with_internal_print_calls(), it throws the AttributeError: 'str' object has no attribute 'write'.

dummy_file = "dummy_textfile.txt"  # file to which the stdout shall be redirected

with contextlib.redirect_stdout(dummy_file):
    # Direct print()-function call
    print("Informative string which shall go to the textfile instead of the console.")

    # Indirect print()-function calls (internally)
    custom_function_with_internal_print_calls(**kwargs)

EDIT: In my particular case, instead of a print()-function within the with-environment, I have a custom function which has internal calls to Python's built-in print()-function. It shouldn't matter if the print()-function appears inside another function, or directly at the top-level to reproduce the error.

Options already tried: Other workarounds don't seem to provide the solution I'm looking for,such as

redefining the print()-function or

writing a decorator for python 2.7x (as I'm using python 3.7x), or also

redirecting the print()-function to a file object via print('Filename:', filename, file=f). The latter would mean in my case to pass a file-handler to all sub-functions in my enclosed function of choice, which is too much extra code modification for this special case.

I hope to be able to employ just the environment with contextlib.redirect_stdout(dummy_file): wrapped around my function in order to redirect every console output of this very function to the dummy_file.

The documentation of contextlib.redirect_stdout() doesn't help me either. Thanks in advance for suggestions.

Andreas L.
  • 3,239
  • 5
  • 26
  • 65
  • 1
    Post your whole code. – ruohola Jan 15 '20 at 17:43
  • 1
    The posted code does not contain a reference to an attribute named `write`, so I don't see how we can help. – John Gordon Jan 15 '20 at 17:47
  • Please post a proper [mcve] (not "your whole code" - only the minimal code required to reproduce the issue). – bruno desthuilliers Jan 15 '20 at 18:08
  • @JohnGordon I guess we can assume that `print_out_all_TIFF_Tags_n_filter_for_desired_TAGs` contains either `sys.stdout.write()` or `print()` calls (the later being mostly a wrapper around the first). – bruno desthuilliers Jan 15 '20 at 18:10
  • I've just edited now my post. Exactly, the print()-function causes the error, and it doesn't matter apparently at which nested level it is called (within my custom function). Anyway, I've solved the problem already as can be seen in my answer below. I have to pass a filehandler instead of a filepath to the contextlib.redirect_stdout() - function. – Andreas L. Jan 15 '20 at 18:36
  • I'm about to open another question, because I'd like to redirect as well internal calls of via subprocess.call(cmd_string, stdout=filehandler) to the dummy-textfile, but it exists with the error "FileNotFoundError: [Errno 2] No such file or directory:". – Andreas L. Jan 15 '20 at 18:38

1 Answers1

1

I found the solution via passing a file-handler "f" to the function contextlib.redirect_stdout(f) instead of the filepath dummy_file, as suggested in this post.

dummy_file = "dummy_textfile.txt"  # file to which the stdout shall be redirected

with open(dummy_file, 'w') as f:
    with contextlib.redirect_stdout(f):
        # Indirect print()-function calls (internally)
        custom_function_with_internal_print_calls(**kwargs)

With this, all print()-function calls write to the dummy_file and restores the standard console output afterwards.

Andreas L.
  • 3,239
  • 5
  • 26
  • 65