commit 47f608b05c0085a5acfb76b08a9efe916b1e09e9 Author: Damian Johnson atagar@torproject.org Date: Sun Dec 2 22:31:22 2012 -0800
Support for SIGNAL events
Implementation and testing for SIGNAL events. This moves tor's signals to an enum, which also makes the Controller's signal() method a little nicer. --- stem/__init__.py | 32 ++++++++++++++++++++++++++++++++ stem/control.py | 14 ++------------ stem/response/events.py | 36 ++++++++++++++++++++++++++++++++++++ test/unit/response/events.py | 9 +++++++++ 4 files changed, 79 insertions(+), 12 deletions(-)
diff --git a/stem/__init__.py b/stem/__init__.py index ea3a5eb..d7ec4f8 100644 --- a/stem/__init__.py +++ b/stem/__init__.py @@ -28,6 +28,22 @@ Library for working with the tor process. **DEBUG** low level runtime information =========== ===========
+.. data:: Signal (enum) + + Signals that the tor process will accept. + + ========================= =========== + Signal Description + ========================= =========== + **RELOAD** or **HUP** reloads our torrc + **SHUTDOWN** or **INT** shut down, waiting ShutdownWaitLength first if we're a relay + **DUMP** or **USR1** dumps information about open connections and circuits to our log + **DEBUG** or **USR2** switch our logging to the DEBUG runlevel + **HALT** or **TERM** exit tor immediately + **NEWNYM** switch to new circuits, so new application requests don't share any circuits with old ones (this also clears our DNS cache) + **CLEARDNSCACHE** clears cached DNS results + ========================= =========== + .. data:: CircStatus (enum)
Statuses that a circuit can be in. Tor may provide statuses not in this enum. @@ -334,6 +350,7 @@ __all__ = [ "SocketError", "SocketClosed", "Runlevel", + "Signal", "CircStatus", "CircBuildFlag", "CircPurpose", @@ -412,6 +429,21 @@ Runlevel = stem.util.enum.UppercaseEnum( "ERR", )
+Signal = stem.util.enum.UppercaseEnum( + "RELOAD", + "HUP", + "SHUTDOWN", + "INT", + "DUMP", + "USR1", + "DEBUG", + "USR2", + "HALT", + "TERM", + "NEWNYM", + "CLEARDNSCACHE", +) + CircStatus = stem.util.enum.UppercaseEnum( "LAUNCHED", "BUILT", diff --git a/stem/control.py b/stem/control.py index a8f7913..ec3273a 100644 --- a/stem/control.py +++ b/stem/control.py @@ -93,6 +93,7 @@ providing its own for interacting at a higher level. **NOTICE** :class:`stem.response.events.LogEvent` **NS** :class:`stem.response.events.NetworkStatusEvent` **ORCONN** :class:`stem.response.events.ORConnEvent` + **SIGNAL** :class:`stem.response.events.SignalEvent` **STATUS_CLIENT** :class:`stem.response.events.StatusEvent` **STATUS_GENERAL** :class:`stem.response.events.StatusEvent` **STATUS_SERVER** :class:`stem.response.events.StatusEvent` @@ -1327,18 +1328,7 @@ class Controller(BaseController): """ Sends a signal to the Tor client.
- :param str signal: type of signal to be sent. Must be one of the following... - - * **RELOAD** or **HUP** - reload configuration - * **SHUTDOWN** or **INT** - shut down, waiting ShutdownWaitLength first - if we're a relay - * **DUMP** or **USR1** - dump log information about open connections and - circuits - * **DEBUG** or **USR2** - switch logging to the DEBUG runlevel - * **HALT** or **TERM** - exit immediately - * **NEWNYM** - switch to new circuits, so new application requests don't - share any circuits with old ones (this also clears our DNS cache) - * **CLEARDNSCACHE** - clears cached DNS results + :param stem.Signal signal: type of signal to be sent
:raises: :class:`stem.InvalidArguments` if signal provided wasn't recognized """ diff --git a/stem/response/events.py b/stem/response/events.py index 8e437d9..98e1bf3 100644 --- a/stem/response/events.py +++ b/stem/response/events.py @@ -599,6 +599,41 @@ class ORConnEvent(Event): log_id = "event.orconn.unknown_reason.%s" % self.reason log.log_once(log_id, log.INFO, unrecognized_msg % ('reason', self.reason))
+class SignalEvent(Event): + """ + Event that indicates that tor has received and acted upon a signal being sent + to the process. As of tor version 0.2.4.6 the only signals conveyed by this + event are... + + * RELOAD + * DUMP + * DEBUG + * NEWNYM + * CLEARDNSCACHE + + This was introduced in tor version 0.2.3.1. + + :var stem.Signal signal: signal that tor received + """ + + _POSITIONAL_ARGS = ("signal",) + + def _parse(self): + # log if we recieved an unrecognized signal + unrecognized_msg = UNRECOGNIZED_ATTR_MSG % ("SIGNAL", self) + + expected_signals = ( + stem.Signal.RELOAD, + stem.Signal.DUMP, + stem.Signal.DEBUG, + stem.Signal.NEWNYM, + stem.Signal.CLEARDNSCACHE, + ) + + if not self.signal in expected_signals: + log_id = "event.signal.unknown_signal.%s" % self.signal + log.log_once(log_id, log.INFO, unrecognized_msg % ('signal', self.signal)) + class StatusEvent(Event): """ Notification of a change in tor's state. These are generally triggered for @@ -729,6 +764,7 @@ EVENT_TYPE_TO_CLASS = { "NOTICE": LogEvent, "NS": NetworkStatusEvent, "ORCONN": ORConnEvent, + "SIGNAL": SignalEvent, "STATUS_CLIENT": StatusEvent, "STATUS_GENERAL": StatusEvent, "STATUS_SERVER": StatusEvent, diff --git a/test/unit/response/events.py b/test/unit/response/events.py index b74f4ad..6d5f0d3 100644 --- a/test/unit/response/events.py +++ b/test/unit/response/events.py @@ -499,6 +499,15 @@ class TestEvents(unittest.TestCase): self.assertEqual(ORClosureReason.DONE, event.reason) self.assertEqual(None, event.circ_count)
+ def test_signal_event(self): + event = _get_event("650 SIGNAL DEBUG") + self.assertTrue(isinstance(event, stem.response.events.SignalEvent)) + self.assertEqual("SIGNAL DEBUG", str(event)) + self.assertEqual(Signal.DEBUG, event.signal) + + event = _get_event("650 SIGNAL DUMP") + self.assertEqual(Signal.DUMP, event.signal) + def test_status_event_consensus_arrived(self): event = _get_event(STATUS_CLIENT_CONSENSUS_ARRIVED)
tor-commits@lists.torproject.org