Module thread_io::write

source ·
Expand description

This module contains functions for writing in a background thread.

  • The simplest to use is the writer function. It accepts any io::Write instance that implements Send.
  • The writer_init function handles cases where the wrapped writer cannot be sent safely across the thread boundary by providing a closure for initializing the writer in the background thread.
  • writer_finish and writer_init_finish provide an additional finish closure, which allows for executing final code after all writing is done, or also for returning the wrapped writer to the main thread. Usually, write calls happen in the background even after func returned, finalizing code should thus always go after the writer...() function call or be placed in the finish closure (useful for non-Send writers).

Error handling

  • io::Errors occurring during writing in the background are returned by the write method of the writer in the main thread as expected, but with a delay of at east one call.
  • The func closure running in the main thread allows returning errors of any type. However, in contrast to the functions in the read module, the error needs to implement From<io::Error> because additional write calls can happen in the background after func is already finished, and eventual errors have to be returned as well.
  • If an error is returned from func in the main thread, and around the same time a writing error happens in the background thread, which does not reach the main thread due to the reporting delay, the latter will be discarded and the error from func returned instead. Due to this, there is no guarantee on how much data is still written after the custom error occurs.
  • panics in the background writer are correctly forwarded to the main thread, but are also given lower priority if an error is returned from func.

Flushing

Trying to mimick the expected functionality of io::Write as closely as possible, the writer provided in the func closure in the main thread also forwards flush() calls to the background writer. write and flush calls are guaranteed to be in the same order as in the main thread. A flush call will always trigger the writer in the main thread to send any buffered data to the background before the actual flushing is queued.

In addition, flush() is always called after all writing is done. It is assumed that usually no more data will be written after this, and a call to flush() ensures that that possible flushing errors don’t go unnoticed like they would if the file is closed automatically when dropped. With File, it is still possible that when going out of scope, unreported errors occur when writing OS-internal metadata. To address this, File::sync_all or File::sync_data can be called after the writer call finished, or in the case of non-Send writers in the finish closure of writer_finish / writer_init_finish.

Structs

  • The writer in the main thread

Functions

  • Sends writer to a background thread and provides another writer in the main thread, which then submits its data to the background writer.
  • Like writer, but accepts another closure taking the wrapped writer by value before it goes out of scope (and there is no error). Useful for performing finalizing actions or returning the wrapped writer to the main thread (if it implements Send).
  • Like writer, but the wrapped writer is initialized in a closure (init_writer()) in the background thread. This allows using writers that don’t implement Send.
  • This method takes both an initializing closure (see writer_init), and a closure for finalizing or returning data back to the main thread (see writer_finish).