30
30
31
31
from . import documents , _base as base
32
32
from .http_constants import ResourceType
33
- from .documents import _OperationType , ConnectionPolicy
33
+ from .documents import ConnectionPolicy
34
34
from ._request_object import RequestObject
35
35
36
36
# pylint: disable=protected-access
@@ -43,40 +43,27 @@ class EndpointOperationType(object):
43
43
WriteType = "Write"
44
44
45
45
class RegionalRoutingContext (object ):
46
- def __init__ (self , primary_endpoint : str , alternate_endpoint : str ):
46
+ def __init__ (self , primary_endpoint : str ):
47
47
self .primary_endpoint : str = primary_endpoint
48
- self .alternate_endpoint : str = alternate_endpoint
49
48
50
49
def set_primary (self , endpoint : str ):
51
50
self .primary_endpoint = endpoint
52
51
53
- def set_alternate (self , endpoint : str ):
54
- self .alternate_endpoint = endpoint
55
-
56
52
def get_primary (self ):
57
53
return self .primary_endpoint
58
54
59
- def get_alternate (self ):
60
- return self .alternate_endpoint
61
-
62
55
def __eq__ (self , other ):
63
- return (self .primary_endpoint == other .primary_endpoint
64
- and self .alternate_endpoint == other .alternate_endpoint )
56
+ return self .primary_endpoint == other .primary_endpoint
65
57
66
58
def __str__ (self ):
67
- return "Primary: " + self .primary_endpoint + ", Alternate: " + self . alternate_endpoint
59
+ return "Primary: " + self .primary_endpoint
68
60
69
- def get_endpoints_by_location (new_locations : List [Dict [str , str ]],
70
- old_regional_routing_contexts_by_location : Dict [str , RegionalRoutingContext ],
71
- default_regional_endpoint : RegionalRoutingContext ,
72
- writes : bool ,
73
- use_multiple_write_locations : bool ):
61
+ def get_regional_routing_contexts_by_loc (new_locations : List [Dict [str , str ]]):
74
62
# construct from previous object
75
- regional_routing_context_by_location : OrderedDict [str , RegionalRoutingContext ] = collections .OrderedDict ()
63
+ regional_routing_contexts_by_location : OrderedDict [str , RegionalRoutingContext ] = collections .OrderedDict ()
76
64
parsed_locations = []
77
65
78
-
79
- for new_location in new_locations : # pylint: disable=too-many-nested-blocks
66
+ for new_location in new_locations :
80
67
# if name in new_location and same for database account endpoint
81
68
if "name" in new_location and "databaseAccountEndpoint" in new_location :
82
69
if not new_location ["name" ]:
@@ -85,44 +72,19 @@ def get_endpoints_by_location(new_locations: List[Dict[str, str]],
85
72
try :
86
73
region_uri = new_location ["databaseAccountEndpoint" ]
87
74
parsed_locations .append (new_location ["name" ])
88
- if not writes or use_multiple_write_locations :
89
- regional_object = RegionalRoutingContext (region_uri , region_uri )
90
- elif new_location ["name" ] in old_regional_routing_contexts_by_location :
91
- regional_object = old_regional_routing_contexts_by_location [new_location ["name" ]]
92
- current = regional_object .get_primary ()
93
- # swap the previous with current and current with new region_uri received from the gateway
94
- if current != region_uri :
95
- regional_object .set_alternate (current )
96
- regional_object .set_primary (region_uri )
97
- # This is the bootstrapping condition
98
- else :
99
- regional_object = RegionalRoutingContext (region_uri , region_uri )
100
- # if it is for writes, then we update the previous to default_endpoint
101
- if writes :
102
- # if region_uri is different than global endpoint set global endpoint
103
- # as fallback
104
- # else construct regional uri
105
- if region_uri != default_regional_endpoint .get_primary ():
106
- regional_object .set_alternate (default_regional_endpoint .get_primary ())
107
- else :
108
- constructed_region_uri = LocationCache .GetLocationalEndpoint (
109
- default_regional_endpoint .get_primary (),
110
- new_location ["name" ])
111
- regional_object .set_alternate (constructed_region_uri )
112
- regional_routing_context_by_location .update ({new_location ["name" ]: regional_object })
75
+ regional_object = RegionalRoutingContext (region_uri )
76
+ regional_routing_contexts_by_location .update ({new_location ["name" ]: regional_object })
113
77
except Exception as e :
114
78
raise e
115
79
116
80
# Also store a hash map of endpoints for each location
117
- locations_by_endpoints = {value .get_primary (): key for key , value in regional_routing_context_by_location .items ()}
81
+ locations_by_endpoints = {value .get_primary (): key for key , value in regional_routing_contexts_by_location .items ()}
118
82
119
- return regional_routing_context_by_location , locations_by_endpoints , parsed_locations
83
+ return regional_routing_contexts_by_location , locations_by_endpoints , parsed_locations
120
84
121
85
def _get_health_check_endpoints (regional_routing_contexts ) -> Set [str ]:
122
86
# should use the endpoints in the order returned from gateway and only the ones specified in preferred locations
123
- preferred_endpoints = {context .get_primary () for context in regional_routing_contexts }.union (
124
- {context .get_alternate () for context in regional_routing_contexts }
125
- )
87
+ preferred_endpoints = {context .get_primary () for context in regional_routing_contexts }
126
88
return preferred_endpoints
127
89
128
90
def _get_applicable_regional_routing_contexts (regional_routing_contexts : List [RegionalRoutingContext ],
@@ -157,8 +119,7 @@ def __init__(
157
119
default_endpoint : str ,
158
120
connection_policy : ConnectionPolicy ,
159
121
):
160
- self .default_regional_routing_context : RegionalRoutingContext = RegionalRoutingContext (default_endpoint ,
161
- default_endpoint )
122
+ self .default_regional_routing_context : RegionalRoutingContext = RegionalRoutingContext (default_endpoint )
162
123
self .effective_preferred_locations : List [str ] = []
163
124
self .enable_multiple_writable_locations : bool = False
164
125
self .write_regional_routing_contexts : List [RegionalRoutingContext ] = [self .default_regional_routing_context ]
@@ -205,9 +166,8 @@ def perform_on_database_account_read(self, database_account):
205
166
206
167
def get_all_write_endpoints (self ) -> Set [str ]:
207
168
return {
208
- endpoint
169
+ context . get_primary ()
209
170
for context in self .get_write_regional_routing_contexts ()
210
- for endpoint in (context .get_primary (), context .get_alternate ())
211
171
}
212
172
213
173
def get_ordered_write_locations (self ):
@@ -272,10 +232,6 @@ def resolve_service_endpoint(self, request):
272
232
request .use_preferred_locations if request .use_preferred_locations is not None else True
273
233
)
274
234
275
- # whether to check for write or read unavailable
276
- endpoint_operation_type = EndpointOperationType .WriteType if (
277
- documents ._OperationType .IsWriteOperation (request .operation_type )) else EndpointOperationType .ReadType
278
-
279
235
if not use_preferred_locations or (
280
236
documents ._OperationType .IsWriteOperation (request .operation_type )
281
237
and not self .can_use_multiple_write_locations_for_request (request )
@@ -290,14 +246,6 @@ def resolve_service_endpoint(self, request):
290
246
and write_location in self .account_write_regional_routing_contexts_by_location ):
291
247
write_regional_routing_context = (
292
248
self .account_write_regional_routing_contexts_by_location )[write_location ]
293
- if (
294
- request .last_routed_location_endpoint_within_region is not None
295
- and request .last_routed_location_endpoint_within_region
296
- == write_regional_routing_context .get_primary ()
297
- or self .is_endpoint_unavailable_internal (write_regional_routing_context .get_primary (),
298
- endpoint_operation_type )
299
- ):
300
- return write_regional_routing_context .get_alternate ()
301
249
return write_regional_routing_context .get_primary ()
302
250
# if endpoint discovery is off for reads it should use passed in endpoint
303
251
return self .default_regional_routing_context .get_primary ()
@@ -308,14 +256,6 @@ def resolve_service_endpoint(self, request):
308
256
else self ._get_applicable_read_regional_routing_contexts (request )
309
257
)
310
258
regional_routing_context = regional_routing_contexts [location_index % len (regional_routing_contexts )]
311
- if (
312
- request .last_routed_location_endpoint_within_region is not None
313
- and request .last_routed_location_endpoint_within_region
314
- == regional_routing_context .get_primary ()
315
- or self .is_endpoint_unavailable_internal (regional_routing_context .get_primary (),
316
- endpoint_operation_type )
317
- ):
318
- return regional_routing_context .get_alternate ()
319
259
return regional_routing_context .get_primary ()
320
260
321
261
def should_refresh_endpoints (self ): # pylint: disable=too-many-return-statements
@@ -342,7 +282,7 @@ def should_refresh_endpoints(self): # pylint: disable=too-many-return-statement
342
282
return True
343
283
344
284
if not self .can_use_multiple_write_locations ():
345
- if self .is_location_unavailable (self .write_regional_routing_contexts [0 ],
285
+ if self .is_endpoint_unavailable (self .write_regional_routing_contexts [0 ]. get_primary () ,
346
286
EndpointOperationType .WriteType ):
347
287
# same logic as other
348
288
# Since most preferred write endpoint is unavailable, we can only refresh in background if
@@ -360,16 +300,7 @@ def should_refresh_endpoints(self): # pylint: disable=too-many-return-statement
360
300
return should_refresh
361
301
return False
362
302
363
- def is_location_unavailable (self , endpoint : RegionalRoutingContext , operation_type : str ):
364
- # For writes with single write region accounts only mark it unavailable if both are down
365
- if not _OperationType .IsReadOnlyOperation (operation_type ) and not self .can_use_multiple_write_locations ():
366
- return (self .is_endpoint_unavailable_internal (endpoint .get_primary (), operation_type )
367
- and self .is_endpoint_unavailable_internal (endpoint .get_alternate (), operation_type ))
368
-
369
- # For reads mark the region as down if primary endpoint is unavailable
370
- return self .is_endpoint_unavailable_internal (endpoint .get_primary (), operation_type )
371
-
372
- def is_endpoint_unavailable_internal (self , endpoint : str , expected_available_operation : str ):
303
+ def is_endpoint_unavailable (self , endpoint : str , expected_available_operation : str ):
373
304
unavailability_info = (
374
305
self .location_unavailability_info_by_endpoint [endpoint ]
375
306
if endpoint in self .location_unavailability_info_by_endpoint
@@ -420,24 +351,12 @@ def update_location_cache(self, write_locations=None, read_locations=None, enabl
420
351
if read_locations :
421
352
(self .account_read_regional_routing_contexts_by_location ,
422
353
self .account_locations_by_read_endpoints ,
423
- self .account_read_locations ) = get_endpoints_by_location (
424
- read_locations ,
425
- self .account_read_regional_routing_contexts_by_location ,
426
- self .default_regional_routing_context ,
427
- False ,
428
- self .connection_policy .UseMultipleWriteLocations
429
- )
354
+ self .account_read_locations ) = get_regional_routing_contexts_by_loc (read_locations )
430
355
431
356
if write_locations :
432
357
(self .account_write_regional_routing_contexts_by_location ,
433
358
self .account_locations_by_write_endpoints ,
434
- self .account_write_locations ) = get_endpoints_by_location (
435
- write_locations ,
436
- self .account_write_regional_routing_contexts_by_location ,
437
- self .default_regional_routing_context ,
438
- True ,
439
- self .connection_policy .UseMultipleWriteLocations
440
- )
359
+ self .account_write_locations ) = get_regional_routing_contexts_by_loc (write_locations )
441
360
442
361
# if preferred locations is empty and the default endpoint is a global endpoint,
443
362
# we should use the read locations from gateway as effective preferred locations
@@ -482,7 +401,8 @@ def get_preferred_regional_routing_contexts(
482
401
regional_endpoint = endpoints_by_location [location ] if location in endpoints_by_location \
483
402
else None
484
403
if regional_endpoint :
485
- if self .is_location_unavailable (regional_endpoint , expected_available_operation ):
404
+ if self .is_endpoint_unavailable (regional_endpoint .get_primary (),
405
+ expected_available_operation ):
486
406
unavailable_endpoints .append (regional_endpoint )
487
407
else :
488
408
regional_endpoints .append (regional_endpoint )
@@ -525,12 +445,10 @@ def can_use_multiple_write_locations_for_request(self, request): # pylint: disa
525
445
526
446
def endpoints_to_health_check (self ) -> Set [str ]:
527
447
# add read endpoints from gateway and in preferred locations
528
- health_check_endpoints = _get_health_check_endpoints (
529
- self .read_regional_routing_contexts
530
- )
448
+ health_check_endpoints = _get_health_check_endpoints (self .read_regional_routing_contexts )
531
449
# add first write endpoint in case that the write region is not in preferred locations
532
- health_check_endpoints = health_check_endpoints .union (_get_health_check_endpoints (
533
- self .write_regional_routing_contexts [:1 ]
450
+ health_check_endpoints = health_check_endpoints .union (
451
+ _get_health_check_endpoints ( self .write_regional_routing_contexts [:1 ]
534
452
))
535
453
536
454
return health_check_endpoints
0 commit comments