1414# limitations under the License.
1515#
1616import abc
17+ import re
1718from typing import Awaitable , Callable , Optional , Sequence , Union
1819
1920import google .api_core # type: ignore
2021from google .api_core import exceptions as core_exceptions # type: ignore
2122from google .api_core import gapic_v1 # type: ignore
2223from google .api_core import retry as retries # type: ignore
24+ from google .api_core import retry_async as retries_async # type: ignore
2325from google .api_core import version
2426import google .auth # type: ignore
2527from google .auth import credentials as ga_credentials # type: ignore
2628from google .longrunning import operations_pb2
2729from google .oauth2 import service_account # type: ignore
28- from google .protobuf import empty_pb2 # type: ignore
30+ import google .protobuf
31+ from google .protobuf import empty_pb2 , json_format # type: ignore
2932from grpc import Compression
3033
3134
35+ PROTOBUF_VERSION = google .protobuf .__version__
36+
3237DEFAULT_CLIENT_INFO = gapic_v1 .client_info .ClientInfo (
3338 gapic_version = version .__version__ ,
3439)
@@ -51,6 +56,7 @@ def __init__(
5156 quota_project_id : Optional [str ] = None ,
5257 client_info : gapic_v1 .client_info .ClientInfo = DEFAULT_CLIENT_INFO ,
5358 always_use_jwt_access : Optional [bool ] = False ,
59+ url_scheme = "https" ,
5460 ** kwargs ,
5561 ) -> None :
5662 """Instantiate the transport.
@@ -76,7 +82,20 @@ def __init__(
7682 your own client library.
7783 always_use_jwt_access (Optional[bool]): Whether self signed JWT should
7884 be used for service account credentials.
85+ url_scheme: the protocol scheme for the API endpoint. Normally
86+ "https", but for testing or local servers,
87+ "http" can be specified.
7988 """
89+ maybe_url_match = re .match ("^(?P<scheme>http(?:s)?://)?(?P<host>.*)$" , host )
90+ if maybe_url_match is None :
91+ raise ValueError (
92+ f"Unexpected hostname structure: { host } "
93+ ) # pragma: NO COVER
94+
95+ url_match_items = maybe_url_match .groupdict ()
96+
97+ host = f"{ url_scheme } ://{ host } " if not url_match_items ["scheme" ] else host
98+
8099 # Save the hostname. Default to port 443 (HTTPS) if none is specified.
81100 if ":" not in host :
82101 host += ":443"
@@ -115,12 +134,13 @@ def __init__(
115134 # Save the credentials.
116135 self ._credentials = credentials
117136
118- def _prep_wrapped_messages (self , client_info ):
137+ def _prep_wrapped_messages (self , client_info , is_async = False ):
119138 # Precompute the wrapped methods.
139+ retry_class = retries_async .AsyncRetry if is_async else retries .Retry
120140 self ._wrapped_methods = {
121141 self .list_operations : gapic_v1 .method .wrap_method (
122142 self .list_operations ,
123- default_retry = retries . Retry (
143+ default_retry = retry_class (
124144 initial = 0.5 ,
125145 maximum = 10.0 ,
126146 multiplier = 2.0 ,
@@ -135,7 +155,7 @@ def _prep_wrapped_messages(self, client_info):
135155 ),
136156 self .get_operation : gapic_v1 .method .wrap_method (
137157 self .get_operation ,
138- default_retry = retries . Retry (
158+ default_retry = retry_class (
139159 initial = 0.5 ,
140160 maximum = 10.0 ,
141161 multiplier = 2.0 ,
@@ -150,7 +170,7 @@ def _prep_wrapped_messages(self, client_info):
150170 ),
151171 self .delete_operation : gapic_v1 .method .wrap_method (
152172 self .delete_operation ,
153- default_retry = retries . Retry (
173+ default_retry = retry_class (
154174 initial = 0.5 ,
155175 maximum = 10.0 ,
156176 multiplier = 2.0 ,
@@ -165,7 +185,7 @@ def _prep_wrapped_messages(self, client_info):
165185 ),
166186 self .cancel_operation : gapic_v1 .method .wrap_method (
167187 self .cancel_operation ,
168- default_retry = retries . Retry (
188+ default_retry = retry_class (
169189 initial = 0.5 ,
170190 maximum = 10.0 ,
171191 multiplier = 2.0 ,
@@ -189,6 +209,38 @@ def close(self):
189209 """
190210 raise NotImplementedError ()
191211
212+ def _convert_protobuf_message_to_dict (
213+ self , message : google .protobuf .message .Message
214+ ):
215+ r"""Converts protobuf message to a dictionary.
216+
217+ When the dictionary is encoded to JSON, it conforms to proto3 JSON spec.
218+
219+ Args:
220+ message(google.protobuf.message.Message): The protocol buffers message
221+ instance to serialize.
222+
223+ Returns:
224+ A dict representation of the protocol buffer message.
225+ """
226+ # For backwards compatibility with protobuf 3.x 4.x
227+ # Remove once support for protobuf 3.x and 4.x is dropped
228+ # https://github.com/googleapis/python-api-core/issues/643
229+ if PROTOBUF_VERSION [0 :2 ] in ["3." , "4." ]:
230+ result = json_format .MessageToDict (
231+ message ,
232+ preserving_proto_field_name = True ,
233+ including_default_value_fields = True , # type: ignore # backward compatibility
234+ )
235+ else :
236+ result = json_format .MessageToDict (
237+ message ,
238+ preserving_proto_field_name = True ,
239+ always_print_fields_with_no_presence = True ,
240+ )
241+
242+ return result
243+
192244 @property
193245 def list_operations (
194246 self ,
0 commit comments