def test_exception_response(self): """ Simulates sending a command to the node and getting an exception response. """ adapter = HttpAdapter('http://localhost:14265') error_message = 'java.lang.ArrayIndexOutOfBoundsException: 4' mocked_response = create_http_response( status=500, content=json.dumps({ 'exception': error_message, 'duration': 16, }), ) mocked_sender = Mock(return_value=mocked_response) # noinspection PyUnresolvedReferences with patch.object(adapter, '_send_http_request', mocked_sender): with self.assertRaises(BadApiResponse) as context: adapter.send_request({'command': 'helloWorld'}) self.assertEqual( text_type(context.exception), '500 response from node: {error}'.format(error=error_message), )
def test_non_200_status(self): """ The node sends back a non-200 response that we don't know how to handle. """ adapter = HttpAdapter('http://localhost') decoded_response = {'message': 'Request limit exceeded.'} mocked_response = create_http_response( status=429, content=json.dumps(decoded_response), ) mocked_sender = Mock(return_value=mocked_response) # noinspection PyUnresolvedReferences with patch.object(adapter, '_send_http_request', mocked_sender): with self.assertRaises(BadApiResponse) as context: adapter.send_request({'command': 'helloWorld'}) self.assertEqual( text_type(context.exception), '429 response from node: {decoded}'.format( decoded=decoded_response), )
def test_ipv4_address(self): """ Configuring an HttpAdapter using an IPv4 address. """ uri = 'http://127.0.0.1:8080/' adapter = HttpAdapter(uri) self.assertEqual(adapter.node_url, uri)
def test_https(self): """ Configuring HttpAdapter using a valid ``https://`` URI. """ uri = 'https://localhost:14265/' adapter = HttpAdapter(uri) self.assertEqual(adapter.node_url, uri)
def test_empty_response(self): """ The response is empty. """ adapter = HttpAdapter('http://localhost:14265') mocked_response = create_http_response('') mocked_sender = Mock(return_value=mocked_response) # noinspection PyUnresolvedReferences with patch.object(adapter, '_send_http_request', mocked_sender): with self.assertRaises(BadApiResponse) as context: adapter.send_request({'command': 'helloWorld'}) self.assertEqual( text_type(context.exception), 'Empty 200 response from node.', )
def test_success_response(self): """ Simulates sending a command to the node and getting a success response. """ adapter = HttpAdapter('http://localhost:14265') expected_result = { 'message': 'Hello, cornode!', } mocked_response = create_http_response(json.dumps(expected_result)) mocked_sender = Mock(return_value=mocked_response) # noinspection PyUnresolvedReferences with patch.object(adapter, '_send_http_request', mocked_sender): result = adapter.send_request({'command': 'helloWorld'}) self.assertEqual(result, expected_result)
def test_non_json_response(self): """ The response is not JSON. """ adapter = HttpAdapter('http://localhost:14265') invalid_response = 'EHLO cornodetoken.com' # Erm... mocked_response = create_http_response(invalid_response) mocked_sender = Mock(return_value=mocked_response) # noinspection PyUnresolvedReferences with patch.object(adapter, '_send_http_request', mocked_sender): with self.assertRaises(BadApiResponse) as context: adapter.send_request({'command': 'helloWorld'}) self.assertEqual( text_type(context.exception), 'Non-JSON 200 response from node: ' + invalid_response, )
def test_non_object_response(self): """ The response is valid JSON, but it's not an object. """ adapter = HttpAdapter('http://localhost:14265') invalid_response = ['message', 'Hello, cornode!'] mocked_response = create_http_response(json.dumps(invalid_response)) mocked_sender = Mock(return_value=mocked_response) # noinspection PyUnresolvedReferences with patch.object(adapter, '_send_http_request', mocked_sender): with self.assertRaises(BadApiResponse) as context: adapter.send_request({'command': 'helloWorld'}) self.assertEqual( text_type(context.exception), 'Malformed 200 response from node: {response!r}'.format( response=invalid_response, ), )
def test_trytes_in_request(): """ Sending a request that includes trytes. """ adapter = HttpAdapter('http://localhost:14265') # Response is not important for this test; we just need to make # sure that the request is converted correctly. mocked_sender = Mock(return_value=create_http_response('{}')) # noinspection PyUnresolvedReferences with patch.object(adapter, '_send_http_request', mocked_sender): adapter.send_request({ 'command': 'helloWorld', 'trytes': [ TryteString(b'RBTC9D9DCDQAEASBYBCCKBFA'), TryteString( b'CCPCBDVC9DTCEAKDXC9D9DEARCWCPCBDVCTCEAHDWCTCEAKDCDFD9DSCSA', ), ], }) mocked_sender.assert_called_once_with( url=adapter.node_url, payload=json.dumps({ 'command': 'helloWorld', # Tryte sequences are converted to strings for transport. 'trytes': [ 'RBTC9D9DCDQAEASBYBCCKBFA', 'CCPCBDVC9DTCEAKDXC9D9DEARCWCPCBDVCTCEAHDWCTCEAKDCDFD9DSCSA', ], }), headers={ 'Content-type': 'application/json', }, )
def test_router_aliasing(self): """ The router will try to re-use existing adapter instances. """ wrapper1 = RoutingWrapper('http://localhost:14265') adapter_default = wrapper1.adapter # The router will try to minimize the number of adapter instances # that it creates from URIs. wrapper1\ .add_route('alpha', 'http://localhost:14265')\ .add_route('bravo', 'http://localhost:14265')\ # Two routes with the same URI => same adapter instance. self.assertIs( wrapper1.get_adapter('bravo'), wrapper1.get_adapter('alpha'), ) # "127.0.0.1" != "localhost", so separate adapters created. wrapper1.add_route('charlie', 'http://127.0.0.1:14265') self.assertIsNot( wrapper1.get_adapter('charlie'), wrapper1.get_adapter('alpha'), ) # Providing an adapter instance bypasses the whole setup. wrapper1.add_route('delta', HttpAdapter('http://localhost:14265')) self.assertIsNot( wrapper1.get_adapter('delta'), wrapper1.get_adapter('alpha'), ) # The default adapter is always kept separate, even if it URI # matches a routing adapter. self.assertIsNot( wrapper1.get_adapter('foo'), wrapper1.get_adapter('alpha'), ) # Aliased adapters are not shared between routers. wrapper2 = RoutingWrapper(adapter_default) wrapper2.add_route('echo', 'http://localhost:14265') self.assertIsNot( wrapper2.get_adapter('echo'), wrapper1.get_adapter('alpha'), )
def test_configure_error_udp(self): """ UDP is not a valid protocol for ``HttpAdapter``. """ with self.assertRaises(InvalidUri): HttpAdapter.configure('udp://localhost:14265')
def test_configure_error_non_numeric_port(self): """ Attempting to configure HttpAdapter with non-numeric port. """ with self.assertRaises(InvalidUri): HttpAdapter.configure('http://localhost:cornode/')
def test_configure_error_empty_host(self): """ Attempting to configure HttpAdapter with empty host. """ with self.assertRaises(InvalidUri): HttpAdapter.configure('http://:14265')
def test_configure_error_invalid_protocol(self): """ Attempting to configure HttpAdapter with unsupported protocol. """ with self.assertRaises(InvalidUri): HttpAdapter.configure('ftp://localhost:14265/')
def test_configure_error_missing_protocol(self): """ Forgetting to add the protocol to the URI. """ with self.assertRaises(InvalidUri): HttpAdapter.configure('localhost:14265')