[tor-commits] [stem/master] Implement convenience method for handling SAVECONF requests
atagar at torproject.org
atagar at torproject.org
Tue Jul 10 16:32:16 UTC 2012
commit e68adb7fdd465e1780bc4ee1243e0c226add77d9
Author: Ravi Chandra Padmala <neenaoffline at gmail.com>
Date: Wed Jun 27 18:34:15 2012 +0530
Implement convenience method for handling SAVECONF requests
This also changes the Exception structure a bit. I have added an
InsatisfiableRequest class which will be raised when a valid request
couldn't be satisfied by Tor.
I've also added a super class for non-socket non-protocol errors called
OperationFailed. Any error that was raised by an error response returned
by Tor (i.e., one with an error code & a message) should subclass this.
The exceptions now look like
ControllerError - Base exception raised when using the controller.
|- ProtocolError - Malformed socket data.
|- OperationFailed - Tor was unable to successfully complete the operation.
| |- UnsatisfiableRequest - Tor was unable to satisfy a valid request.
| +- InvalidRequest - Invalid request.
| +- InvalidArguments - Invalid request parameters.
+- SocketError - Communication with the socket failed.
+- SocketClosed - Socket has been shut down.
---
stem/control.py | 20 ++++++++++++++++++++
stem/socket.py | 28 ++++++++++++++++++++--------
test/integ/control/controller.py | 20 ++++++++++++++++++++
3 files changed, 60 insertions(+), 8 deletions(-)
diff --git a/stem/control.py b/stem/control.py
index 51804cc..e2bf282 100644
--- a/stem/control.py
+++ b/stem/control.py
@@ -20,6 +20,7 @@ interacting at a higher level.
|- reset_conf - reverts configuration options to their default values
|- set_options - sets or resets the values of multiple configuration options
|- load_conf - loads configuration information as if it was in the torrc
+ |- save_conf - saves configuration information to the torrc
|- get_version - convenience method to get tor version
|- authenticate - convenience method to authenticate the controller
+- protocolinfo - convenience method to get the protocol info
@@ -777,6 +778,25 @@ class Controller(BaseController):
raise stem.socket.InvalidRequest(response.code, response.message)
elif not response.is_ok():
raise stem.socket.ProtocolError("+LOADCONF Received unexpected response\n%s" % str(response))
+
+ def save_conf(self):
+ """
+ Saves the current configuration options into the active torrc file.
+
+ :raises:
+ :class:`stem.socket.ControllerError` if the call fails
+ :class:`stem.socket.OperationFailed` if the client is unable to save the configuration file
+ """
+
+ response = self.msg("SAVECONF")
+ stem.response.convert("SINGLELINE", response)
+
+ if response.is_ok():
+ return True
+ elif response.code == "551":
+ raise stem.socket.OperationFailed(response.code, response.message)
+ else:
+ raise stem.socket.ProtocolError("SAVECONF returned unexpected response code")
def _case_insensitive_lookup(entries, key, default = UNDEFINED):
"""
diff --git a/stem/socket.py b/stem/socket.py
index 7d40056..5492e30 100644
--- a/stem/socket.py
+++ b/stem/socket.py
@@ -28,8 +28,10 @@ as instances of the :class:`stem.response.ControlMessage` class.
ControllerError - Base exception raised when using the controller.
|- ProtocolError - Malformed socket data.
- |- InvalidRequest - Invalid request.
- | +- InvalidArguments - Invalid request parameters.
+ |- OperationFailed - Tor was unable to successfully complete the operation.
+ | |- UnsatisfiableRequest - Tor was unable to satisfy a valid request.
+ | +- InvalidRequest - Invalid request.
+ | +- InvalidArguments - Invalid request parameters.
+- SocketError - Communication with the socket failed.
+- SocketClosed - Socket has been shut down.
"""
@@ -550,9 +552,9 @@ class ControllerError(Exception):
class ProtocolError(ControllerError):
"Malformed content from the control socket."
-class InvalidRequest(ControllerError):
+class OperationFailed(ControllerError):
"""
- Base Exception class for invalid requests
+ Base exception class for failed operations that return an error code
:var str code: error code returned by Tor
:var str message: error message returned by Tor or a human readable error message
@@ -560,21 +562,31 @@ class InvalidRequest(ControllerError):
def __init__(self, code = None, message = None):
"""
- Initializes an InvalidRequest object.
+ Initializes an OperationFailed object.
:param str code: error code returned by Tor
:param str message: error message returned by Tor or a human readable error message
- :returns: object of InvalidRequest class
+ :returns: object of OperationFailed class
"""
- super(InvalidRequest, self).__init__()
+ super(ControllerError, self).__init__()
self.code = code
self.message = message
+class UnsatisfiableRequest(OperationFailed):
+ """
+ Exception raised if Tor was unable to process our request.
+ """
+
+class InvalidRequest(OperationFailed):
+ """
+ Exception raised when the request was invalid or malformed.
+ """
+
class InvalidArguments(InvalidRequest):
"""
- Exception class for invalid requests which contain invalid arguments.
+ Exception class for requests which had invalid arguments.
:var str code: error code returned by Tor
:var str message: error message returned by Tor or a human readable error message
diff --git a/test/integ/control/controller.py b/test/integ/control/controller.py
index 857799d..54f2626 100644
--- a/test/integ/control/controller.py
+++ b/test/integ/control/controller.py
@@ -296,4 +296,24 @@ class TestController(unittest.TestCase):
finally:
# reload original valid config
controller.load_conf(oldconf)
+
+ def test_saveconf(self):
+
+ if test.runner.require_control(self): return
+
+ runner = test.runner.get_runner()
+
+ # only testing for success, since we need to run out of disk space to test
+ # for failure
+ with runner.get_tor_controller() as controller:
+ oldconf = runner.get_torrc_contents()
+
+ try:
+ controller.set_conf("ContactInfo", "confsaved")
+ controller.save_conf()
+ with file(runner.get_torrc_path()) as torrcfile:
+ self.assertTrue("\nContactInfo confsaved\n" in torrcfile.read())
+ finally:
+ controller.load_conf(oldconf)
+ controller.save_conf()
More information about the tor-commits
mailing list