You've already forked bthlabs-jsonrpc
v1.1.0b1
This commit is contained in:
@@ -1,46 +1,25 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# type: ignore
|
||||
from __future__ import annotations
|
||||
|
||||
import json
|
||||
from unittest import mock
|
||||
|
||||
import pytest
|
||||
|
||||
from bthlabs_jsonrpc_core import exceptions, executor
|
||||
from bthlabs_jsonrpc_core.codecs import JSONCodec
|
||||
from bthlabs_jsonrpc_core.registry import MethodRegistry
|
||||
from bthlabs_jsonrpc_core.serializer import JSONRPCSerializer
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
def single_call():
|
||||
return {
|
||||
'jsonrpc': '2.0',
|
||||
'id': 'test',
|
||||
'method': 'test',
|
||||
}
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
def batch_calls():
|
||||
return [
|
||||
{
|
||||
'jsonrpc': '2.0',
|
||||
'id': 'test',
|
||||
'method': 'test',
|
||||
},
|
||||
{
|
||||
'jsonrpc': '2.0',
|
||||
'id': 'test2',
|
||||
'method': 'test',
|
||||
},
|
||||
]
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
def jsonrpc_error():
|
||||
def jsonrpc_error() -> exceptions.BaseJSONRPCError:
|
||||
return exceptions.BaseJSONRPCError('I HAZ FIAL')
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
def execute_context():
|
||||
def execute_context() -> executor.Executor.ExecuteContext:
|
||||
return executor.Executor.ExecuteContext([])
|
||||
|
||||
|
||||
@@ -55,7 +34,7 @@ def test_CallContext_invalid_context():
|
||||
assert result.kwargs is None
|
||||
|
||||
|
||||
def test_CallContext_is_valid_method_none(fake_handler):
|
||||
def test_CallContext_is_valid_method_none(fake_handler: mock.Mock):
|
||||
# When
|
||||
call_context = executor.Executor.CallContext(None, fake_handler, [], {})
|
||||
|
||||
@@ -71,7 +50,7 @@ def test_CallContext_is_valid_handler_none():
|
||||
assert call_context.is_valid is False
|
||||
|
||||
|
||||
def test_CallContext_is_valid_args_none(fake_handler):
|
||||
def test_CallContext_is_valid_args_none(fake_handler: mock.Mock):
|
||||
# When
|
||||
call_context = executor.Executor.CallContext(
|
||||
'test', fake_handler, None, {},
|
||||
@@ -81,7 +60,7 @@ def test_CallContext_is_valid_args_none(fake_handler):
|
||||
assert call_context.is_valid is False
|
||||
|
||||
|
||||
def test_CallContext_is_valid_kwargs_none(fake_handler):
|
||||
def test_CallContext_is_valid_kwargs_none(fake_handler: mock.Mock):
|
||||
# When
|
||||
call_context = executor.Executor.CallContext(
|
||||
'test', fake_handler, [], None,
|
||||
@@ -91,7 +70,7 @@ def test_CallContext_is_valid_kwargs_none(fake_handler):
|
||||
assert call_context.is_valid is False
|
||||
|
||||
|
||||
def test_CallContext_is_valid(fake_handler):
|
||||
def test_CallContext_is_valid(fake_handler: mock.Mock):
|
||||
# When
|
||||
call_context = executor.Executor.CallContext('test', fake_handler, [], {})
|
||||
|
||||
@@ -99,12 +78,13 @@ def test_CallContext_is_valid(fake_handler):
|
||||
assert call_context.is_valid is True
|
||||
|
||||
|
||||
def test_init_default_namespace():
|
||||
def test_init():
|
||||
# When
|
||||
result = executor.Executor()
|
||||
|
||||
# Then
|
||||
assert result.namespace == MethodRegistry.DEFAULT_NAMESPACE
|
||||
assert isinstance(result.codec, JSONCodec) is True
|
||||
|
||||
|
||||
def test_init_custom_namespace():
|
||||
@@ -115,8 +95,17 @@ def test_init_custom_namespace():
|
||||
assert result.namespace == 'testing'
|
||||
|
||||
|
||||
def test_init_custom_codec(fake_custom_codec: mock.Mock):
|
||||
# When
|
||||
result = executor.Executor(codec=fake_custom_codec)
|
||||
|
||||
# Then
|
||||
assert result.codec == fake_custom_codec
|
||||
|
||||
|
||||
@mock.patch.object(executor.MethodRegistry, 'shared_registry')
|
||||
def test_list_methods(mock_shared_registry, fake_method_registry):
|
||||
def test_list_methods(mock_shared_registry: mock.Mock,
|
||||
fake_method_registry: mock.Mock):
|
||||
# Given
|
||||
fake_method_registry.get_methods.return_value = ['test']
|
||||
mock_shared_registry.return_value = fake_method_registry
|
||||
@@ -170,6 +159,21 @@ def test_deserialize_data():
|
||||
assert result == 'spam'
|
||||
|
||||
|
||||
def test_deserialize_data_custom_codec(fake_custom_codec: mock.Mock):
|
||||
# Given
|
||||
fake_custom_codec.decode.return_value = 'spam'
|
||||
|
||||
the_executor = executor.Executor(codec=fake_custom_codec)
|
||||
|
||||
# When
|
||||
result = the_executor.deserialize_data('"spam"')
|
||||
|
||||
# Then
|
||||
assert result == 'spam'
|
||||
|
||||
fake_custom_codec.decode.assert_called_once_with('"spam"')
|
||||
|
||||
|
||||
def test_deserialize_data_error():
|
||||
# Given
|
||||
the_executor = executor.Executor()
|
||||
@@ -184,7 +188,25 @@ def test_deserialize_data_error():
|
||||
assert False, 'No exception raised?'
|
||||
|
||||
|
||||
def test_get_calls_batch(batch_calls):
|
||||
def test_deserialize_data_custom_codec_error(fake_custom_codec: mock.Mock):
|
||||
# Given
|
||||
error = RuntimeError('I HAZ FAIL')
|
||||
fake_custom_codec.decode.side_effect = error
|
||||
|
||||
the_executor = executor.Executor(codec=fake_custom_codec)
|
||||
|
||||
# When
|
||||
try:
|
||||
_ = the_executor.deserialize_data(None)
|
||||
except Exception as exception:
|
||||
# Then
|
||||
assert isinstance(exception, exceptions.JSONRPCParseError)
|
||||
assert exception.__cause__ == error
|
||||
else:
|
||||
assert False, 'No exception raised?'
|
||||
|
||||
|
||||
def test_get_calls_batch(batch_calls: list):
|
||||
# Given
|
||||
the_executor = executor.Executor()
|
||||
|
||||
@@ -195,7 +217,7 @@ def test_get_calls_batch(batch_calls):
|
||||
assert result == batch_calls
|
||||
|
||||
|
||||
def test_get_calls_single(single_call):
|
||||
def test_get_calls_single(single_call: dict):
|
||||
# Given
|
||||
the_executor = executor.Executor()
|
||||
|
||||
@@ -234,7 +256,7 @@ def test_get_call_spec_not_dict():
|
||||
assert False, 'No exception raised?'
|
||||
|
||||
|
||||
def test_get_call_spec_wihtout_jsonrpc(single_call):
|
||||
def test_get_call_spec_wihtout_jsonrpc(single_call: dict):
|
||||
# Given
|
||||
single_call.pop('jsonrpc')
|
||||
|
||||
@@ -250,7 +272,7 @@ def test_get_call_spec_wihtout_jsonrpc(single_call):
|
||||
assert False, 'No exception raised?'
|
||||
|
||||
|
||||
def test_get_call_spec_invalid_jsonrpc(single_call):
|
||||
def test_get_call_spec_invalid_jsonrpc(single_call: dict):
|
||||
# Given
|
||||
single_call['jsonrpc'] = 'test'
|
||||
|
||||
@@ -266,7 +288,7 @@ def test_get_call_spec_invalid_jsonrpc(single_call):
|
||||
assert False, 'No exception raised?'
|
||||
|
||||
|
||||
def test_get_call_spec_wihtout_method(single_call):
|
||||
def test_get_call_spec_wihtout_method(single_call: dict):
|
||||
# Given
|
||||
single_call.pop('method')
|
||||
|
||||
@@ -283,9 +305,9 @@ def test_get_call_spec_wihtout_method(single_call):
|
||||
|
||||
|
||||
@mock.patch.object(executor.MethodRegistry, 'shared_registry')
|
||||
def test_get_call_spec_internal_method(mock_shared_registry,
|
||||
single_call,
|
||||
fake_handler):
|
||||
def test_get_call_spec_internal_method(mock_shared_registry: mock.Mock,
|
||||
single_call: dict,
|
||||
fake_handler: mock.Mock):
|
||||
# Given
|
||||
single_call['method'] = 'system.list_methods'
|
||||
|
||||
@@ -307,11 +329,13 @@ def test_get_call_spec_internal_method(mock_shared_registry,
|
||||
|
||||
|
||||
@mock.patch.object(executor.MethodRegistry, 'shared_registry')
|
||||
def test_get_call_spec_registry_method(mock_shared_registry,
|
||||
single_call,
|
||||
fake_method_registry,
|
||||
fake_handler):
|
||||
def test_get_call_spec_registry_method(mock_shared_registry: mock.Mock,
|
||||
single_call: dict,
|
||||
fake_method_registry: mock.Mock,
|
||||
fake_handler: mock.Mock):
|
||||
# Given
|
||||
single_call['method'] = 'test'
|
||||
|
||||
fake_method_registry.get_handler.return_value = fake_handler
|
||||
mock_shared_registry.return_value = fake_method_registry
|
||||
|
||||
@@ -333,10 +357,12 @@ def test_get_call_spec_registry_method(mock_shared_registry,
|
||||
|
||||
|
||||
@mock.patch.object(executor.MethodRegistry, 'shared_registry')
|
||||
def test_get_call_spec_method_not_found(mock_shared_registry,
|
||||
single_call,
|
||||
fake_method_registry):
|
||||
def test_get_call_spec_method_not_found(mock_shared_registry: mock.Mock,
|
||||
single_call: dict,
|
||||
fake_method_registry: mock.Mock):
|
||||
# Given
|
||||
single_call['method'] = 'test'
|
||||
|
||||
fake_method_registry.get_handler.return_value = None
|
||||
mock_shared_registry.return_value = fake_method_registry
|
||||
|
||||
@@ -353,10 +379,10 @@ def test_get_call_spec_method_not_found(mock_shared_registry,
|
||||
|
||||
|
||||
@mock.patch.object(executor.MethodRegistry, 'shared_registry')
|
||||
def test_get_call_spec_invalid_params(mock_shared_registry,
|
||||
single_call,
|
||||
fake_method_registry,
|
||||
fake_handler):
|
||||
def test_get_call_spec_invalid_params(mock_shared_registry: mock.Mock,
|
||||
single_call: dict,
|
||||
fake_method_registry: mock.Mock,
|
||||
fake_handler: mock.Mock):
|
||||
# Given
|
||||
single_call['params'] = 'spam'
|
||||
|
||||
@@ -376,10 +402,10 @@ def test_get_call_spec_invalid_params(mock_shared_registry,
|
||||
|
||||
|
||||
@mock.patch.object(executor.MethodRegistry, 'shared_registry')
|
||||
def test_get_call_spec_with_args(mock_shared_registry,
|
||||
single_call,
|
||||
fake_method_registry,
|
||||
fake_handler):
|
||||
def test_get_call_spec_with_args(mock_shared_registry: mock.Mock,
|
||||
single_call: dict,
|
||||
fake_method_registry: mock.Mock,
|
||||
fake_handler: mock.Mock):
|
||||
# Given
|
||||
single_call['params'] = ['spam']
|
||||
|
||||
@@ -402,10 +428,10 @@ def test_get_call_spec_with_args(mock_shared_registry,
|
||||
|
||||
|
||||
@mock.patch.object(executor.MethodRegistry, 'shared_registry')
|
||||
def test_get_call_spec_with_kwargs(mock_shared_registry,
|
||||
single_call,
|
||||
fake_method_registry,
|
||||
fake_handler):
|
||||
def test_get_call_spec_with_kwargs(mock_shared_registry: mock.Mock,
|
||||
single_call: dict,
|
||||
fake_method_registry: mock.Mock,
|
||||
fake_handler: mock.Mock):
|
||||
# Given
|
||||
single_call['params'] = {'spam': True}
|
||||
|
||||
@@ -427,7 +453,9 @@ def test_get_call_spec_with_kwargs(mock_shared_registry,
|
||||
mock_enrich_kwargs.assert_called_with({'spam': True})
|
||||
|
||||
|
||||
def test_process_results(batch_calls, single_call, jsonrpc_error):
|
||||
def test_process_results(batch_calls: list,
|
||||
single_call: dict,
|
||||
jsonrpc_error: exceptions.BaseJSONRPCError):
|
||||
# Given
|
||||
call_without_id = {**single_call}
|
||||
call_without_id.pop('id')
|
||||
@@ -465,7 +493,7 @@ def test_process_results(batch_calls, single_call, jsonrpc_error):
|
||||
assert second_response == expected_second_response
|
||||
|
||||
|
||||
def test_process_results_single_call(single_call):
|
||||
def test_process_results_single_call(single_call: dict):
|
||||
# Given
|
||||
call_results = [
|
||||
(single_call, 'OK'),
|
||||
@@ -485,7 +513,7 @@ def test_process_results_single_call(single_call):
|
||||
assert result == expected_result
|
||||
|
||||
|
||||
def test_process_results_top_level_error(jsonrpc_error):
|
||||
def test_process_results_top_level_error(jsonrpc_error: exceptions.BaseJSONRPCError):
|
||||
# Given
|
||||
call_results = [
|
||||
(None, jsonrpc_error),
|
||||
@@ -505,7 +533,7 @@ def test_process_results_top_level_error(jsonrpc_error):
|
||||
assert result == expected_result
|
||||
|
||||
|
||||
def test_process_results_empty(single_call):
|
||||
def test_process_results_empty(single_call: dict):
|
||||
# Given
|
||||
single_call.pop('id')
|
||||
|
||||
@@ -522,9 +550,9 @@ def test_process_results_empty(single_call):
|
||||
assert result is None
|
||||
|
||||
|
||||
def test_call_context_invalid_context(jsonrpc_error,
|
||||
execute_context,
|
||||
single_call):
|
||||
def test_call_context_invalid_context(jsonrpc_error: exceptions.BaseJSONRPCError,
|
||||
execute_context: executor.Executor.ExecuteContext,
|
||||
single_call: dict):
|
||||
# Given
|
||||
the_executor = executor.Executor()
|
||||
|
||||
@@ -539,10 +567,10 @@ def test_call_context_invalid_context(jsonrpc_error,
|
||||
assert result.is_valid is False
|
||||
|
||||
|
||||
def test_call_context_handle_jsonrpc_error(fake_handler,
|
||||
jsonrpc_error,
|
||||
execute_context,
|
||||
single_call):
|
||||
def test_call_context_handle_jsonrpc_error(fake_handler: mock.Mock,
|
||||
jsonrpc_error: exceptions.BaseJSONRPCError,
|
||||
execute_context: executor.Executor.ExecuteContext,
|
||||
single_call: dict):
|
||||
# Given
|
||||
the_executor = executor.Executor()
|
||||
|
||||
@@ -562,9 +590,9 @@ def test_call_context_handle_jsonrpc_error(fake_handler,
|
||||
assert call_result[1] == jsonrpc_error
|
||||
|
||||
|
||||
def test_call_context_handle_exception(fake_handler,
|
||||
execute_context,
|
||||
single_call):
|
||||
def test_call_context_handle_exception(fake_handler: mock.Mock,
|
||||
execute_context: executor.Executor.ExecuteContext,
|
||||
single_call: dict):
|
||||
# Given
|
||||
the_executor = executor.Executor()
|
||||
|
||||
@@ -585,7 +613,9 @@ def test_call_context_handle_exception(fake_handler,
|
||||
assert call_result[1].data == 'I HAZ FIAL'
|
||||
|
||||
|
||||
def test_call_context(fake_handler, execute_context, single_call):
|
||||
def test_call_context(fake_handler: mock.Mock,
|
||||
execute_context: executor.Executor.ExecuteContext,
|
||||
single_call: dict):
|
||||
# Given
|
||||
the_executor = executor.Executor()
|
||||
|
||||
@@ -610,7 +640,7 @@ def test_call_context(fake_handler, execute_context, single_call):
|
||||
assert execute_context.results[0] == expected_call_result
|
||||
|
||||
|
||||
def test_execute_context_handle_jsonrpc_error(jsonrpc_error):
|
||||
def test_execute_context_handle_jsonrpc_error(jsonrpc_error: exceptions.BaseJSONRPCError):
|
||||
# Given
|
||||
the_executor = executor.Executor()
|
||||
|
||||
@@ -638,7 +668,7 @@ def test_execute_context_handle_exception():
|
||||
assert result.serializer is None
|
||||
|
||||
|
||||
def test_execute_context_handle_empty_results(single_call):
|
||||
def test_execute_context_handle_empty_results(single_call: dict):
|
||||
# Given
|
||||
the_executor = executor.Executor()
|
||||
|
||||
@@ -656,7 +686,7 @@ def test_execute_context_handle_empty_results(single_call):
|
||||
assert mock_serializer.called is False
|
||||
|
||||
|
||||
def test_execute_context(fake_rpc_serializer, single_call):
|
||||
def test_execute_context(fake_rpc_serializer: mock.Mock, single_call: dict):
|
||||
# Given
|
||||
fake_responses = {
|
||||
'jsonrpc': '2.0',
|
||||
@@ -712,7 +742,7 @@ def test_before_call():
|
||||
|
||||
|
||||
@mock.patch.object(executor.MethodRegistry, 'shared_registry')
|
||||
def test_execute(mock_shared_registry, fake_method_registry):
|
||||
def test_execute(mock_shared_registry: mock.Mock, fake_method_registry: mock.Mock):
|
||||
# Given
|
||||
fake_method_registry.get_handler.return_value = None
|
||||
fake_method_registry.get_methods.return_value = []
|
||||
|
||||
Reference in New Issue
Block a user