File: getconf.py

package info (click to toggle)
python-stem 1.2.2-1.1
  • links: PTS, VCS
  • area: main
  • in suites: jessie, jessie-kfreebsd
  • size: 4,568 kB
  • ctags: 2,036
  • sloc: python: 20,108; makefile: 127; sh: 3
file content (116 lines) | stat: -rw-r--r-- 3,368 bytes parent folder | download | duplicates (4)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
"""
Unit tests for the stem.response.getconf.GetConfResponse class.
"""

import unittest

import stem.response
import stem.response.getconf
import stem.socket

from test import mocking

EMPTY_RESPONSE = '250 OK'

SINGLE_RESPONSE = """\
250 DataDirectory=/home/neena/.tor"""

BATCH_RESPONSE = """\
250-CookieAuthentication=0
250-ControlPort=9100
250-DataDirectory=/tmp/fake dir
250 DirPort"""

MULTIVALUE_RESPONSE = """\
250-ControlPort=9100
250-ExitPolicy=accept 34.3.4.5
250-ExitPolicy=accept 3.4.53.3
250-ExitPolicy=accept 3.4.53.3
250 ExitPolicy=reject 23.245.54.3"""

UNRECOGNIZED_KEY_RESPONSE = '''552-Unrecognized configuration key "brickroad"
552 Unrecognized configuration key "submarine"'''

INVALID_RESPONSE = """\
123-FOO
232 BAR"""


class TestGetConfResponse(unittest.TestCase):
  def test_empty_response(self):
    """
    Parses a GETCONF reply without options (just calling "GETCONF").
    """

    control_message = mocking.get_message(EMPTY_RESPONSE)
    stem.response.convert('GETCONF', control_message)

    # now this should be a GetConfResponse (ControlMessage subclass)
    self.assertTrue(isinstance(control_message, stem.response.ControlMessage))
    self.assertTrue(isinstance(control_message, stem.response.getconf.GetConfResponse))

    self.assertEqual({}, control_message.entries)

  def test_single_response(self):
    """
    Parses a GETCONF reply response for a single parameter.
    """

    control_message = mocking.get_message(SINGLE_RESPONSE)
    stem.response.convert('GETCONF', control_message)
    self.assertEqual({'DataDirectory': ['/home/neena/.tor']}, control_message.entries)

  def test_batch_response(self):
    """
    Parses a GETCONF reply for muiltiple parameters.
    """

    control_message = mocking.get_message(BATCH_RESPONSE)
    stem.response.convert('GETCONF', control_message)

    expected = {
      'CookieAuthentication': ['0'],
      'ControlPort': ['9100'],
      'DataDirectory': ['/tmp/fake dir'],
      'DirPort': [],
    }

    self.assertEqual(expected, control_message.entries)

  def test_multivalue_response(self):
    """
    Parses a GETCONF reply containing a single key with multiple parameters.
    """

    control_message = mocking.get_message(MULTIVALUE_RESPONSE)
    stem.response.convert('GETCONF', control_message)

    expected = {
      'ControlPort': ['9100'],
      'ExitPolicy': ['accept 34.3.4.5', 'accept 3.4.53.3', 'accept 3.4.53.3', 'reject 23.245.54.3']
    }

    self.assertEqual(expected, control_message.entries)

  def test_unrecognized_key_response(self):
    """
    Parses a GETCONF reply that contains an error code with an unrecognized key.
    """

    control_message = mocking.get_message(UNRECOGNIZED_KEY_RESPONSE)
    self.assertRaises(stem.InvalidArguments, stem.response.convert, 'GETCONF', control_message)

    try:
      stem.response.convert('GETCONF', control_message)
    except stem.InvalidArguments as exc:
      self.assertEqual(exc.arguments, ['brickroad', 'submarine'])

  def test_invalid_content(self):
    """
    Parses a malformed GETCONF reply that contains an invalid response code.
    This is a proper controller message, but malformed according to the
    GETCONF's spec.
    """

    control_message = mocking.get_message(INVALID_RESPONSE)
    self.assertRaises(stem.ProtocolError, stem.response.convert, 'GETCONF', control_message)