'Wraps the .runInteraction() method on the underlying db_pool.'

@defer.inlineCallbacks
def runInteraction(self, desc, func, *args, **kwargs):

    current_context = LoggingContext.current_context()
    start_time = (time.time() * 1000)
    after_callbacks = []
    final_callbacks = []
    def inner_func(conn, *args, **kwargs):
        with LoggingContext('runInteraction') as context:
            sql_scheduling_timer.inc_by(((time.time() * 1000) - start_time))
            if self.database_engine.is_connection_closed(conn):
                logger.debug('Reconnecting    closed    database    connection')
                conn.reconnect()
            current_context.copy_to(context)
            return self._new_transaction(conn, desc, after_callbacks, final_callbacks, current_context, func, *args, **kwargs)
    try:
        with PreserveLoggingContext():
            result = (yield self._db_pool.runWithConnection(inner_func, *args, **kwargs))
        for (after_callback, after_args, after_kwargs) in after_callbacks:
            after_callback(*after_args, **after_kwargs)
    finally:
        for (after_callback, after_args, after_kwargs) in final_callbacks:
            after_callback(*after_args, **after_kwargs)
    defer.returnValue(result)
