Skip to content

Fix keepalive gRPC channel options - #39

Merged
johnbywater merged 2 commits into
pyeventsourcing:1.3from
maarioos123:fix-keepalive-grpc-options
Oct 16, 2026
Merged

johnbywater merged 2 commits into
pyeventsourcing:1.3from
maarioos123:fix-keepalive-grpc-options

Conversation

@maarioos123

Copy link
Copy Markdown

Fixes #38.

What this changes

  • KeepAliveInterval sets grpc.keepalive_time_ms. It used to set grpc.keepalive_ms, which gRPC ignores, so no keepalive pings were sent.
  • KeepAliveTimeout also sets grpc.http2.ping_timeout_ms. With grpcio 1.84, an unanswered ping closes the connection only after this time (default 60 s), not after grpc.keepalive_timeout_ms.
  • TestGrpcOptions and the options table in the README use the new names.

The issue also suggested grpc.http2.max_pings_without_data=0. It was not needed: the first unanswered ping is enough to close the connection, so I left it out.

How I tested it

  • tests/test_client.py -k "TestGrpcOptions or keep_alive": 3 passed.
  • KurrentDB 26.1.2 (insecure, in memory), frozen with docker pause, 40 reads in threads, with KeepAliveInterval=5000&KeepAliveTimeout=5000:
    • Before this change: after 60 s, 40 of 40 reads still waited.
    • With this change: all 40 failed at 9.8 s with ServiceUnavailableError: Stream removed (ping timeout). After docker unpause, the same client read normally.
  • Normal use with this change and 5 s pings, for about 95 s with idle gaps up to 45 s: all reads and appends succeeded, and KurrentDB logged no too_many_pings or GOAWAY.

I did not run the full test suite, because it needs the cluster from docker-compose.yml.

🤖 Generated with Claude Code

@johnbywater

Copy link
Copy Markdown
Collaborator

Thanks for this @maarioos123! Looks good to me. Looks like some older image sources have been taken down after completing the move to Docker Hub. I will review the available images and adjust accordingly.

johnbywater and others added 2 commits October 16, 2026 16:33
KeepAliveInterval was passed as "grpc.keepalive_ms", which gRPC ignores, so
no keepalive pings were sent. Pass it as "grpc.keepalive_time_ms".

KeepAliveTimeout now also sets "grpc.http2.ping_timeout_ms". With grpcio
1.84, an unanswered ping closes the connection only after that time
(default 60s), not after "grpc.keepalive_timeout_ms".

Fixes pyeventsourcing#38

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
@johnbywater
johnbywater force-pushed the fix-keepalive-grpc-options branch from 92af4bf to 29284d0 Compare October 16, 2026 15:38
@johnbywater
johnbywater merged commit 29284d0 into pyeventsourcing:1.3 Oct 16, 2026
83 of 90 checks passed
@johnbywater

Copy link
Copy Markdown
Collaborator

Thanks again @maarioos123. These changes are in https://pypi.org/project/kurrentdbclient/1.3.4/ which has been tested with all the latest Docker images, updated versions of the dependencies, and Python 3.15. Let us know if you have any further issues.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

KeepAliveInterval sets an unknown gRPC option, so keepalive pings are never sent

2 participants