e6data-python-connector 2.3.9rc4__tar.gz → 2.3.9rc6__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (77) hide show
  1. {e6data_python_connector-2.3.9rc4/e6data_python_connector.egg-info → e6data_python_connector-2.3.9rc6}/PKG-INFO +2 -2
  2. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/README.md +1 -1
  3. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/e6data_grpc.py +46 -36
  4. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/strategy.py +33 -17
  5. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6/e6data_python_connector.egg-info}/PKG-INFO +2 -2
  6. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/setup.py +1 -1
  7. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/LICENSE +0 -0
  8. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/MANIFEST.in +0 -0
  9. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/__init__.py +0 -0
  10. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/cluster_manager.py +0 -0
  11. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/cluster_server/__init__.py +0 -0
  12. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/cluster_server/cluster_pb2.py +0 -0
  13. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/cluster_server/cluster_pb2_grpc.py +0 -0
  14. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/common.py +0 -0
  15. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/constants.py +0 -0
  16. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/datainputstream.py +0 -0
  17. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/date_time_utils.py +0 -0
  18. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/dialect.py +0 -0
  19. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/e6x_vector/__init__.py +0 -0
  20. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/e6x_vector/constants.py +0 -0
  21. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/e6x_vector/ttypes.py +0 -0
  22. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/exceptions.py +0 -0
  23. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/server/QueryEngineService.py +0 -0
  24. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/server/__init__.py +0 -0
  25. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/server/constants.py +0 -0
  26. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/server/e6x_engine_pb2.py +0 -0
  27. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/server/e6x_engine_pb2.pyi +0 -0
  28. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/server/e6x_engine_pb2_grpc.py +0 -0
  29. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/server/ttypes.py +0 -0
  30. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector/typeId.py +0 -0
  31. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector.egg-info/SOURCES.txt +0 -0
  32. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector.egg-info/dependency_links.txt +0 -0
  33. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector.egg-info/entry_points.txt +0 -0
  34. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector.egg-info/requires.txt +0 -0
  35. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/e6data_python_connector.egg-info/top_level.txt +0 -0
  36. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/pyproject.toml +0 -0
  37. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/setup.cfg +0 -0
  38. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/__init__.py +0 -0
  39. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/analyze_38_nines.py +0 -0
  40. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/analyze_all_cases.py +0 -0
  41. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/analyze_binary.py +0 -0
  42. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/analyze_correct_value.py +0 -0
  43. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/analyze_fields.py +0 -0
  44. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/check_decimal_errors.py +0 -0
  45. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/cleanup_test_files.py +0 -0
  46. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/debug_38_nines.py +0 -0
  47. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/debug_binary.py +0 -0
  48. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/final_test.py +0 -0
  49. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/move_tests.py +0 -0
  50. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/quick_test.py +0 -0
  51. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_38_nines.py +0 -0
  52. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_all_decimal128_cases.py +0 -0
  53. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_cluster_manager_efficiency.py +0 -0
  54. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_cluster_manager_none_strategy.py +0 -0
  55. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_cluster_manager_strategy.py +0 -0
  56. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_comprehensive.py +0 -0
  57. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_current_implementation.py +0 -0
  58. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_decimal128_binary_parsing.py +0 -0
  59. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_decimal128_parsing.py +0 -0
  60. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_fix.py +0 -0
  61. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_improved_parsing.py +0 -0
  62. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_known_case.py +0 -0
  63. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_manual_analysis.py +0 -0
  64. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_mock_server.py +0 -0
  65. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_multiprocessing_fix.py +0 -0
  66. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_new_implementation.py +0 -0
  67. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_specific_binary.py +0 -0
  68. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_strategy.py +0 -0
  69. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_strategy_logic.py +0 -0
  70. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_strategy_persistence_fix.py +0 -0
  71. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_strategy_sharing_fix.py +0 -0
  72. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/test_user_binary_value.py +0 -0
  73. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/tests.py +0 -0
  74. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/tests_grpc.py +0 -0
  75. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/validate_decimal128.py +0 -0
  76. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/validate_implementation.py +0 -0
  77. {e6data_python_connector-2.3.9rc4 → e6data_python_connector-2.3.9rc6}/test/verify_decimal_fix.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.2
2
2
  Name: e6data-python-connector
3
- Version: 2.3.9rc4
3
+ Version: 2.3.9rc6
4
4
  Summary: Client for the e6data distributed SQL Engine.
5
5
  Home-page: https://github.com/e6x-labs/e6data-python-connector
6
6
  Author: e6data, Inc.
@@ -38,7 +38,7 @@ Dynamic: summary
38
38
 
39
39
  # e6data Python Connector
40
40
 
41
- ![version](https://img.shields.io/badge/version-2.3.9rc4-blue.svg)
41
+ ![version](https://img.shields.io/badge/version-2.3.9rc6-blue.svg)
42
42
 
43
43
  ## Introduction
44
44
 
@@ -1,6 +1,6 @@
1
1
  # e6data Python Connector
2
2
 
3
- ![version](https://img.shields.io/badge/version-2.3.9rc4-blue.svg)
3
+ ![version](https://img.shields.io/badge/version-2.3.9rc6-blue.svg)
4
4
 
5
5
  ## Introduction
6
6
 
@@ -7,6 +7,7 @@ from __future__ import absolute_import
7
7
  from __future__ import unicode_literals
8
8
 
9
9
  import datetime
10
+ import logging
10
11
  import re
11
12
  import sys
12
13
  import time
@@ -27,6 +28,9 @@ from e6data_python_connector.datainputstream import get_query_columns_info, read
27
28
  from e6data_python_connector.server import e6x_engine_pb2_grpc, e6x_engine_pb2
28
29
  from e6data_python_connector.typeId import *
29
30
 
31
+ # Set up logging
32
+ logger = logging.getLogger(__name__)
33
+
30
34
  apilevel = '2.0'
31
35
  threadsafety = 2 # Threads may share the e6xdb and connections.
32
36
  paramstyle = 'pyformat' # Python extended format codes, e.g. ...WHERE name=%(name)s
@@ -134,20 +138,20 @@ def _get_shared_strategy():
134
138
  global _strategy_manager, _shared_strategy
135
139
 
136
140
  # Try to use multiprocessing.Manager for process-safe storage
137
- try:
138
- if _strategy_manager is None:
139
- _strategy_manager = multiprocessing.Manager()
140
- _shared_strategy = _strategy_manager.dict()
141
- _shared_strategy['active_strategy'] = None
142
- _shared_strategy['last_check_time'] = 0
143
- _shared_strategy['pending_strategy'] = None
144
- _shared_strategy['query_strategy_map'] = _strategy_manager.dict()
145
- _shared_strategy['last_transition_time'] = 0
146
- _shared_strategy['session_invalidated'] = False
147
- return _shared_strategy
148
- except:
149
- # Fall back to thread-local storage if Manager fails
150
- return _local_strategy_cache
141
+ # try:
142
+ # if _strategy_manager is None:
143
+ # _strategy_manager = multiprocessing.Manager()
144
+ # _shared_strategy = _strategy_manager.dict()
145
+ # _shared_strategy['active_strategy'] = None
146
+ # _shared_strategy['last_check_time'] = 0
147
+ # _shared_strategy['pending_strategy'] = None
148
+ # _shared_strategy['query_strategy_map'] = _strategy_manager.dict()
149
+ # _shared_strategy['last_transition_time'] = 0
150
+ # _shared_strategy['session_invalidated'] = False
151
+ # return _shared_strategy
152
+ # except:
153
+ # # Fall back to thread-local storage if Manager fails
154
+ return _local_strategy_cache
151
155
 
152
156
 
153
157
  def _get_active_strategy():
@@ -177,8 +181,11 @@ def _set_active_strategy(strategy):
177
181
  current_time = time.time()
178
182
 
179
183
  # Only update transition time if strategy actually changed
180
- if shared_strategy['active_strategy'] != normalized_strategy:
184
+ old_strategy = shared_strategy['active_strategy']
185
+ if old_strategy != normalized_strategy:
181
186
  shared_strategy['last_transition_time'] = current_time
187
+ # Debug log for strategy switches
188
+ logger.debug(f"Strategy switched from {old_strategy} to {normalized_strategy}")
182
189
 
183
190
  shared_strategy['active_strategy'] = normalized_strategy
184
191
  shared_strategy['last_check_time'] = current_time
@@ -207,7 +214,12 @@ def _set_pending_strategy(strategy):
207
214
  current_active = shared_strategy['active_strategy']
208
215
 
209
216
  if normalized_strategy != current_active:
217
+ old_pending = shared_strategy.get('pending_strategy')
210
218
  shared_strategy['pending_strategy'] = normalized_strategy
219
+
220
+ # Debug log for pending strategy changes
221
+ if old_pending != normalized_strategy:
222
+ logger.debug(f"Pending strategy changed from {old_pending} to {normalized_strategy}")
211
223
 
212
224
 
213
225
  def _apply_pending_strategy():
@@ -219,12 +231,15 @@ def _apply_pending_strategy():
219
231
  new_strategy = shared_strategy['pending_strategy']
220
232
  current_time = time.time()
221
233
 
234
+ logger.debug(f"Strategy transition initiated: {old_strategy} -> {new_strategy}")
235
+
222
236
  shared_strategy['active_strategy'] = new_strategy
223
237
  shared_strategy['pending_strategy'] = None
224
238
  shared_strategy['last_check_time'] = current_time
225
239
  shared_strategy['last_transition_time'] = current_time
226
240
  shared_strategy['session_invalidated'] = True # Invalidate all sessions
227
241
 
242
+ logger.debug(f"Strategy successfully applied and sessions invalidated")
228
243
  return new_strategy
229
244
  return None
230
245
 
@@ -380,7 +395,6 @@ class Connection(object):
380
395
  """
381
396
  self.grpc_auto_resume_timeout_seconds = self._grpc_options.pop('grpc_auto_resume_timeout_seconds')
382
397
  self._create_client()
383
- self._hash = str(datetime.datetime.now().timestamp()) + 'hash' + str(id(self))
384
398
 
385
399
  @property
386
400
  def _get_grpc_options(self):
@@ -521,7 +535,6 @@ class Connection(object):
521
535
  _set_pending_strategy(new_strategy)
522
536
  # Don't apply immediately - let new queries use fresh connections
523
537
  except _InactiveRpcError as e:
524
- print(self._hash, self.cluster_name, 'Error during authentication with active strategy:', active_strategy, file=sys.stderr)
525
538
  if e.code() == grpc.StatusCode.UNKNOWN and 'status: 456' in e.details():
526
539
  # Strategy changed, clear cache and retry
527
540
  _clear_strategy_cache()
@@ -563,7 +576,6 @@ class Connection(object):
563
576
  # Don't apply immediately - let new queries use fresh connections
564
577
  break
565
578
  except _InactiveRpcError as e:
566
- print(self._hash, self.cluster_name, 'Error during authentication with strategy:', strategy, file=sys.stderr)
567
579
  if e.code() == grpc.StatusCode.UNKNOWN and 'status: 456' in e.details():
568
580
  # Wrong strategy, try the next one
569
581
  last_error = e
@@ -590,24 +602,23 @@ class Connection(object):
590
602
  cluster_uuid=self.cluster_name,
591
603
  timeout=self.grpc_auto_resume_timeout_seconds
592
604
  ).resume()
593
- print(self._hash, self.cluster_name, 'Cluster resume status:', status, file=sys.stderr)
594
605
  if status:
595
- # return self.get_session_id
596
- authenticate_request = e6x_engine_pb2.AuthenticateRequest(
597
- user=self.__username,
598
- password=self.__password
599
- )
600
- authenticate_response = self._client.authenticate(
601
- authenticate_request,
602
- metadata=_get_grpc_header(cluster=self.cluster_name, strategy=_get_active_strategy())
603
- )
604
- self._session_id = authenticate_response.sessionId
605
- # Check for new strategy in authenticate response
606
- if hasattr(authenticate_response, 'new_strategy') and authenticate_response.new_strategy:
607
- new_strategy = authenticate_response.new_strategy.lower()
608
- if new_strategy != _get_active_strategy():
609
- _set_pending_strategy(new_strategy)
610
- # Don't apply immediately - let new queries use fresh connections
606
+ return self.get_session_id
607
+ # authenticate_request = e6x_engine_pb2.AuthenticateRequest(
608
+ # user=self.__username,
609
+ # password=self.__password
610
+ # )
611
+ # authenticate_response = self._client.authenticate(
612
+ # authenticate_request,
613
+ # metadata=_get_grpc_header(cluster=self.cluster_uuid, strategy=_get_active_strategy())
614
+ # )
615
+ # self._session_id = authenticate_response.sessionId
616
+ # # Check for new strategy in authenticate response
617
+ # if hasattr(authenticate_response, 'new_strategy') and authenticate_response.new_strategy:
618
+ # new_strategy = authenticate_response.new_strategy.lower()
619
+ # if new_strategy != _get_active_strategy():
620
+ # _set_pending_strategy(new_strategy)
621
+ # # Don't apply immediately - let new queries use fresh connections
611
622
  else:
612
623
  raise e
613
624
  else:
@@ -615,7 +626,6 @@ class Connection(object):
615
626
  else:
616
627
  raise e
617
628
  except Exception as e:
618
- print(self._hash, self.cluster_name, 'Error during authentication:', e, file=sys.stderr)
619
629
  self._channel.close()
620
630
  raise e
621
631
  return self._session_id
@@ -41,23 +41,23 @@ def _initialize_shared_state():
41
41
  if _shared_strategy is not None:
42
42
  return _shared_strategy
43
43
 
44
- try:
45
- # Try to create multiprocessing Manager
46
- _manager = multiprocessing.Manager()
47
- _shared_strategy = _manager.dict({
48
- 'active_strategy': None,
49
- 'last_check_time': 0,
50
- 'pending_strategy': None,
51
- 'query_strategy_map': _manager.dict(),
52
- 'last_transition_time': 0,
53
- 'session_invalidated': False
54
- })
55
- _logger.debug("Successfully initialized multiprocessing Manager for strategy sharing")
56
- return _shared_strategy
57
- except Exception as e:
58
- # Fall back to thread-local storage if Manager fails
59
- _logger.warning(f"Failed to initialize multiprocessing Manager: {e}. Using thread-local storage.")
60
- return _local_strategy_cache
44
+ # try:
45
+ # # Try to create multiprocessing Manager
46
+ # _manager = multiprocessing.Manager()
47
+ # _shared_strategy = _manager.dict({
48
+ # 'active_strategy': None,
49
+ # 'last_check_time': 0,
50
+ # 'pending_strategy': None,
51
+ # 'query_strategy_map': _manager.dict(),
52
+ # 'last_transition_time': 0,
53
+ # 'session_invalidated': False
54
+ # })
55
+ # _logger.debug("Successfully initialized multiprocessing Manager for strategy sharing")
56
+ # return _shared_strategy
57
+ # except Exception as e:
58
+ # # Fall back to thread-local storage if Manager fails
59
+ # _logger.warning(f"Failed to initialize multiprocessing Manager: {e}. Using thread-local storage.")
60
+ return _local_strategy_cache
61
61
 
62
62
 
63
63
  def _get_shared_strategy():
@@ -85,8 +85,14 @@ def _set_active_strategy(strategy):
85
85
  _logger.warning(f"Invalid strategy value: {strategy}. Must be 'blue' or 'green'.")
86
86
  return
87
87
 
88
+ old_strategy = shared_strategy.get('active_strategy')
88
89
  shared_strategy['active_strategy'] = normalized_strategy
89
90
  shared_strategy['last_check_time'] = time.time()
91
+
92
+ # Debug log for strategy switches
93
+ if old_strategy != normalized_strategy:
94
+ _logger.debug(f"Strategy switched from {old_strategy} to {normalized_strategy}")
95
+
90
96
  _logger.info(f"Active deployment strategy set to: {normalized_strategy}")
91
97
 
92
98
 
@@ -105,7 +111,13 @@ def _set_pending_strategy(strategy):
105
111
 
106
112
  current_active = shared_strategy.get('active_strategy')
107
113
  if normalized_strategy != current_active:
114
+ old_pending = shared_strategy.get('pending_strategy')
108
115
  shared_strategy['pending_strategy'] = normalized_strategy
116
+
117
+ # Debug log for pending strategy changes
118
+ if old_pending != normalized_strategy:
119
+ _logger.debug(f"Pending strategy changed from {old_pending} to {normalized_strategy}")
120
+
109
121
  _logger.info(f"Pending deployment strategy set to: {normalized_strategy}")
110
122
 
111
123
 
@@ -160,11 +172,15 @@ def _apply_pending_strategy():
160
172
  if len(query_map) == 0:
161
173
  # No active queries, safe to transition
162
174
  _logger.info(f"Last query completed, applying pending strategy: {pending_strategy}")
175
+ _logger.debug(f"Strategy transition initiated: {active_strategy} -> {pending_strategy}")
176
+
163
177
  shared_strategy['active_strategy'] = pending_strategy
164
178
  shared_strategy['pending_strategy'] = None
165
179
  shared_strategy['last_transition_time'] = time.time()
166
180
  shared_strategy['session_invalidated'] = True # Invalidate all sessions
181
+
167
182
  _logger.info(f"Strategy transition completed: {active_strategy} -> {pending_strategy}")
183
+ _logger.debug(f"Strategy successfully applied and sessions invalidated")
168
184
 
169
185
 
170
186
  def _is_strategy_cache_valid():
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.2
2
2
  Name: e6data-python-connector
3
- Version: 2.3.9rc4
3
+ Version: 2.3.9rc6
4
4
  Summary: Client for the e6data distributed SQL Engine.
5
5
  Home-page: https://github.com/e6x-labs/e6data-python-connector
6
6
  Author: e6data, Inc.
@@ -38,7 +38,7 @@ Dynamic: summary
38
38
 
39
39
  # e6data Python Connector
40
40
 
41
- ![version](https://img.shields.io/badge/version-2.3.9rc4-blue.svg)
41
+ ![version](https://img.shields.io/badge/version-2.3.9rc6-blue.svg)
42
42
 
43
43
  ## Introduction
44
44
 
@@ -12,7 +12,7 @@
12
12
 
13
13
  import setuptools
14
14
 
15
- VERSION = (2, 3, 9,'rc4')
15
+ VERSION = (2, 3, 9,'rc6')
16
16
 
17
17
 
18
18
  def get_long_desc():