pollConfigDefaults.ts 3.9 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182
  1. /**
  2. * Bridge poll interval defaults. Extracted from pollConfig.ts so callers
  3. * that don't need live GrowthBook tuning (daemon via Agent SDK) can avoid
  4. * the growthbook.ts → config.ts → file.ts → sessionStorage.ts → commands.ts
  5. * transitive dependency chain.
  6. */
  7. /**
  8. * Poll interval when actively seeking work (no transport / below maxSessions).
  9. * Governs user-visible "connecting…" latency on initial work pickup and
  10. * recovery speed after the server re-dispatches a work item.
  11. */
  12. const POLL_INTERVAL_MS_NOT_AT_CAPACITY = 2000
  13. /**
  14. * Poll interval when the transport is connected. Runs independently of
  15. * heartbeat — when both are enabled, the heartbeat loop breaks out to poll
  16. * at this interval. Set to 0 to disable at-capacity polling entirely.
  17. *
  18. * Server-side constraints that bound this value:
  19. * - BRIDGE_LAST_POLL_TTL = 4h (Redis key expiry → environment auto-archived)
  20. * - max_poll_stale_seconds = 24h (session-creation health gate, currently disabled)
  21. *
  22. * 10 minutes gives 24× headroom on the Redis TTL while still picking up
  23. * server-initiated token-rotation redispatches within one poll cycle.
  24. * The transport auto-reconnects internally for 10 minutes on transient WS
  25. * failures, so poll is not the recovery path — it's strictly a liveness
  26. * signal plus a backstop for permanent close.
  27. */
  28. const POLL_INTERVAL_MS_AT_CAPACITY = 600_000
  29. /**
  30. * Multisession bridge (bridgeMain.ts) poll intervals. Defaults match the
  31. * single-session values so existing GrowthBook configs without these fields
  32. * preserve current behavior. Ops can tune these independently via the
  33. * tengu_bridge_poll_interval_config GB flag.
  34. */
  35. const MULTISESSION_POLL_INTERVAL_MS_NOT_AT_CAPACITY =
  36. POLL_INTERVAL_MS_NOT_AT_CAPACITY
  37. const MULTISESSION_POLL_INTERVAL_MS_PARTIAL_CAPACITY =
  38. POLL_INTERVAL_MS_NOT_AT_CAPACITY
  39. const MULTISESSION_POLL_INTERVAL_MS_AT_CAPACITY = POLL_INTERVAL_MS_AT_CAPACITY
  40. export type PollIntervalConfig = {
  41. poll_interval_ms_not_at_capacity: number
  42. poll_interval_ms_at_capacity: number
  43. non_exclusive_heartbeat_interval_ms: number
  44. multisession_poll_interval_ms_not_at_capacity: number
  45. multisession_poll_interval_ms_partial_capacity: number
  46. multisession_poll_interval_ms_at_capacity: number
  47. reclaim_older_than_ms: number
  48. session_keepalive_interval_v2_ms: number
  49. }
  50. export const DEFAULT_POLL_CONFIG: PollIntervalConfig = {
  51. poll_interval_ms_not_at_capacity: POLL_INTERVAL_MS_NOT_AT_CAPACITY,
  52. poll_interval_ms_at_capacity: POLL_INTERVAL_MS_AT_CAPACITY,
  53. // 0 = disabled. When > 0, at-capacity loops send per-work-item heartbeats
  54. // at this interval. Independent of poll_interval_ms_at_capacity — both may
  55. // run (heartbeat periodically yields to poll). 60s gives 5× headroom under
  56. // the server's 300s heartbeat TTL. Named non_exclusive to distinguish from
  57. // the old heartbeat_interval_ms field (either-or semantics in pre-#22145
  58. // clients — heartbeat suppressed poll). Old clients ignore this key; ops
  59. // can set both fields during rollout.
  60. non_exclusive_heartbeat_interval_ms: 0,
  61. multisession_poll_interval_ms_not_at_capacity:
  62. MULTISESSION_POLL_INTERVAL_MS_NOT_AT_CAPACITY,
  63. multisession_poll_interval_ms_partial_capacity:
  64. MULTISESSION_POLL_INTERVAL_MS_PARTIAL_CAPACITY,
  65. multisession_poll_interval_ms_at_capacity:
  66. MULTISESSION_POLL_INTERVAL_MS_AT_CAPACITY,
  67. // Poll query param: reclaim unacknowledged work items older than this.
  68. // Matches the server's DEFAULT_RECLAIM_OLDER_THAN_MS (work_service.py:24).
  69. // Enables picking up stale-pending work after JWT expiry, when the prior
  70. // ack failed because the session_ingress_token was already stale.
  71. reclaim_older_than_ms: 5000,
  72. // 0 = disabled. When > 0, push a silent {type:'keep_alive'} frame to
  73. // session-ingress at this interval so upstream proxies don't GC an idle
  74. // remote-control session. 2 min is the default. _v2: bridge-only gate
  75. // (pre-v2 clients read the old key, new clients ignore it).
  76. session_keepalive_interval_v2_ms: 120_000,
  77. }