22
22
from nova import context
23
23
from nova import log as logging
24
24
from nova import rpc
25
from nova.tests import test_rpc_common
28
28
LOG = logging.getLogger('nova.tests.rpc')
31
class RpcTestCase(test.TestCase):
31
class RpcTestCase(test_rpc_common._BaseRpcTestCase):
33
34
super(RpcTestCase, self).setUp()
34
self.conn = rpc.create_connection(True)
35
self.receiver = TestReceiver()
36
self.consumer = rpc.create_consumer(self.conn,
40
self.consumer.attach_to_eventlet()
41
self.context = context.get_admin_context()
43
def test_call_succeed(self):
45
result = rpc.call(self.context, 'test', {"method": "echo",
46
"args": {"value": value}})
47
self.assertEqual(value, result)
49
def test_call_succeed_despite_multiple_returns(self):
51
result = rpc.call(self.context, 'test', {"method": "echo_three_times",
52
"args": {"value": value}})
53
self.assertEqual(value + 2, result)
55
def test_call_succeed_despite_multiple_returns_yield(self):
57
result = rpc.call(self.context, 'test',
58
{"method": "echo_three_times_yield",
59
"args": {"value": value}})
60
self.assertEqual(value + 2, result)
62
def test_multicall_succeed_once(self):
64
result = rpc.multicall(self.context,
67
"args": {"value": value}})
68
for i, x in enumerate(result):
70
self.fail('should only receive one response')
71
self.assertEqual(value + i, x)
73
def test_multicall_succeed_three_times(self):
75
result = rpc.multicall(self.context,
77
{"method": "echo_three_times",
78
"args": {"value": value}})
79
for i, x in enumerate(result):
80
self.assertEqual(value + i, x)
82
def test_multicall_succeed_three_times_yield(self):
84
result = rpc.multicall(self.context,
86
{"method": "echo_three_times_yield",
87
"args": {"value": value}})
88
for i, x in enumerate(result):
89
self.assertEqual(value + i, x)
91
def test_context_passed(self):
92
"""Makes sure a context is passed through rpc call."""
94
result = rpc.call(self.context,
95
'test', {"method": "context",
96
"args": {"value": value}})
97
self.assertEqual(self.context.to_dict(), result)
99
def test_call_exception(self):
100
"""Test that exception gets passed back properly.
102
rpc.call returns a RemoteError object. The value of the
103
exception is converted to a string, so we convert it back
104
to an int in the test.
108
self.assertRaises(rpc.RemoteError,
113
"args": {"value": value}})
115
rpc.call(self.context,
118
"args": {"value": value}})
119
self.fail("should have thrown rpc.RemoteError")
120
except rpc.RemoteError as exc:
121
self.assertEqual(int(exc.value), value)
123
def test_nested_calls(self):
124
"""Test that we can do an rpc.call inside another call."""
125
class Nested(object):
127
def echo(context, queue, value):
128
"""Calls echo in the passed queue"""
129
LOG.debug(_("Nested received %(queue)s, %(value)s")
131
# TODO: so, it will replay the context and use the same REQID?
133
ret = rpc.call(context,
136
"args": {"value": value}})
137
LOG.debug(_("Nested return %s"), ret)
141
conn = rpc.create_connection(True)
142
consumer = rpc.create_consumer(conn,
146
consumer.attach_to_eventlet()
148
result = rpc.call(self.context,
149
'nested', {"method": "echo",
150
"args": {"queue": "test",
152
self.assertEqual(value, result)
155
class TestReceiver(object):
156
"""Simple Proxy class so the consumer has methods to call.
158
Uses static methods because we aren't actually storing any state.
163
def echo(context, value):
164
"""Simply returns whatever value is sent in."""
165
LOG.debug(_("Received %s"), value)
169
def context(context, value):
170
"""Returns dictionary version of context."""
171
LOG.debug(_("Received %s"), context)
172
return context.to_dict()
175
def echo_three_times(context, value):
177
context.reply(value + 1)
178
context.reply(value + 2)
181
def echo_three_times_yield(context, value):
187
def fail(context, value):
188
"""Raises an exception with the value sent in."""
189
raise Exception(value)
37
super(RpcTestCase, self).tearDown()