1# Copyright 2016 gRPC authors.
2#
3# Licensed under the Apache License, Version 2.0 (the "License");
4# you may not use this file except in compliance with the License.
5# You may obtain a copy of the License at
6#
7#     http://www.apache.org/licenses/LICENSE-2.0
8#
9# Unless required by applicable law or agreed to in writing, software
10# distributed under the License is distributed on an "AS IS" BASIS,
11# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12# See the License for the specific language governing permissions and
13# limitations under the License.
14"""Reference implementation for reflection in gRPC Python."""
15
16import sys
17import grpc
18
19from grpc_reflection.v1alpha import reflection_pb2 as _reflection_pb2
20from grpc_reflection.v1alpha import reflection_pb2_grpc as _reflection_pb2_grpc
21
22from grpc_reflection.v1alpha._base import BaseReflectionServicer
23
24SERVICE_NAME = _reflection_pb2.DESCRIPTOR.services_by_name[
25    'ServerReflection'].full_name
26
27
28class ReflectionServicer(BaseReflectionServicer):
29    """Servicer handling RPCs for service statuses."""
30
31    def ServerReflectionInfo(self, request_iterator, context):
32        # pylint: disable=unused-argument
33        for request in request_iterator:
34            if request.HasField('file_by_filename'):
35                yield self._file_by_filename(request.file_by_filename)
36            elif request.HasField('file_containing_symbol'):
37                yield self._file_containing_symbol(
38                    request.file_containing_symbol)
39            elif request.HasField('file_containing_extension'):
40                yield self._file_containing_extension(
41                    request.file_containing_extension.containing_type,
42                    request.file_containing_extension.extension_number)
43            elif request.HasField('all_extension_numbers_of_type'):
44                yield self._all_extension_numbers_of_type(
45                    request.all_extension_numbers_of_type)
46            elif request.HasField('list_services'):
47                yield self._list_services()
48            else:
49                yield _reflection_pb2.ServerReflectionResponse(
50                    error_response=_reflection_pb2.ErrorResponse(
51                        error_code=grpc.StatusCode.INVALID_ARGUMENT.value[0],
52                        error_message=grpc.StatusCode.INVALID_ARGUMENT.value[1].
53                        encode(),
54                    ))
55
56
57_enable_server_reflection_doc = """Enables server reflection on a server.
58
59Args:
60    service_names: Iterable of fully-qualified service names available.
61    server: grpc.Server to which reflection service will be added.
62    pool: DescriptorPool object to use (descriptor_pool.Default() if None).
63"""
64
65if sys.version_info[0] >= 3 and sys.version_info[1] >= 6:
66    # Exposes AsyncReflectionServicer as public API.
67    from . import _async as aio
68    from grpc.experimental import aio as grpc_aio  # pylint: disable=ungrouped-imports
69
70    def enable_server_reflection(service_names, server, pool=None):
71        if isinstance(server, grpc_aio.Server):
72            _reflection_pb2_grpc.add_ServerReflectionServicer_to_server(
73                aio.ReflectionServicer(service_names, pool=pool), server)
74        else:
75            _reflection_pb2_grpc.add_ServerReflectionServicer_to_server(
76                ReflectionServicer(service_names, pool=pool), server)
77
78    enable_server_reflection.__doc__ = _enable_server_reflection_doc
79
80    __all__ = [
81        "SERVICE_NAME",
82        "ReflectionServicer",
83        "enable_server_reflection",
84        "aio",
85    ]
86else:
87
88    def enable_server_reflection(service_names, server, pool=None):
89        _reflection_pb2_grpc.add_ServerReflectionServicer_to_server(
90            ReflectionServicer(service_names, pool=pool), server)
91
92    enable_server_reflection.__doc__ = _enable_server_reflection_doc
93
94    __all__ = [
95        "SERVICE_NAME",
96        "ReflectionServicer",
97        "enable_server_reflection",
98    ]
99