Repository navigation
Commit da44dd4
committed
pubsub: stop leaking Redis connections from abandoned subscriptions
Every pub/sub subscription pins one dedicated Redis connection in the
API process. redis-py 8 lowered the default asyncio pool size to 100,
and once 100 subscriptions are held every other Redis command (INCR on
subscribe, PUBLISH on node updates) fails with MaxConnectionsError,
which surfaced as HTTP 500 for all writes and took the whole pipeline
down.
The subscriptions piled up because a client that subscribes and dies
before its first listen() leaves last_poll unset, and
cleanup_stale_subscriptions() only ever looked at last_poll, so such
entries were never removed. A crash-looping external client exhausted
the pool in about an hour.
Fixes:
- cleanup_stale_subscriptions() ages never-polled subscriptions from
their creation time.
- On every subscribe, evict that user's never-polled subscriptions
older than abandoned_subscription_seconds (60s) and then enforce a cap
of max_subscriptions_per_user (20) active subscriptions, returning
HTTP 429 when exceeded.
- Pass an explicit redis_max_connections (1000) to the Redis pool.
- Close the previous PubSub when rebuilding after a connection error,
and close the half-initialised PubSub if SUBSCRIBE fails, so neither
path leaks a pooled connection.
- Keep the keep-alive loop alive across transient Redis errors.
- Map Redis MaxConnectionsError / ConnectionError to a 503 with
Retry-After instead of a generic 500.
All new settings are overridable through the environment via
PubSubSettings. Unit tests cover the cleanup, eviction, limit, rebuild
and keep-alive paths.
Signed-off-by: Denys Fedoryshchenko <denys.f@collabora.com>1 parent e9c829d commit da44dd4
4 files changed
Lines changed: 332 additions & 10 deletions
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
27 | 27 | | |
28 | 28 | | |
29 | 29 | | |
| 30 | + | |
| 31 | + | |
| 32 | + | |
| 33 | + | |
| 34 | + | |
| 35 | + | |
| 36 | + | |
| 37 | + | |
| 38 | + | |
| 39 | + | |
30 | 40 | | |
31 | 41 | | |
32 | 42 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
57 | 57 | | |
58 | 58 | | |
59 | 59 | | |
| 60 | + | |
60 | 61 | | |
61 | 62 | | |
62 | 63 | | |
| |||
80 | 81 | | |
81 | 82 | | |
82 | 83 | | |
83 | | - | |
| 84 | + | |
84 | 85 | | |
85 | 86 | | |
86 | 87 | | |
| |||
2146 | 2147 | | |
2147 | 2148 | | |
2148 | 2149 | | |
2149 | | - | |
| 2150 | + | |
| 2151 | + | |
| 2152 | + | |
| 2153 | + | |
| 2154 | + | |
| 2155 | + | |
| 2156 | + | |
2150 | 2157 | | |
2151 | 2158 | | |
2152 | 2159 | | |
| |||
2385 | 2392 | | |
2386 | 2393 | | |
2387 | 2394 | | |
| 2395 | + | |
| 2396 | + | |
| 2397 | + | |
| 2398 | + | |
| 2399 | + | |
| 2400 | + | |
| 2401 | + | |
| 2402 | + | |
| 2403 | + | |
| 2404 | + | |
2388 | 2405 | | |
2389 | 2406 | | |
2390 | 2407 | | |
2391 | 2408 | | |
| 2409 | + | |
| 2410 | + | |
| 2411 | + | |
| 2412 | + | |
| 2413 | + | |
| 2414 | + | |
| 2415 | + | |
2392 | 2416 | | |
2393 | 2417 | | |
2394 | 2418 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
33 | 33 | | |
34 | 34 | | |
35 | 35 | | |
| 36 | + | |
| 37 | + | |
| 38 | + | |
| 39 | + | |
36 | 40 | | |
37 | 41 | | |
38 | 42 | | |
| |||
80 | 84 | | |
81 | 85 | | |
82 | 86 | | |
83 | | - | |
| 87 | + | |
| 88 | + | |
| 89 | + | |
84 | 90 | | |
85 | 91 | | |
86 | 92 | | |
| |||
226 | 232 | | |
227 | 233 | | |
228 | 234 | | |
229 | | - | |
| 235 | + | |
| 236 | + | |
| 237 | + | |
| 238 | + | |
| 239 | + | |
| 240 | + | |
230 | 241 | | |
231 | 242 | | |
| 243 | + | |
| 244 | + | |
| 245 | + | |
| 246 | + | |
| 247 | + | |
| 248 | + | |
| 249 | + | |
| 250 | + | |
| 251 | + | |
| 252 | + | |
| 253 | + | |
| 254 | + | |
232 | 255 | | |
233 | 256 | | |
234 | 257 | | |
| |||
372 | 395 | | |
373 | 396 | | |
374 | 397 | | |
375 | | - | |
376 | 398 | | |
377 | 399 | | |
378 | 400 | | |
| 401 | + | |
| 402 | + | |
| 403 | + | |
379 | 404 | | |
380 | 405 | | |
381 | 406 | | |
382 | 407 | | |
383 | 408 | | |
384 | | - | |
| 409 | + | |
| 410 | + | |
| 411 | + | |
| 412 | + | |
| 413 | + | |
| 414 | + | |
385 | 415 | | |
386 | 416 | | |
387 | 417 | | |
| |||
407 | 437 | | |
408 | 438 | | |
409 | 439 | | |
| 440 | + | |
| 441 | + | |
| 442 | + | |
| 443 | + | |
| 444 | + | |
| 445 | + | |
| 446 | + | |
| 447 | + | |
| 448 | + | |
| 449 | + | |
| 450 | + | |
| 451 | + | |
| 452 | + | |
| 453 | + | |
| 454 | + | |
| 455 | + | |
| 456 | + | |
| 457 | + | |
| 458 | + | |
| 459 | + | |
| 460 | + | |
| 461 | + | |
| 462 | + | |
| 463 | + | |
| 464 | + | |
| 465 | + | |
| 466 | + | |
| 467 | + | |
| 468 | + | |
| 469 | + | |
| 470 | + | |
| 471 | + | |
| 472 | + | |
| 473 | + | |
| 474 | + | |
| 475 | + | |
| 476 | + | |
| 477 | + | |
| 478 | + | |
| 479 | + | |
| 480 | + | |
| 481 | + | |
| 482 | + | |
| 483 | + | |
| 484 | + | |
| 485 | + | |
| 486 | + | |
| 487 | + | |
410 | 488 | | |
411 | 489 | | |
412 | 490 | | |
| |||
479 | 557 | | |
480 | 558 | | |
481 | 559 | | |
482 | | - | |
483 | | - | |
| 560 | + | |
484 | 561 | | |
485 | 562 | | |
486 | 563 | | |
| |||
532 | 609 | | |
533 | 610 | | |
534 | 611 | | |
| 612 | + | |
535 | 613 | | |
536 | 614 | | |
537 | 615 | | |
538 | 616 | | |
| 617 | + | |
| 618 | + | |
| 619 | + | |
539 | 620 | | |
540 | 621 | | |
541 | 622 | | |
| |||
695 | 776 | | |
696 | 777 | | |
697 | 778 | | |
| 779 | + | |
| 780 | + | |
| 781 | + | |
| 782 | + | |
698 | 783 | | |
699 | 784 | | |
700 | 785 | | |
| |||
703 | 788 | | |
704 | 789 | | |
705 | 790 | | |
706 | | - | |
707 | | - | |
| 791 | + | |
| 792 | + | |
| 793 | + | |
| 794 | + | |
708 | 795 | | |
709 | 796 | | |
710 | 797 | | |
| |||
0 commit comments