Check conformance to grpc.GenericRpcHandler type

pull/15689/head
Nathaniel Manista 7 years ago
parent 8872a312c3
commit 369d827445
  1. 8
      src/python/grpcio/grpc/__init__.py
  2. 19
      src/python/grpcio/grpc/_server.py
  3. 1
      src/python/grpcio_tests/tests/tests.json
  4. 52
      src/python/grpcio_tests/tests/unit/_server_test.py

@ -1656,9 +1656,11 @@ def server(thread_pool,
A Server object.
"""
from grpc import _server # pylint: disable=cyclic-import
return _server.Server(thread_pool, () if handlers is None else handlers, ()
if interceptors is None else interceptors, () if
options is None else options, maximum_concurrent_rpcs)
return _server.create_server(thread_pool, ()
if handlers is None else handlers, ()
if interceptors is None else interceptors, ()
if options is None else options,
maximum_concurrent_rpcs)
################################### __all__ #################################

@ -787,7 +787,16 @@ def _start(state):
thread.start()
class Server(grpc.Server):
def _validate_generic_rpc_handlers(generic_rpc_handlers):
for generic_rpc_handler in generic_rpc_handlers:
service_attribute = getattr(generic_rpc_handler, 'service', None)
if service_attribute is None:
raise AttributeError(
'"{}" must conform to grpc.GenericRpcHandler type but does '
'not have "service" method!'.format(generic_rpc_handler))
class _Server(grpc.Server):
# pylint: disable=too-many-arguments
def __init__(self, thread_pool, generic_handlers, interceptors, options,
@ -800,6 +809,7 @@ class Server(grpc.Server):
thread_pool, maximum_concurrent_rpcs)
def add_generic_rpc_handlers(self, generic_rpc_handlers):
_validate_generic_rpc_handlers(generic_rpc_handlers)
_add_generic_handlers(self._state, generic_rpc_handlers)
def add_insecure_port(self, address):
@ -817,3 +827,10 @@ class Server(grpc.Server):
def __del__(self):
_stop(self._state, None)
def create_server(thread_pool, generic_rpc_handlers, interceptors, options,
maximum_concurrent_rpcs):
_validate_generic_rpc_handlers(generic_rpc_handlers)
return _Server(thread_pool, generic_rpc_handlers, interceptors, options,
maximum_concurrent_rpcs)

@ -53,6 +53,7 @@
"unit._server_ssl_cert_config_test.ServerSSLCertReloadTestCertConfigReuse",
"unit._server_ssl_cert_config_test.ServerSSLCertReloadTestWithClientAuth",
"unit._server_ssl_cert_config_test.ServerSSLCertReloadTestWithoutClientAuth",
"unit._server_test.ServerTest",
"unit._session_cache_test.SSLSessionCacheTest",
"unit.beta._beta_features_test.BetaFeaturesTest",
"unit.beta._beta_features_test.ContextManagementAndLifecycleTest",

@ -0,0 +1,52 @@
# Copyright 2018 The gRPC Authors.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
from concurrent import futures
import unittest
import grpc
class _ActualGenericRpcHandler(grpc.GenericRpcHandler):
def service(self, handler_call_details):
return None
class ServerTest(unittest.TestCase):
def test_not_a_generic_rpc_handler_at_construction(self):
with self.assertRaises(AttributeError) as exception_context:
grpc.server(
futures.ThreadPoolExecutor(max_workers=5),
handlers=[
_ActualGenericRpcHandler(),
object(),
])
self.assertIn('grpc.GenericRpcHandler',
str(exception_context.exception))
def test_not_a_generic_rpc_handler_after_construction(self):
server = grpc.server(futures.ThreadPoolExecutor(max_workers=5))
with self.assertRaises(AttributeError) as exception_context:
server.add_generic_rpc_handlers([
_ActualGenericRpcHandler(),
object(),
])
self.assertIn('grpc.GenericRpcHandler',
str(exception_context.exception))
if __name__ == '__main__':
unittest.main(verbosity=2)
Loading…
Cancel
Save