Skip to content

Commit 164bef4

Browse files
authored
feat: session state transfer (#517)
1 parent e758863 commit 164bef4

37 files changed

+988
-260
lines changed

.github/styles/config/vocabularies/Aurora/accept.txt

Lines changed: 0 additions & 17 deletions
This file was deleted.

.github/workflows/autoscaling_tests.yml

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -10,20 +10,18 @@ jobs:
1010

1111
steps:
1212
- name: 'Clone repository'
13-
uses: actions/checkout@v3
14-
with:
15-
fetch-depth: 50
13+
uses: actions/checkout@v4
1614

1715
- name: 'Set up JDK 8'
18-
uses: actions/setup-java@v3
16+
uses: actions/setup-java@v4
1917
with:
2018
distribution: 'corretto'
2119
java-version: 8
2220

2321
- name: Install poetry
24-
uses: abatilo/actions-poetry@v2
22+
uses: abatilo/actions-poetry@v3
2523
with:
26-
poetry-version: '1.4.2'
24+
poetry-version: '1.8.2'
2725

2826
- name: Install dependencies
2927
run: poetry install
@@ -61,7 +59,7 @@ jobs:
6159

6260
- name: 'Archive results'
6361
if: always()
64-
uses: actions/upload-artifact@v3
62+
uses: actions/upload-artifact@v4
6563
with:
6664
name: pytest-autoscaling-report
6765
path: ./tests/integration/container/reports

.github/workflows/draft_release.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@ jobs:
3232
- name: 'Install poetry'
3333
uses: abatilo/actions-poetry@v2
3434
with:
35-
poetry-version: '1.4.2'
35+
poetry-version: '1.8.2'
3636
- name: 'Install dependencies'
3737
run: poetry install
3838
- name: 'Run mypy - static type checking'

.github/workflows/integration_tests.yml

Lines changed: 6 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -19,26 +19,24 @@ jobs:
1919

2020
steps:
2121
- name: 'Clone repository'
22-
uses: actions/checkout@v3
23-
with:
24-
fetch-depth: 50
22+
uses: actions/checkout@v4
2523

2624
- name: 'Set up JDK 8'
27-
uses: actions/setup-java@v3
25+
uses: actions/setup-java@v4
2826
with:
2927
distribution: 'corretto'
3028
java-version: 8
3129

3230
- name: Install poetry
33-
uses: abatilo/actions-poetry@v2
31+
uses: abatilo/actions-poetry@v3
3432
with:
35-
poetry-version: '1.4.2'
33+
poetry-version: '1.8.2'
3634

3735
- name: Install dependencies
3836
run: poetry install
3937

4038
- name: 'Configure AWS Credentials'
41-
uses: aws-actions/configure-aws-credentials@v1
39+
uses: aws-actions/configure-aws-credentials@v4
4240
with:
4341
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
4442
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
@@ -70,7 +68,7 @@ jobs:
7068

7169
- name: 'Archive results'
7270
if: always()
73-
uses: actions/upload-artifact@v3
71+
uses: actions/upload-artifact@v4
7472
with:
7573
name: pytest-integration-report
7674
path: ./tests/integration/container/reports

.github/workflows/integration_tests_codebuild.yml

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -17,20 +17,18 @@ jobs:
1717

1818
steps:
1919
- name: 'Clone repository'
20-
uses: actions/checkout@v3
21-
with:
22-
fetch-depth: 50
20+
uses: actions/checkout@v4
2321

2422
- name: 'Set up JDK 8'
25-
uses: actions/setup-java@v3
23+
uses: actions/setup-java@v4
2624
with:
2725
distribution: 'corretto'
2826
java-version: 8
2927

3028
- name: Install poetry
31-
uses: abatilo/actions-poetry@v2
29+
uses: abatilo/actions-poetry@v3
3230
with:
33-
poetry-version: '1.4.2'
31+
poetry-version: '1.8.2'
3432

3533
- name: Install dependencies
3634
run: poetry install
@@ -71,7 +69,7 @@ jobs:
7169

7270
- name: 'Archive results'
7371
if: always()
74-
uses: actions/upload-artifact@v3
72+
uses: actions/upload-artifact@v4
7573
with:
7674
name: pytest-integration-report
7775
path: ./tests/integration/container/reports

.github/workflows/main.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ jobs:
2525
poetry-version: ["1.8.2"]
2626

2727
steps:
28-
- uses: actions/checkout@v3
28+
- uses: actions/checkout@v4
2929
- name: Set up Python ${{ matrix.python-version }}
3030
uses: actions/setup-python@v4
3131
with:

.github/workflows/mysql_performance_tests.yml

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -10,26 +10,26 @@ jobs:
1010

1111
steps:
1212
- name: 'Clone repository'
13-
uses: actions/checkout@v3
13+
uses: actions/checkout@v4
1414
with:
1515
fetch-depth: 50
1616

1717
- name: 'Set up JDK 8'
18-
uses: actions/setup-java@v3
18+
uses: actions/setup-java@v4
1919
with:
2020
distribution: 'corretto'
2121
java-version: 8
2222

2323
- name: Install poetry
2424
uses: abatilo/actions-poetry@v2
2525
with:
26-
poetry-version: '1.4.2'
26+
poetry-version: '1.8.2'
2727

2828
- name: Install dependencies
2929
run: poetry install
3030

3131
- name: 'Configure AWS Credentials'
32-
uses: aws-actions/configure-aws-credentials@v1
32+
uses: aws-actions/configure-aws-credentials@v4
3333
with:
3434
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
3535
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
@@ -63,7 +63,7 @@ jobs:
6363

6464
- name: 'Archive results'
6565
if: always()
66-
uses: actions/upload-artifact@v3
66+
uses: actions/upload-artifact@v4
6767
with:
6868
name: pytest-performance-report
6969
path: ./tests/integration/container/reports

.github/workflows/pg_performance_tests.yml

Lines changed: 6 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -10,26 +10,24 @@ jobs:
1010

1111
steps:
1212
- name: 'Clone repository'
13-
uses: actions/checkout@v3
14-
with:
15-
fetch-depth: 50
13+
uses: actions/checkout@v4
1614

1715
- name: 'Set up JDK 8'
18-
uses: actions/setup-java@v3
16+
uses: actions/setup-java@v4
1917
with:
2018
distribution: 'corretto'
2119
java-version: 8
2220

2321
- name: Install poetry
24-
uses: abatilo/actions-poetry@v2
22+
uses: abatilo/actions-poetry@v3
2523
with:
26-
poetry-version: '1.4.2'
24+
poetry-version: '1.8.2'
2725

2826
- name: Install dependencies
2927
run: poetry install
3028

3129
- name: 'Configure AWS Credentials'
32-
uses: aws-actions/configure-aws-credentials@v1
30+
uses: aws-actions/configure-aws-credentials@v4
3331
with:
3432
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
3533
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
@@ -63,7 +61,7 @@ jobs:
6361

6462
- name: 'Archive results'
6563
if: always()
66-
uses: actions/upload-artifact@v3
64+
uses: actions/upload-artifact@v4
6765
with:
6866
name: pytest-performance-report
6967
path: ./tests/integration/container/reports

.github/workflows/vale.yml

Lines changed: 0 additions & 19 deletions
This file was deleted.

README.md

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -106,7 +106,6 @@ The following table lists the connection properties used with the AWS Advanced P
106106
| `failover_reader_connect_timeout_sec` | [Failover Plugin](./docs/using-the-python-driver/using-plugins/UsingTheFailoverPlugin.md) |
107107
| `failover_timeout_sec` | [Failover Plugin](./docs/using-the-python-driver/using-plugins/UsingTheFailoverPlugin.md) |
108108
| `failover_writer_reconnect_interval_sec` | [Failover Plugin](./docs/using-the-python-driver/using-plugins/UsingTheFailoverPlugin.md) |
109-
| `keep_session_state_on_failover` | [Failover Plugin](./docs/using-the-python-driver/using-plugins/UsingTheFailoverPlugin.md) |
110109
| `failure_detection_count` | [Host Monitoring Plugin](./docs/using-the-python-driver/using-plugins/UsingTheHostMonitoringPlugin.md) |
111110
| `failure_detection_enabled` | [Host Monitoring Plugin](./docs/using-the-python-driver/using-plugins/UsingTheHostMonitoringPlugin.md) |
112111
| `failure_detection_interval_ms` | [Host Monitoring Plugin](./docs/using-the-python-driver/using-plugins/UsingTheHostMonitoringPlugin.md) |

aws_advanced_python_wrapper/failover_plugin.py

Lines changed: 4 additions & 48 deletions
Original file line numberDiff line numberDiff line change
@@ -86,8 +86,6 @@ def __init__(self, plugin_service: PluginService, props: Properties):
8686
self._properties)
8787
self._failover_reader_connect_timeout_sec = WrapperProperties.FAILOVER_READER_CONNECT_TIMEOUT_SEC.get_float(
8888
self._properties)
89-
self._keep_session_state_on_failover = WrapperProperties.KEEP_SESSION_STATE_ON_FAILOVER.get_bool(
90-
self._properties)
9189
self._telemetry_failover_additional_top_trace_setting = (
9290
WrapperProperties.TELEMETRY_FAILOVER_ADDITIONAL_TOP_TRACE.get_bool(self._properties))
9391
self._failover_mode: FailoverMode
@@ -162,12 +160,6 @@ def execute(self, target: type, method_name: str, execute_func: Callable, *args:
162160
if self._is_closed and not self._allowed_on_closed_connection(method_name):
163161
self._invalid_invocation_on_closed_connection()
164162

165-
if method_name == "Connection.set_read_only" and args is not None and len(args) > 0:
166-
self._saved_read_only_status = bool(args[0])
167-
168-
if method_name == "Connection.autocommit_setter" and args is not None and len(args) > 0:
169-
self._saved_auto_commit_status = bool(args[0])
170-
171163
try:
172164
if self._requires_update_topology(method_name):
173165
self._update_topology(False)
@@ -234,13 +226,6 @@ def _connect(
234226
self._host_list_provider_service, host,
235227
properties,
236228
connect_func)
237-
if self._keep_session_state_on_failover:
238-
self._saved_read_only_status = False if self._saved_read_only_status == self._plugin_service.driver_dialect.is_read_only(
239-
conn) \
240-
else self._saved_read_only_status
241-
self._saved_auto_commit_status = False \
242-
if self._saved_read_only_status == self._plugin_service.driver_dialect.get_autocommit(conn) \
243-
else self._saved_auto_commit_status
244229

245230
if is_initial_connection:
246231
self._plugin_service.refresh_host_list(conn)
@@ -261,18 +246,15 @@ def _update_topology(self, force_update: bool):
261246
else:
262247
self._plugin_service.refresh_host_list()
263248

264-
def _transfer_session_state(self, from_conn: Connection, to_conn: Connection):
265-
if from_conn is None or self._plugin_service.driver_dialect.is_closed(from_conn) or to_conn is None:
266-
return
267-
268-
self._plugin_service.driver_dialect.transfer_session_state(from_conn, to_conn)
269-
270249
def _failover(self, failed_host: Optional[HostInfo]):
271250
"""
272251
Initiates the failover procedure. This process tries to establish a new connection to an instance in the topology.
273252
274253
:param failed_host: The host with network errors.
275254
"""
255+
if failed_host is not None:
256+
self._plugin_service.set_availability(failed_host.as_aliases(), HostAvailability.UNAVAILABLE)
257+
276258
if self._failover_mode == FailoverMode.STRICT_WRITER:
277259
self._failover_writer()
278260
else:
@@ -312,8 +294,6 @@ def _failover_reader(self, failed_host: Optional[HostInfo]):
312294
else:
313295
if result.exception is not None:
314296
raise result.exception
315-
if self._keep_session_state_on_failover:
316-
self.restore_session_state(result.connection)
317297
if result.connection is not None and result.new_host is not None:
318298
self._plugin_service.set_current_connection(result.connection, result.new_host)
319299

@@ -342,7 +322,7 @@ def _failover_reader(self, failed_host: Optional[HostInfo]):
342322

343323
def _failover_writer(self):
344324
telemetry_factory = self._plugin_service.get_telemetry_factory()
345-
context = telemetry_factory.open_telemetry_context("failover to writer node", TelemetryTraceLevel.NESTED)
325+
context = telemetry_factory.open_telemetry_context("failover to writer host", TelemetryTraceLevel.NESTED)
346326
self._failover_writer_triggered_counter.inc()
347327

348328
try:
@@ -356,8 +336,6 @@ def _failover_writer(self):
356336
raise FailoverFailedError(Messages.get("FailoverPlugin.UnableToConnectToWriter"))
357337

358338
writer_host = self._get_writer(result.topology)
359-
if self._keep_session_state_on_failover:
360-
self.restore_session_state(result.new_connection)
361339

362340
self._plugin_service.set_current_connection(result.new_connection, writer_host)
363341

@@ -381,21 +359,6 @@ def _failover_writer(self):
381359
if self._telemetry_failover_additional_top_trace_setting:
382360
telemetry_factory.post_copy(context, TelemetryTraceLevel.FORCE_TOP_LEVEL)
383361

384-
def restore_session_state(self, conn: Optional[Connection]):
385-
"""
386-
Restores partial session state from saved values to a connection.
387-
388-
:param conn: The connection to transfer state to.
389-
"""
390-
if conn is None:
391-
return
392-
393-
if self._saved_read_only_status is not None:
394-
self._plugin_service.driver_dialect.set_read_only(conn, self._saved_read_only_status)
395-
396-
if self._saved_auto_commit_status is not None:
397-
self._plugin_service.driver_dialect.set_autocommit(conn, self._saved_auto_commit_status)
398-
399362
def _invalidate_current_connection(self):
400363
"""
401364
Invalidate the current connection before switching to a new connection.
@@ -451,13 +414,6 @@ def _connect_to(self, host: HostInfo):
451414
"""
452415
try:
453416
connection_for_host = self._plugin_service.connect(host, self._properties)
454-
current_connection = self._plugin_service.current_connection
455-
456-
if connection_for_host is not None and current_connection is not None and \
457-
current_connection != connection_for_host:
458-
self._transfer_session_state(current_connection, connection_for_host)
459-
self._invalidate_current_connection()
460-
461417
self._plugin_service.set_current_connection(connection_for_host, host)
462418
self._plugin_service.update_in_transaction(False)
463419

0 commit comments

Comments
 (0)