Example #1
0
    def __init__(self, destination, reactor):
        """
        @param destination: The underlying destination for log files. This will
            be called from a non-reactor thread.

        @param reactor: The main reactor.
        """
        self._destination = destination
        self._reactor = Reactor()
        # Ick. See https://twistedmatrix.com/trac/ticket/6982 for real solution.
        self._reactor._registerAsIOThread = False
        self._mainReactor = reactor
        self._thread = None
Example #2
0
    def __init__(self, destination, reactor):
        """
        @param destination: The underlying destination for log files. This will
            be called from a non-reactor thread.

        @param reactor: The main reactor.
        """
        self._destination = destination
        self._reactor = Reactor()
        # Ick. See https://twistedmatrix.com/trac/ticket/6982 for real solution.
        self._reactor._registerAsIOThread = False
        self._mainReactor = reactor
        self._thread = None
Example #3
0
    def __init__(self, logFile, reactor):
        """
        @param logFile: A C{file}-like object that is at the end of its existing
           contents (e.g. opened with append mode) and accepts bytes.
        @type logFile: C{file}, or any file-like object with C{write}, C{flush}
            and C{close} methods e.g. a L{twisted.python.logfile.LogFile} if you
            want log rotation.

        @param reactor: The main reactor.
        """
        self._logFile = logFile
        self._reactor = Reactor()
        # Ick. See https://twistedmatrix.com/trac/ticket/6982 for real solution.
        self._reactor._registerAsIOThread = False
        self._mainReactor = reactor
        self._thread = None
Example #4
0
    def __init__(self, logFile, reactor):
        """
        @param logFile: A C{file}-like object that is at the end of its existing
           contents (e.g. opened with append mode) and accepts bytes.
        @type logFile: C{file}, or any file-like object with C{write}, C{flush}
            and C{close} methods e.g. a L{twisted.python.logfile.LogFile} if you
            want log rotation.

        @param reactor: The main reactor.
        """
        self._logFile = logFile
        self._reactor = Reactor()
        # Ick. See https://twistedmatrix.com/trac/ticket/6982 for real solution.
        self._reactor._registerAsIOThread = False
        self._mainReactor = reactor
        self._thread = None
Example #5
0
class ThreadedWriter(Service):
    """
    An non-blocking Eliot log destination that wraps a blocking
    destination, writing log messages to the latter in a managed thread.

    Unfortunately Python's Queue is not reentrant
    (http://bugs.python.org/issue14976) and neither is RLock
    (http://bugs.python.org/issue13697). In order to queue items in a thread we
    therefore rely on the self-pipe trick, and the easiest way to do that is by
    running another reactor in the thread.

    @ivar _reactor: A private reactor running in a thread which will do the log
        writes.

    @ivar _thread: C{None}, or a L{threading.Thread} running the private
        reactor.
    """

    name = "Eliot Log Writer"

    def __init__(self, destination, reactor):
        """
        @param destination: The underlying destination for log files. This will
            be called from a non-reactor thread.

        @param reactor: The main reactor.
        """
        self._destination = destination
        self._reactor = Reactor()
        # Ick. See https://twistedmatrix.com/trac/ticket/6982 for real solution.
        self._reactor._registerAsIOThread = False
        self._mainReactor = reactor
        self._thread = None

    def startService(self):
        """
        Start the writer thread.
        """
        Service.startService(self)
        self._thread = threading.Thread(target=self._writer)
        self._thread.start()
        addDestination(self)

    def stopService(self):
        """
        Stop the writer thread, wait for it to finish.
        """
        Service.stopService(self)
        removeDestination(self)
        self._reactor.callFromThread(self._reactor.stop)
        return deferToThreadPool(
            self._mainReactor, self._mainReactor.getThreadPool(), self._thread.join
        )

    def __call__(self, data):
        """
        Add the data to the queue, to be serialized to JSON and written by the
        writer thread with a newline added.

        @param data: C{bytes} to write to disk.
        """
        self._reactor.callFromThread(self._destination, data)

    def _writer(self):
        """
        The function run by the writer thread.
        """
        self._reactor.run(installSignalHandlers=False)
Example #6
0
class ThreadedFileWriter(Service):
    """
    An Eliot log destination that writes log messages as lines to a file, using
    a managed thread.

    Unfortunately Python's Queue is not reentrant
    (http://bugs.python.org/issue14976) and neither is RLock
    (http://bugs.python.org/issue13697). In order to queue items in a thread we
    therefore rely on the self-pipe trick, and the easiest way to do that is by
    running another reactor in the thread.

    @ivar _reactor: A private reactor running in a thread which will do the log
        writes.

    @ivar _thread: C{None}, or a L{threading.Thread} running the private
        reactor.
    """
    name = u"Eliot Log Writer"

    def __init__(self, logFile, reactor):
        """
        @param logFile: A C{file}-like object that is at the end of its existing
           contents (e.g. opened with append mode) and accepts bytes.
        @type logFile: C{file}, or any file-like object with C{write}, C{flush}
            and C{close} methods e.g. a L{twisted.python.logfile.LogFile} if you
            want log rotation.

        @param reactor: The main reactor.
        """
        self._logFile = logFile
        self._reactor = Reactor()
        # Ick. See https://twistedmatrix.com/trac/ticket/6982 for real solution.
        self._reactor._registerAsIOThread = False
        self._mainReactor = reactor
        self._thread = None

    def startService(self):
        """
        Start the writer thread.
        """
        Service.startService(self)
        self._thread = threading.Thread(target=self._writer)
        self._thread.start()
        addDestination(self)

    def stopService(self):
        """
        Stop the writer thread, wait for it to finish.
        """
        Service.stopService(self)
        removeDestination(self)
        self._reactor.callFromThread(self._reactor.stop)
        return deferToThreadPool(self._mainReactor,
                                 self._mainReactor.getThreadPool(),
                                 self._thread.join)

    def __call__(self, data):
        """
        Write given bytes to the queue, to be written by the writer thread with a
        newline added.

        @param data: C{bytes} to write to disk.
        """
        self._reactor.callFromThread(self._logFile.write, data + b'\n')

    def _writer(self):
        """
        The function run by the writer thread.
        """
        self._reactor.run(installSignalHandlers=False)
        self._logFile.close()
Example #7
0
class ThreadedFileWriter(Service):
    """
    An Eliot log destination that writes log messages as lines to a file, using
    a managed thread.

    Unfortunately Python's Queue is not reentrant
    (http://bugs.python.org/issue14976) and neither is RLock
    (http://bugs.python.org/issue13697). In order to queue items in a thread we
    therefore rely on the self-pipe trick, and the easiest way to do that is by
    running another reactor in the thread.

    @ivar _reactor: A private reactor running in a thread which will do the log
        writes.

    @ivar _thread: C{None}, or a L{threading.Thread} running the private
        reactor.
    """
    name = u"Eliot Log Writer"


    def __init__(self, logFile, reactor):
        """
        @param logFile: A C{file}-like object that is at the end of its existing
           contents (e.g. opened with append mode) and accepts bytes.
        @type logFile: C{file}, or any file-like object with C{write}, C{flush}
            and C{close} methods e.g. a L{twisted.python.logfile.LogFile} if you
            want log rotation.

        @param reactor: The main reactor.
        """
        self._logFile = logFile
        self._reactor = Reactor()
        # Ick. See https://twistedmatrix.com/trac/ticket/6982 for real solution.
        self._reactor._registerAsIOThread = False
        self._mainReactor = reactor
        self._thread = None


    def startService(self):
        """
        Start the writer thread.
        """
        Service.startService(self)
        self._thread = threading.Thread(target=self._writer)
        self._thread.start()
        addDestination(self)


    def stopService(self):
        """
        Stop the writer thread, wait for it to finish.
        """
        Service.stopService(self)
        removeDestination(self)
        self._reactor.callFromThread(self._reactor.stop)
        return deferToThreadPool(
            self._mainReactor, self._mainReactor.getThreadPool(),
            self._thread.join)


    def __call__(self, data):
        """
        Write given bytes to the queue, to be written by the writer thread with a
        newline added.

        @param data: C{bytes} to write to disk.
        """
        self._reactor.callFromThread(self._logFile.write, data + b'\n')


    def _writer(self):
        """
        The function run by the writer thread.
        """
        self._reactor.run(installSignalHandlers=False)
        self._logFile.close()
Example #8
0
class ThreadedWriter(Service):
    """
    An non-blocking Eliot log destination that wraps a blocking
    destination, writing log messages to the latter in a managed thread.

    Unfortunately Python's Queue is not reentrant
    (http://bugs.python.org/issue14976) and neither is RLock
    (http://bugs.python.org/issue13697). In order to queue items in a thread we
    therefore rely on the self-pipe trick, and the easiest way to do that is by
    running another reactor in the thread.

    @ivar _reactor: A private reactor running in a thread which will do the log
        writes.

    @ivar _thread: C{None}, or a L{threading.Thread} running the private
        reactor.
    """

    name = "Eliot Log Writer"

    def __init__(self, destination, reactor):
        """
        @param destination: The underlying destination for log files. This will
            be called from a non-reactor thread.

        @param reactor: The main reactor.
        """
        self._destination = destination
        self._reactor = Reactor()
        # Ick. See https://twistedmatrix.com/trac/ticket/6982 for real solution.
        self._reactor._registerAsIOThread = False
        self._mainReactor = reactor
        self._thread = None

    def startService(self):
        """
        Start the writer thread.
        """
        Service.startService(self)
        self._thread = threading.Thread(target=self._writer)
        self._thread.start()
        addDestination(self)

    def stopService(self):
        """
        Stop the writer thread, wait for it to finish.
        """
        Service.stopService(self)
        removeDestination(self)
        self._reactor.callFromThread(self._reactor.stop)
        return deferToThreadPool(self._mainReactor,
                                 self._mainReactor.getThreadPool(),
                                 self._thread.join)

    def __call__(self, data):
        """
        Add the data to the queue, to be serialized to JSON and written by the
        writer thread with a newline added.

        @param data: C{bytes} to write to disk.
        """
        self._reactor.callFromThread(self._destination, data)

    def _writer(self):
        """
        The function run by the writer thread.
        """
        self._reactor.run(installSignalHandlers=False)