+
    jHàj ´ ã                  ó‚  € R t ^ RIHt ^ RIt^ RIt^ RIt^ RIt^ RIt^ RIt^ RI	t	^ RI
HtHt ^ RIHt ^ RIHt ^ RIHt ^ RIHt ^ RIHt ^ R	IHt ^ R
IHtHt ^ RIHtHt ^ RIH t H!t!H"t" ^ RI#H$t$H%t% ^ RI&H't'H(t(H)t)H*t*H+t+ ^ RI,H-t-H.t.H/t/H0t0 ]Pb                  ! R4      t2RR/R R llt3R R lt4R R lt5 ! R R4      t6R# )a+  Startup sequence, resume/restore and handoff methods for GatewayRunner.

Split out of ``gateway/run.py``; bound onto ``GatewayRunner`` via the MRO.
``gateway.run`` internals are imported lazily inside method bodies (import cycle),
so ``patch("gateway.run.X")`` keeps intercepting them at call time.
)ÚannotationsN)ÚnullcontextÚsuppress)Úcopy_context)ÚPath)Út)ÚPlatform)Ú#looks_like_telegram_private_chat_id)ÚBasePlatformAdapter)ÚMessageEventÚMessageType)ÚSessionSourceÚbuild_session_key)Ú"DEFAULT_GATEWAY_CRON_DRAIN_TIMEOUTÚGATEWAY_FATAL_CONFIG_EXIT_CODEÚis_global_startup_conflict)Ú_log_suppressedÚ_send_error)ÚDEFAULT_HEARTBEAT_INTERVAL_SÚ DEFAULT_LOOP_WATCHDOG_INTERVAL_SÚ!DEFAULT_LOOP_WATCHDOG_MAX_STRIKESÚDEFAULT_LOOP_WATCHDOG_TIMEOUT_SÚloop_heartbeat_forever)ÚAnyÚDictÚOptionalÚTuplezgateway.runÚhydrate_secretsTc               ó$   € V ^8„  d   QhRRRRRR/# )é   Úhomer   r   ÚboolÚreturnÚNone© )Úformats   "Ú8/home/ubuntu/.hermes/hermes-agent/gateway/run_startup.pyÚ__annotate__r'   (   s!   € ÷ ñ ˜tð ¸ð Èñ ó    c               óœ   € ^ RI Hp ^ RIHp V! \	        V 4      VR7      ;_uu_ 4        V! 4        RRR4       R#   + '       g   i     R# ; i)zâInstall the catalog plugin of every feature that left core (Home Assistant) *home* uses, in
*home*'s runtime scope (its config, secrets and allow_lazy_installs); once per process per home.
Blocking: call it off the event loop.©Ú_profile_runtime_scope©Úrecover_at_startup)r   N)Úgateway.runr+   Úhermes_cli.left_core_migrationr-   r   )r    r   r+   r-   s   &$  r&   Úrecover_left_core_inr0   (   s1   € õ 3ÝAÙ	¤ T£
¸O×	LÖ	LÙÔ÷ 
M×	L×	LÒ	Lús	   ¨:ºA	c               ó   € V ^8„  d   QhRR/# ©r   r"   r#   r$   )r%   s   "r&   r'   r'   2   s   € ÷ 
#ñ 
#¨Dñ 
#r(   c                 óÌ   € ^ RI Hp  ^ RIHpHp V ! 4        \        V! 4       4      pVP                  4       \        V! 4       4      P                  4       8w  d   \        V4       R# R# )a]  Left-core migration for the homes whose platform config the runner loads first: the launch
home and the default root (the multiplex primary; a named launcher is then served as a
secondary). Every secondary runs :func:`recover_left_core_in` before its plugins are discovered,
so a platform plugin it gets starts its adapter in the same gateway start.r,   )Úget_default_hermes_rootÚget_hermes_homeN)r/   r-   Úhermes_constantsr4   r5   r   Úresolver0   )r-   r4   r5   Úroots       r&   Ú"recover_left_core_at_gateway_startr9   2   sK   € õ
 BßIÙÔÜÑ'Ó)Ó*€DØ‡|�|ƒ~œ™oÓ/Ó0×8Ñ8Ó:Ô:Ü˜TÖ"ñ ;r(   c               ó   € V ^8„  d   QhRR/# )r   r"   zOptional[tuple]r$   )r%   s   "r&   r'   r'   @   s   € ÷ Gñ G /ñ Gr(   c                ó¾   € ^ RI Hp ^ RIHp VP	                  V P
                  4      pV! V P
                  RV4      pV'       g   R# . VOV! V P
                  RV4      N5# )a^  ``(dm_policy_env, group_policy_env, allow_all_env)`` for a platform that declares
``own_policy_env``, else None. The live entry wins; a bundled platform whose entry is absent
(plugin disabled, safe mode) or lacks the field (a user plugin overriding it) falls back to the
names its ``gateway_env.AUTHZ`` declares, so the startup refusal never weakens.)Úauthz_field©Úplatform_registryÚown_policy_envNÚallow_all_env)Úgateway.platform_envr<   Úgateway.platform_registryr>   ÚgetÚvalue)Úplatformr<   r>   ÚentryÚowns   &    r&   Ú_own_policy_envsrH   @   sT   € õ
 1Ý;Ø×!Ñ! (§.¡.Ó1€EÙ
�h—n‘nÐ&6¸Ó
>€CßÙØFˆSÐF‘+˜hŸn™n¨o¸uÓEÑFÐFr(   c                  ó(  € ] tR t^Nt$ Rt]R R l4       tRtR]R&   R R lt	R	 R
 lt
R R ltR R ltR R ltR tR R ltR R ltR]P$                  RR/R R lltR R lt]R]P$                  /R R ll4       tR R ltR R/R! R" lltR# R$ lt]R—R% R& ll4       tR'R(/R) R* lltR+ R, ltR- R. ltR/ R0 ltR1 R2 ltR'R(/R3 R4 lltR˜R5 R6 llt R7 R8 lt!R˜R9 R: llt"R; R< lt#R= R> lt$R?R@/RA RB llt%R™RC RD llt&RE RF lt'RG RH lt(RI RJ lt)RK RL lt*RM RN lt+RO RP lt,]RQ 4       t-RR t.RšRS RT llt/R›RU RV llt0RW RX lt1RY t2RZ R[ lt3R\ R] lt4R^ R_ lt5R` Ra lt6Rœt7]8;QJ d    . Rb ]7 4       F  NK  	  5M! Rb ]7 4       4      R�,           t9]8;QJ d    . Rc ]7 4       F  NK  	  5M! Rc ]7 4       4      t:Rd Re lt;]Rf Rg l4       t<]Rh Ri l4       t=]R]P|                  /Rj Rk ll4       t?Rl Rm lt@Rn Ro ltARp Rq ltBRr Rs ltCRt Ru ltDRv Rw ltERx Ry ltFRz R{ ltGR| R} ltHR~ R ltIR€ R� ltJRžtKRŸtLR‚ Rƒ ltM]R„ R… l4       tNR† R‡ ltORˆ R‰ ltP]QP¤                   ! RŠ R‹4      4       tSRŒ R� ltTRŽ R� ltU]R� R‘ l4       tVR’ R“ ltWR˜R” R• lltXR–tYR(# ) ÚGatewayStartupMixinzGStartup sequence, resume/restore and handoff methods for GatewayRunner.c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   Ú GatewayStartupMixin.__annotate__R   s   € ÷ Mñ M˜tñ Mr(   c                 ó–   € ^ RI Hp Hp V! \        P                  ! R4      4      p\
        P                  RW 8X  d	   R4       R# T4       R# )aP  Report the ENFORCED per-turn budget: ``agent.max_turns`` is bridged into
``HERMES_MAX_ITERATIONS`` before this runs, so the env slot already carries the config value;
resolve it the same way the turn loop does (``none``/``unlimited`` spellings included) instead of
``int()`` on the raw string with an invented ``500`` default (#116888).)ÚTURN_LIMIT_UNLIMITEDÚresolve_turn_limitÚHERMES_MAX_ITERATIONSziAgent budget: max_iterations=%s (agent.max_turns from config.yaml, else the HERMES_MAX_ITERATIONS bridge)Ú	unlimitedN)Úhermes_cli.configrN   rO   ÚosÚgetenvÚloggerÚinfo)rN   rO   Úlimits      r&   Ú_log_agent_budgetÚ%GatewayStartupMixin._log_agent_budgetQ   s=   € ÷ 	OÙ"¤2§9¢9Ð-DÓ#EÓFˆÜ�‰ÐØ#(Ô#@�Kö	MØFKö	Mr(   Fr!   Ú_startup_parked_platformsc               ó   € V ^8„  d   QhRR/# )r   r"   Ústrr$   )r%   s   "r&   r'   rL   `   s   € ÷ Kñ K ñ Kr(   c                	ó.   € V P                   '       d   R # R# )ÚdegradedÚrunning)rZ   ©Úselfs   &r&   Ú_serving_stateÚ"GatewayStartupMixin._serving_state`   s   € Ø!×;×;Ð;ˆzÐJÀÐJr(   c               ó(   € V ^8„  d   QhRRRRRRRR/# )	r   Úadapterr
   Úeventr   Úsession_keyr\   r"   r#   r$   )r%   s   "r&   r'   rL   c   s,   € ÷ ?ñ ?Ø*ð?Ø3?ð?ØNQð?à	ñ?r(   c              ƒ  ó.  "  € ^ RI Hp  VP                  V4      G Rj  x€L
  \        VR/ 4      p\	        V\
        4      '       d   VP                  V4      MRpVe   \        P                  ! V4      G Rj  x€L
  V P                  V4      pV'       d   VP                  P                  MRVJ d   V P                  V4       R# R#  L¦ LP  T P                  T4      pT'       d   TP                  P                  MRTJ d   T P                  T4       i i ; i5i)zŒDispatch one synthetic startup resume and wait for its agent turn (inbound stays queued
until it finishes, else a user message can race it).)Ú_AGENT_PENDING_SENTINELNÚ_session_tasks)r.   ri   Úhandle_messageÚgetattrÚ
isinstanceÚdictrC   ÚasyncioÚshieldÚ_peek_session_stateÚturnÚagentÚ_release_running_agent_state)ra   re   rf   rg   ri   Úsession_tasksÚtaskÚ
_pre_states   &&&&    r&   Ú_run_startup_resume_eventÚ-GatewayStartupMixin._run_startup_resume_eventc   sî   é € õ
 	8ð
	?Ø×(Ñ(¨Ó/×/Ð/Ü# GÐ-=¸rÓBˆMÜ5?ÀÌt×5TÒ5T�=×$Ñ$ [Ô1ÐZ^ˆDØÒÜ—n’n TÓ*×*Ð*ð ×1Ñ1°+Ó>ˆJß)3�
—‘×%Ò%¸ÐBYÓYØ×1Ñ1°+Ö>ñ Zñ 0ñ +øð ×1Ñ1°+Ó>ˆJß)3�
—‘×%Ò%¸ÐBYÓYØ×1Ñ1°+Õ>ð ZüsA   ‚DŠC	 žCŸAC	 Á6CÁ7C	 Á;A
DÃC	 ÃC	 Ã	A	DÄDc               ó    € V ^8„  d   QhRRRR/# )r   rf   r   r"   r#   r$   )r%   s   "r&   r'   rL   u   s   € ÷ ñ °,ð À4ñ r(   c                	ó�  € \        V R R4      pVf	   . ;q n        VP                  V4       \        \        4      ;_uu_ 4        VP
                  p\        P                  RV'       d)   VP                  '       d   VP                  P                  MRV'       d   VP                  MR4       RRR4       R#   + '       g   i     R# ; i)Ú_startup_restore_queueNzJQueued inbound message during gateway startup restore: platform=%s chat=%sÚunknown)rl   r|   Úappendr   Ú	ExceptionÚsourcerU   rV   rE   rD   Úchat_id)ra   rf   Úqueuer€   s   &&  r&   Ú_queue_startup_restore_eventÚ0GatewayStartupMixin._queue_startup_restore_eventu   sƒ   € Ü˜Ð6¸Ó=ˆØŠ=Ø24Ð4ˆEÔ/Ø�‰�UÔÜ”i× Õ Ø—\‘\ˆFÜ�K‰KØ\ß)/°F·O·O°O�—‘×%Ò%Èß"(�—’¨iô÷ !× × Ò ús   Á6B4Á9B4ÂB4Â4C	c               ó   € V ^8„  d   QhRR/# ©r   r"   Úintr$   )r%   s   "r&   r'   rL   ‚   s   € ÷ ñ °Cñ r(   c           
   ƒ  ó&  "  € ^ p\        V RR4      ;'       g    . pV'       d®   VP                  ^ 4      p \        VRR4      pV P                  V4      pVf/   \        P	                  R\        \        VRR4      RR4      4       Kj  \        \        4      ;_uu_ 4        RVn        RRR4       VP                  V4      G Rj  x€L
  T^,          pKµ  V#   + '       g   i     L6; i L$  \         d    \        P                  RRR	7        Kñ  i ; i5i)
z=Replay inbound messages queued while startup auto-resume ran.r|   Nr€   zCDropping startup-restore queued message: adapter unavailable for %srE   rD   Tz6Startup-restore queued replay failed; continuing drain©Úexc_info)
rl   ÚpopÚ_intake_adapter_forrU   Údebugr   r   Ú_hermes_startup_restore_replayrk   Úwarning)ra   Údrainedr‚   rf   r€   re   s   &     r&   Ú_drain_startup_restore_queueÚ0GatewayStartupMixin._drain_startup_restore_queue‚   sï   é € àˆÜ˜Ð6¸Ó=×CÐCÀˆßØ—I‘I˜a“LˆEðÜ  ¨°$Ó7�Ø×2Ñ2°6Ó:�Ø’?Ü—L‘LØ]Ü¤¨°
¸DÓ AÀ7ÈDÓQôñ äœi×(Õ(Ø;?�EÔ8÷ )à×,Ñ,¨UÓ3×3Ð3ð �q�LŠGØˆ÷ )×(úá3øÜô ô —‘ÐWÐbf�ÔgÚðüs^   ‚!D¤D¶AC( ÂDÂC( ÂCÂ%C( ÃC&ÃC( ÃDÃC#	Ã	C( Ã("DÄ
DÄDÄDc               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   ž   s   € ÷ [ñ [ tñ [r(   c                óŽ   € ^ RI Hp V! 4       ^ 8:  d
   RV n        R# \        P                  ! V P                  4       4      V n        R# )z�Kick off the boot turn-machinery warm-up so it overlaps the network-bound platform
connects; ``_finish_startup_restore`` awaits it (bounded).©Ú_startup_warmup_timeout_secsN)r.   r–   Ú_startup_warmup_taskro   Úensure_futureÚ_warm_turn_prerequisites)ra   r–   s   & r&   Ú_start_startup_warmupÚ)GatewayStartupMixin._start_startup_warmupž   s9   € õ 	=Ù'Ó)¨QÔ.Ø(,ˆDÔ%ÙÜ$+×$9Ò$9¸$×:WÑ:WÓ:YÓ$ZˆÖ!r(   c           	   ƒ  óL  "  € \         P                  ! 4       p\        V P                  RR4      '       dk   ^ RIHp ^ RIHp  V! V! 4       4      ;_uu_4       GRj  x€L
  VP                  R\        4       P                  V4      G Rj  x€L
 uuRRR4      GRj  x€L
  # VP                  R\        4       P                  V4      G Rj  x€L
 #  Lp LE L6  + GRj  x€L 
 '       g   i     LL; i  \         d'    \        P                  R\        TRT4      RR	7        Li ; i LZ5i)
a£  Run a boot-time probe on the default executor under the LAUNCH profile's scope when
multiplexing (the ``_discover_gateway_mcp_tools`` shape). Boot probes (``check_fn``s) read profile-scoped secrets; an unscoped read under multiplex fails
closed, so routing overrides resolve as absent and default routing applies. ``copy_context``
carries the contextvars across the executor hop; single-profile keeps environ semantics.Úmultiplex_profilesF)Ú_async_profile_runtime_scope©r5   NzGmultiplex launch-scope entry failed for boot probe %s; running unscopedÚ__name__Tr‰   )ro   Úget_running_looprl   Úconfigr.   rž   r6   r5   Úrun_in_executorr   Úrunr   rU   r�   )ra   ÚfnÚlooprž   r5   s   &&   r&   Ú_run_boot_probe_in_launch_scopeÚ3GatewayStartupMixin._run_boot_probe_in_launch_scope§   sæ   é € ô
 ×'Ò'Ó)ˆÜ�4—;‘;Ð 4°e×<Ò<Ý@Ý8ðIÙ7¹Ó8I×J×JÕJØ!%×!5Ñ!5°d¼L»N×<NÑ<NÐPRÓ!S×S÷ K×JÒJð ×)Ñ)¨$´³×0BÑ0BÀBÓG×GÐGñ KÙS÷ K×J×JÒJûäô Iô —‘ÐfÜ$ R¨°RÓ8À4ð ö IðIúñ
 Hùs¡   ‚?D$ÁC. ÁCÁC. Á)CÂCÂ	CÂC. ÂCÂC. Â)D$ÃD"ÃD$ÃC. ÃCÃC. ÃC+	ÃCÃ
C+	Ã$C+	Ã&C. Ã*D$Ã+C. Ã..DÄD$ÄDÄD$c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   º   s   € ÷ ñ °ñ r(   c              ƒ  ó^  "  € ^ RI Hp \        \        P                  RRR7      ;_uu_ 4        \
        P                  ! 4       pV P                  V4      G Rj  x€L
 p\        P                  R\
        P                  ! 4       V,
          V4       RRR4       R#  L?  + '       g   i     R# ; i5i)z—Initialize turn machinery on an executor thread before the gate opens. Never raises: a
failed warm-up degrades to lazy init and must not block startup.)Ú_warm_turn_machinery_synczHTurn-machinery warm-up failed; first inbound turn will initialize lazilyTr‰   Nz?Turn machinery warmed in %.1fs (%d tool schema(s) materialized))
r.   r«   r   ÚloggingÚWARNINGÚtimeÚ	monotonicr§   rU   rV   )ra   r«   Út0Ú
tool_counts   &   r&   r™   Ú,GatewayStartupMixin._warm_turn_prerequisitesº   s…   é € õ 	:ÜÜ�O‰OÐgØ÷
ö 
ô —’Ó!ˆBØ#×CÑCÐD]Ó^×^ˆJÜ�K‰KØQÜ—’Ó  2Õ% zô÷
ñ 
ñ
 _÷
÷ 
ð 
üs.   ‚+B-­*BÁBÁ5BÂ
B-ÂBÂB*	Â$	B-c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   É   s   € ÷ 
ñ 
¨Tñ 
r(   c              ƒ  óê   "  € ^ RI Hp \        V RR4      pVe   VP                  4       '       d   R# V! 4       pV^ 8:  d   R# V P	                  V0VRR\
        P                  R7      G Rj  x€L
  R#  L5i)z¶Bounded wait for the boot warm-up. On timeout the gate opens anyway (availability outranks
prompt completeness for a WEDGED init); the warm-up continues and a late failure is logged.r•   r—   Nu´   Turn-machinery warm-up still running after %.0fs; opening inbound gate anyway â€” the first turn may see lazily initialized machinery (#99373). Warm-up continues in the background.z5boot turn-machinery warm-up failed after gate release©Úlevel)r.   r–   rl   ÚdoneÚ_wait_bounded_or_releaser¬   ÚDEBUG)ra   r–   rv   Útimeouts   &   r&   Ú_await_startup_warmupÚ)GatewayStartupMixin._await_startup_warmupÉ   sp   é € õ 	=Ü�tÐ3°TÓ:ˆØŠ<˜4Ÿ9™9Ÿ;š;ÙÙ.Ó0ˆØ�aŒ<ÙØ×+Ñ+ØˆF�GðmàCÌ7Ï=É=ð	 ,ó 
÷ 	
ô 	
ùs   ‚-A3°:A3Á*A1Á+A3r¶   Útrackc               ó4   € V ^8„  d   QhRRRRRRRRRR	R
RRR/# )r   ÚtasksÚsetrº   ÚfloatÚwarn_fmtr\   Úlate_msgr¶   r‡   r½   r!   r"   r$   )r%   s   "r&   r'   rL   Ú   sF   € ÷ ñ ØðØ#(ðØ47ðØCFðàðà-1ðð 
ñr(   c             ƒ  ó  "  € V^ 8:  d*   \         P                  ! VRR/ G Rj  x€L
  \        V4      # \         P                  ! WR7      G Rj  x€L
 w  rxV'       d�   VP	                  R4      ^8”  d   V\        V4      3MV3p	\         P                  ! \        P                  V.V	O5!  G Rj  x€L
  V P                  WER7      p
V F/  pVP                  V
4       V'       g   K  V P                  V4       K1  	  V#  LÖ L® LQ5i)aC  ``asyncio.wait`` (which, unlike wait_for/gather+timeout, does NOT cancel on timeout) with
the gate-release warning + late-failure callback every boot gate uses. Returns ``done``.
``warn_fmt`` takes ``%.0fs`` (timeout) and optionally ``%d`` (pending count). A non-positive
``timeout`` opts out of the bound ("wait forever").Úreturn_exceptionsTN©rº   Ú%rµ   )ro   ÚgatherrÀ   ÚwaitÚcountÚlenÚ	to_threadrU   r�   Ú_late_failure_callbackÚadd_done_callbackÚ_retain_background_task)ra   r¿   rº   rÂ   rÃ   r¶   r½   r·   ÚpendingÚargsÚlaterv   s   &&&&&$$     r&   r¸   Ú,GatewayStartupMixin._wait_bounded_or_releaseÚ   sÚ   é € ð �aŒ<Ü—.’. %Ð@¸4Ñ@×@Ð@Ü�u“:ÐÜ%Ÿlšl¨5ÔB×B‰ˆßØ.6¯n©n¸SÓ.AÀAÔ.E�GœS ›\Ñ*ÈGÈ:ˆDÜ×#Ò#¤F§N¡N°HÐD¸tÓD×DÐDØ×.Ñ.¨xÐ.ÓEˆDÛ�Ø×&Ñ& tÔ,ß‘5Ø×0Ñ0°Ö6ñ  ð ˆñ AáBñ Eùs:   ‚!D £C:¤)D ÁC<ÁAD Â,C>Â-1D Ã#D Ã<D Ã>D c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   ð   s   € ÷ `ñ `¨tñ `r(   c              ƒ  ó(  "  € ^ RI Hp ^ p \        \        V R. 4      ;'       g    . 4      pV'       dm   V P	                  \        V4      V! 4       RR\        P                  R7      G Rj  x€L
 pV P                  R\        P                  R7      pV F  pV! V4       K  	  . V n	        V P                  4       G Rj  x€L
  V P                  4       G Rj  x€L
 pRV n        V'       d   \        P                  R	V4       R# R#  L– LG L1  RT n        i ; i5i)
uW  Wait (BOUNDED by ``_startup_restore_drain_timeout_secs``) for startup auto-resume, then
release + drain inbound. On timeout the gate opens and resume turns finish in the background
(NOT cancelled) â€” safe because ``_schedule_resume_pending_sessions`` claims each
``_running_agents`` slot SYNCHRONOUSLY first, so drained inbound queues behind.©Ú#_startup_restore_drain_timeout_secsÚ_startup_restore_taskszÕStartup-restore gate released after %.0fs with %d boot auto-resume turn(s) still running; draining inbound queue now (resume slots already claimed, so no duplicate agents). Slow turn(s) continue in the background.z=background startup auto-resume task failed after gate releaserµ   Nzstartup auto-resume task failedFz;Drained %d inbound message(s) queued during startup restore)r.   r×   Úlistrl   r¸   rÀ   r¬   r¹   rÍ   rØ   r»   r‘   Ú_startup_restore_in_progressrU   rV   )ra   r×   r�   r¿   r·   Úreportrv   s   &      r&   Ú_finish_startup_restoreÚ+GatewayStartupMixin._finish_startup_restoreð   s  é € õ
 	DØˆð	6Üœ Ð'?ÀÓD×JÐJÈÓKˆEßà!×:Ñ:Ü˜“JÑ CÓ EðRð TÔ[b×[hÑ[hð ;ó ÷ �ð ×4Ñ4Ð5VÔ^e×^kÑ^kÐ4Ól�Û �DÙ˜4–Lñ !à*,ˆDÔ'à×,Ñ,Ó.×.Ð.Ø ×=Ñ=Ó?×?ˆGð
 16ˆDÔ-ßÜ�K‰KÐUÐW^Ö_ñ ñ'ñ /Ù?øð
 16ˆDÕ-üs^   ‚	DŒ'D ´5D Á)D Á*AD Â:DÂ;D ÃDÃD ÃDÃ&DÄ D ÄD ÄD Ä	DÄDc               ó    € V ^8„  d   QhRRRR/# )r   Úmessager\   r¶   r‡   r$   )r%   s   "r&   r'   rL     s   € ÷ 
ñ 
¨ð 
°sñ 
r(   c               ó   a a€ R VV 3R llpV# )zÒDone-callback for boot-path tasks that outlive the startup-restore gate: surface a late
failure otherwise swallowed once the task leaves ``_background_tasks``. Cancellation is
expected (shutdown), not an error.c               ó    € V ^8„  d   QhRRRR/# )r   rv   zasyncio.Taskr"   r#   r$   )r%   s   "r&   r'   Ú@GatewayStartupMixin._late_failure_callback.<locals>.__annotate__  s   € ÷ 	Yñ 	Y˜,ð 	Y¨4ñ 	Yr(   c                ó¾   <€ V P                  4       '       d   R # V P                  4       pVe0   \        P                  SS\	        V4      WP
                  3R7       R # R # )Nr‰   )Ú	cancelledÚ	exceptionrU   ÚlogÚtypeÚ__traceback__)rv   Úexcr¶   rß   s   & €€r&   Ú_reportÚ;GatewayStartupMixin._late_failure_callback.<locals>._report  sJ   ø€ Ø�~‰~×ÒÙØ—.‘.Ó"ˆCØŠÜ—
‘
˜5 '´T¸#³YÀ×EVÑEVÐ4W�
ÖXñ r(   r$   )rß   r¶   rê   s   fd r&   rÍ   Ú*GatewayStartupMixin._late_failure_callback  s   ù€ ÷
	Yñ 	Yð ˆr(   c               ó    € V ^8„  d   QhRRRR/# )r   Ú$planned_restart_notification_pendingr!   r"   r#   r$   )r%   s   "r&   r'   rL     s   € ÷ 
ñ 
ÐW[ð 
Ð`dñ 
r(   c             ƒ  ó  a aa"  € ^ RI Hp S P                  4       G Rj  x€L
 oR VVV 3R llp\        P                  ! V! 4       4      pV! 4       pV^ 8:  d   VG Rj  x€L
  R# S P                  V0VRRRR7      G Rj  x€L
  R#  Le L) L
5i)	u_  Run boot-path sends without letting them pin the inbound restore gate (one Telegram
flood-control sleep must not freeze inbound on every platform): same bounded wait as the
resume gate, sends finish in the background on timeout. The ledger claim + ``resume_pending``
clear run INLINE before the send task exists â€” deferring it let a hung notification expire the
gate with zero rows claimed, so answered turns were replayed AND redelivered.

``_send_restart_notification`` and ``_redeliver_pending_obligations`` used to be awaited inline
*before* ``_finish_startup_restore`` released the gate. See #91969.
rÖ   Nc               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   ÚCGatewayStartupMixin._await_startup_boot_sends.<locals>.__annotate__+  s   € ÷ 	?ñ 	? 4ñ 	?r(   c               “  ó¾   <"  € SP                  4       G R j  x€L
  S'       d   SP                  4       G R j  x€L
  SP                  S 4      G R j  x€L
  R #  L? L! L
5i©N)Ú_send_restart_notificationÚ,_replay_pending_planned_restart_notificationÚ_redeliver_claimed_obligations)Úclaimedrî   ra   s   €€€r&   Ú_boot_sendsÚBGatewayStartupMixin._await_startup_boot_sends.<locals>._boot_sends+  sL   øé € Ø×1Ñ1Ó3×3Ð3ß3Ø×GÑGÓI×IÐIØ×5Ñ5°gÓ>×>Ò>ñ 4áIÙ>ùs6   ƒA—A˜A¤A·A¸AÁAÁAÁAÁAz­Boot-path sends still running after %.0fs; releasing inbound gate so other platforms are not frozen. Restart notification / obligation redelivery continue in the background.zBbackground boot-path send failed after gate release: see tracebackT)r½   )r.   r×   Ú_claim_pending_obligationsro   Úcreate_taskr¸   )ra   rî   r×   rø   Ú	boot_taskrº   r÷   s   fd    @r&   Ú_await_startup_boot_sendsÚ-GatewayStartupMixin._await_startup_boot_sends  s“   úé € õ 	DØ×7Ñ7Ó9×9ˆ÷	?ò 	?ô ×'Ò'©«Ó6ˆ	Ù5Ó7ˆØ�aŒ<Ø�OˆOÙØ×+Ñ+ØˆK˜ð_àPÐX\ð	 ,ó 
÷ 	
ò 	
ñ :ñ ñ	
ùs3   …BŸB =BÁBÁ BÁ>B	Á?BÂBÂ	BÚrequire_successc               ó$   € V ^8„  d   QhRRRRRR/# )r   r÷   rÙ   rÿ   r!   r"   r$   )r%   s   "r&   r'   rL   =  s$   € ÷ ñ ØðØ15ðà	ñr(   c             ƒ  óf  "  € . pV Fn  pVP                  R4      ;'       g    RpV'       g   VP                  V4       K9   V P                  P                  V4      G Rj  x€L
  VP                  V4       Kp  	  V#  L  \         d'    \
        P                  RTRR7       T'       d    K¤   LIi ; i5i)zöClear resume flags and return rows safe to redeliver. Startup recovery is best-effort;
runtime reconnect recovery (``require_success``) is stricter: if the session-store write
fails the response must not be sent, or the turn could be resumed too.rg   Ú Nz"clear_resume_pending failed for %sTr‰   )rC   r~   Úasync_session_storeÚclear_resume_pendingr   rU   r�   )ra   r÷   rÿ   ÚsendableÚrowrg   s   &&$   r&   Ú-_clear_resume_pending_for_claimed_obligationsÚAGatewayStartupMixin._clear_resume_pending_for_claimed_obligations=  s¥   é € ð ˆÛˆCØŸ'™' -Ó0×6Ð6°BˆKßØ—‘ Ô$ÙðØ×.Ñ.×CÑCÀKÓP×PÐPð
 �O‰O˜CÖ ñ ð ˆñ QøÜô Ü—‘ÐAÀ;ÐY]�Ô^ß"Úñ #ðüsE   ‚B1¢
B1­B1ÁA=ÁA;Á A=Á$B1Á;A=Á=*B.Â(B1Â-B.Â.B1c               ó   € V ^8„  d   QhRR/# )r   r"   rÙ   r$   )r%   s   "r&   r'   rL   R  s   € ÷ )ñ )°$ñ )r(   c           
   ƒ  óÚ  a
a"  €  ^ RI HpHp \        P                  ! V4      G Rj  x€L
 '       g   . # \        V RR4      ;'       g    / pR oV P                   Uu0 uF  pS! V4      R3kK  	  ppV'       g&   VP                  V3R lV P                   4       4       VP                  4        F"  w  o
pVP                  V
V3R lV 4       4       K$  	  \        P                  ! TRV UUu0 uF  w  rxVkK	  	  uppVR7      G Rj  x€L
 p	T	'       g   . # T P                  T	4      G Rj  x€L
  T	#  ELu upi u uppi  L7  \         d    \        P                  R	R
R7       . u # i ; i L@5i)uª  Claim recoverable delivery-ledger rows and clear their ``resume_pending`` flags (pure DB
work, no sends). Must run INLINE BEFORE ``_schedule_resume_pending_sessions`` and the
abandonable boot-send task: these sessions already produced their answer, so the resume path
must not re-run (re-pay for) the turn however long the sends take. Mid-send / rejected rows
carry a visible recovered-reply marker (gateway/delivery_ledger.py). Returns the rows.

A session with a recoverable obligation already produced its answer â€” the turn completed and only
delivery is owed â€” so clearing ``resume_pending`` here prevents the resume path from re-running (and
re-paying for) a turn whose output we hold, regardless of how long the sends ahead of redelivery
take (#91969). Flood-refused rows adopted inside their wait come back flagged ``adopted``: their
flags are cleared here too, and ``_redeliver_claimed_obligations`` leaves them to the timer.
)Úledger_enabledÚsweep_recoverableNÚ_profile_adaptersc                ó.   € \        V R \        V 4      4      # ©rD   )rl   r\   )Úps   &r&   Ú<lambda>Ú@GatewayStartupMixin._claim_pending_obligations.<locals>.<lambda>f  s   € œg a¨´#°a³&Ô9r(   Údefaultc              3  ó8   <"  € T F  pS! V4      R 3x € K  	  R # 5iró   r$   )Ú.0r  Ú_pvals   & €r&   Ú	<genexpr>ÚAGatewayStartupMixin._claim_pending_obligations.<locals>.<genexpr>j  s   øé € Ð+TÁmÀ©U°1«X°tÕ,<Ãmùó   ƒc              3  ó8   <"  € T F  pS! V4      S3x € K  	  R # 5iró   r$   )r  r  Ú_profiler  s   & €€r&   r  r  l  s   øé € Ð+TÉ)ÀQ©U°1«X°xÕ,@Ë)ùr  )Údeliverable_platformsÚdeliverable_targetszdelivery ledger sweep failedTr‰   )Úgateway.delivery_ledgerr  r  ro   rÌ   rl   ÚadaptersÚupdateÚitemsr   rU   r�   r  )ra   r  r  r  r  Ú_deliverable_targetsÚ	_adaptersrE   Ú_r÷   r  r  s   &         @@r&   rú   Ú.GatewayStartupMixin._claim_pending_obligationsR  sK  ùé € ð	ßQÜ ×*Ò*¨>Ó:×:Ö:Ø�	ô !(¨Ð.AÀ4Ó H× NÐ NÈBÐÙ9ˆEØCGÇ=Â=Ó#QÁ=¸a¡U¨1£X¨yÓ$9Á=Ð Ð#Qç$Ø$×+Ñ+Ô+TÀdÇmÂmÓ+TÔTØ'8×'>Ñ'>Ö'@Ñ#�˜)Ø$×+Ñ+Õ+TÉ)Ó+TÖTñ (Aä#×-Ò-Ø! 4ÙCWÔ&XÑCW±K°H£xÑCWÒ&XØ$8ô÷ ˆG÷ ØˆIð ×@Ñ@ÀÓI×IÐIØˆò5 ;ùò $Rùó 'Yñøô
 ô 	Ü�L‰LÐ7À$ˆLÔGØŠIð	úñ 	JùsŠ   „E+†!D? §D/¨	D? ²D? ³E+´D? ÁD? ÁD2Á/A<D? Ã+D7Ã8D? ÄD=ÄD? Ä
E+ÄE+Ä(E)Ä)E+Ä/D? Ä2D? Ä?$E&Å#E+Å%E&Å&E+c               ó$   € V ^8„  d   QhRRRRRR/# )r   Úlog_fmtr\   Úerrorr"   r#   r$   )r%   s   "r&   r'   rL   ~  s'   € ÷ 
@ñ 
@À3ð 
@Èsð 
@Ðnrñ 
@r(   c              ƒ  ó°   "  € ^ RI Hp  \        P                  ! W0V4      G Rj  x€L
  R#  L  \         d    \
        P                  YRR7        R# i ; i5i)aŠ  Release an unsent runtime delivery-ledger claim; log-only on failure. ``error`` is what the row
goes back to ``failed`` with: the claim's own pre-claim error when the caller knows it, so a
flood-refused row keeps its ``flood_control:<seconds>`` and stays on the flood timer's list (the
release re-stamps ``updated_at``, so it waits the platform's figure once more); else
``send_path_degraded``.)Úrelease_runtime_claimNTr‰   )r  r*  ro   rÌ   r   rU   r�   )Úobligation_idr'  r(  r*  s   &&& r&   Ú_release_runtime_claim_quietÚ0GatewayStartupMixin._release_runtime_claim_quiet}  sH   é € õ 	Bð	@Ü×#Ò#Ð$9È%ÓP×PÔPøÜô 	@Ü�L‰L˜¸$ˆL×?ð	@üs1   ‚AŠ- ¤+¥- ©A«- ­"AÁAÁAÁAÚprofileNc               ó    € V ^8„  d   QhRRRR/# )r   r.  úOptional[str]r"   r#   r$   )r%   s   "r&   r'   rL   Š  s   € ÷ -2ñ -2¸}ð -2ÐX\ñ -2r(   c          	     óB  a aaaaa	a
aa€ ^ RI HoHo	 \        V\        4      '       d   TM\	        \        V4      4      o
S
P                  S;'       g    R3o\        S RR4      oSf   / ;oS n        / S n	        S P                  oSS9   d   SS,          P                  4        R# \        P                  ! 4       ;oSS&   VVVV	VV V
VV3	R lp\        P                  ! V! 4       RP                  ! S!  R7      pVSS&   \        S RR4      pVe   S P                  WT4       R# R# )	zOWake one deadline-driven ledger worker per bot identity, never sleep in a send.)Úflood_retry_delayÚpending_retriesr  Ú_flood_redelivery_tasksNc               “  ó|  <	"  €  \        S	R R4      '       Ed   SP                  4        \        P                  ! S4      G Rj  x€L
 p V  Uu. uF%  pVR,          VR,          3S8X  g   K  VR,          NK'  	  ppV'       g@   SP	                  4       '       d   K“   SP                  SR4       SP                  SR4       R# S! \        V4      \        P                  ! 4       ,
          4      p \        P                  ! SP                  4       VR7      G Rj  x€L
  EK   SP                  SR4       SP                  SR4       R#  ELu upi  L6  \         d     Mi ; i\        S	R R4      '       g   EKo  S	P                  S
SR7      G Rj  x€L 
  EKŽ    SP                  SR4       SP                  SR4       i ; i5i)Ú_runningFNrE   r.  Ú
not_beforerÆ   ©r.  )rl   Úclearro   rÌ   Úis_setr‹   Úminr®   Úwait_forrÉ   ÚTimeoutErrorÚ*_redeliver_failed_obligations_for_platform)ÚwaitingÚrÚ	deadlinesÚdelayr2  ÚkeyrÐ   r3  r.  ra   ÚtargetÚwakeÚwakess       €€€€€€€€€r&   Ú_redeliver_after_waitÚMGatewayStartupMixin._schedule_flood_redelivery.<locals>._redeliver_after_wait›  sn  øé € ð%Ü˜d J°×6Ó6Ø—J‘J”LÜ$+×$5Ò$5°oÓ$F×F�GÙ:Aó !J¹'°QØ%& z¥]°A°iµLÐ$AÀSÑ$Hô "1  <§ ¹'�Ið !Jç$ØŸ;™;Ÿ=š=Ù$Øð —‘˜C Ô&Ø—	‘	˜#˜tÖ$ñ .¬c°)«n¼t¿yºy»{Õ.JÓK�EðÜ%×.Ò.¨t¯y©y«{ÀEÔJ×JÐJÚ ð 7ð$ —‘˜C Ô&Ø—	‘	˜#˜tÖ$ò# Gùò!Jñ Køä'ô Ùðúä˜t Z°×7Õ7Ø"×MÑMÈfÐ^eÐMÓf×fÔføà—‘˜C Ô&Ø—	‘	˜#˜tÕ$üs    ƒF<…=F ÁEÁF ÁEÁ)EÁ6F ÂF Â&F<Â?+F Ã+)E ÄEÄE ÄF Ä&F<ÅF ÅF ÅE ÅEÅF ÅEÅF Å4F Æ
FÆF Æ&F9Æ9F<zflood-redelivery:{}:{})ÚnameÚ_background_tasks)r  r2  r3  rm   r   r\   rD   rl   r4  Ú_flood_redelivery_wakesrÀ   ro   ÚEventrû   r%   Ú_track_task_in)ra   rE   r.  rG  rv   Ú
backgroundr2  rC  rÐ   r3  rD  rE  rF  s   f&d   @@@@@@@r&   Ú_schedule_flood_redeliveryÚ.GatewayStartupMixin._schedule_flood_redeliveryŠ  sû   ÿø€ çNÜ'¨´(×;Ò;‘ÄÌ#ÈhË-ÓAXˆØ�|‰|˜W×1Ð1¨	Ð2ˆÜ˜$Ð 9¸4Ó@ˆØŠ?Ø57Ð7ˆG�dÔ2Ø+-ˆDÔ(Ø×,Ñ,ˆØ�'Œ>ð �#�J�N‰NÔÙÜ#ŸMšM›OÐ+ˆˆu�S‰z÷	%õ 	%ô. ×"Ò"Ñ#8Ó#:ÐAY×A`ÒA`ÐbeÑAfÔgˆØˆ�‰ä˜TÐ#6¸Ó=ˆ
ØÒ!Ø×Ñ 
Ö1ñ "r(   c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   ¹  s   € ÷ Uñ U¸$ñ Ur(   c              ƒ  óª   "  € ^ RI Hp \        P                  ! V4      G Rj  x€L
  F$  pV P	                  VR,          VR,          R7       K&  	  R#  L.5i)z[Recover adopted, newly refused/rejected and unsent released rows without blocking the loop.)r3  NrE   r.  r8  )r  r3  ro   rÌ   rO  )ra   r3  r  s   &  r&   Ú"_arm_flood_timers_for_waiting_rowsÚ6GatewayStartupMixin._arm_flood_timers_for_waiting_rows¹  s>   é € å;Ü ×*Ò*¨?Ó;×;Ò;ˆCØ×+Ñ+¨C°
­OÀSÈÅ^Ð+ÖTõ <ùs   ‚ A¢A£/Ac               ó    € V ^8„  d   QhRRRR/# )r   r÷   rÙ   r"   r‡   r$   )r%   s   "r&   r'   rL   ¿  s   € ÷ -ñ -¸Dð -ÀSñ -r(   c              ƒ  ó@  "  €  ^ RI HpHpHp ^ pT EF¨  pTP                  R4      '       d   K  T P                  T4      G Rj  x€L
 pTf   K<  TR,          pTP                  R4      '       d   TP                  R	T4      T,           pTP                  R
4      '       d   R
TR
,          /MRp	 TP                  TR,          Y‰R7      G Rj  x€L
 p
\        \        P                  RRR7      ;_uu_ 4        T
ex   \        T
RR4      '       de   \        P                   ! Y6R,          4      G Rj  x€L
  T^,          p\
        P#                  RTR,          TR,          TR,          TR,          4       MD\        P                   ! YFR,          \%        \        T
RR4      ;'       g    R4      4      G Rj  x€L
  RRR4       EK«  	  \        \        P                  RRR7      ;_uu_ 4        T P'                  4       G Rj  x€L
  RRR4       T#   \         d    \
        P                  RRR7        ^ # i ; i ELì ELi  \         d,   p\
        P                  RTR,          T4       Rp
 Rp?EL˜Rp?ii ; i ELD LÃ  + '       g   i     EKs  ; i L�  + '       g   i     T# ; i5i)zõRedeliver final responses for claimed rows (network half of the split): runs inside the
bounded boot-send task, so a flood-limited send can be abandoned by the restore gate without
reopening the turn-replay window. Returns the redelivered count.)ÚRECOVERED_MARKERÚmark_deliveredÚmark_failedzdelivery ledger import failedTr‰   ÚadoptedNÚcontentÚneeds_markerÚmarkerÚ	thread_idr�   )r�   r[  Úmetadataz)obligation %s: redelivery send raised: %sr+  zdelivery ledger update failedÚsuccessFzIRedelivered recovered final response to %s:%s (obligation %s, attempt %d)rE   Úattemptsr(  r  zsend failedz%arming flood redelivery timers failed)r  rW  rX  rY  r   rU   r�   rC   Ú_obligation_adapterÚsendr�   r   r¬   r¹   rl   ro   rÌ   rV   r\   rS  )ra   r÷   rW  rX  rY  Úredeliveredr  re   r[  r_  ÚresultÚsend_errs   &&          r&   rö   Ú2GatewayStartupMixin._redeliver_claimed_obligations¿  s8  é € ð	ß]Ñ]ð ˆÜˆCØ�w‰w�y×!Ò!ñ Ø ×4Ñ4°SÓ9×9ˆGØŠÙØ˜)•nˆGØ�w‰w�~×&Ò&ØŸ'™' (Ð,<Ó=ÀÕG�Ø:=¿'¹'À+×:NÒ:N˜ S¨Õ%5Ñ6ÐTXˆHðØ&Ÿ|™|°C¸	µNÈG˜|Óg×g�ô !¤§¡Ð0OÐZ^×_Ö_ØÒ%¬'°&¸)ÀU×*KÒ*KÜ!×+Ò+¨NÀÕ<PÓQ×QÐQØ 1Õ$�KÜ—K‘KØcØ˜J�¨¨Y­¸¸_Õ9MÈsÐS]Íõô
 "×+Ò+Ø#¨Õ%9¼3¼wÀvÈwÐXZÓ?[×?lÐ?lÐ_lÓ;mó÷ ð ÷ `Ò_ñ# ô> œWŸ]™]Ð,SÐ^b×cÖcØ×9Ñ9Ó;×;Ð;÷ dàÐøôK ô 	Ü�L‰LÐ8À4ˆLÔHÚð	úò :ò høÜô Ü—‘ÐJÈCÐP_ÕL`ÐbjÔkØ–ûðúò
 Rñ÷ `×_Ñ_úñ <÷ dÖcàÐüsâ   ‚J„
H Ž5JÁH/Á)JÁ./JÂJÂ,H5Ã	H2Ã
H5Ã$JÃ28I3Ä*I.
Ä+BI3Æ-I1
Æ.I3Æ21JÇ#J
Ç7JÇ8J
Ç<
JÈ"H,È(JÈ+H,È,JÈ2H5È5I+É  I&É JÉ&I+É+JÉ.I3É1I3É3JÉ>
JÊJ
Ê
J	Ê	Jc               ó   € V ^8„  d   QhRR/# )r   r  rn   r$   )r%   s   "r&   r'   rL   î  s   € ÷ ñ ¨Tñ r(   c              ƒ  óØ  "  €  \        VR,          4      pRT9   d"   T P                  Y!P	                  R4      4      pMT P                  P	                  T4      pTfK   ^ RIHp TP	                  R4      pT P                  TR,          RT! T4      '       d   TMR	R
7      G Rj  x€L
  T#   \         d2    \        P                  RTR,          TP	                  R4      4        R# i ; i LE5i)zVResolve the adapter for a claimed ledger row, or None when it cannot be delivered now.rE   z"obligation %s: unknown platform %rr+  Nr.  )Úis_flood_errorÚ
last_errorz4failed to release undispatched runtime obligation %sÚsend_path_degraded©r(  )
r   r   rU   r�   rC   Ú_authorization_adapterr  r  rj  r,  )ra   r  rE   re   rj  rk  s   &&    r&   rb  Ú'GatewayStartupMixin._obligation_adapterî  sä   é € ð	Ü  J¥Ó0ˆHð ˜ÔØ×1Ñ1°(¿G¹GÀIÓ<NÓO‰Gð —m‘m×'Ñ'¨Ó1ˆGð Š?Ý>àŸ™ Ó.ˆJØ×3Ñ3Ø�OÕ$Ð&\Ù$2°:×$>Ò$>‘jÐDXð 4ó ÷ ð ð ˆøô- ô 	Ü�L‰LÐ=¸sÀ?Õ?SÐUX×U\ÑU\Ð]gÓUhÔiÚð	úñ$ùs:   ‚C*„B) –A?C*ÂC*Â"C(Â#C*Â)8C%Ã!C*Ã$C%Ã%C*c               ó   € V ^8„  d   QhRR/# r†   r$   )r%   s   "r&   r'   rL   
  s   € ÷ bñ b°cñ br(   c              ƒ  óp   "  € T P                  V P                  4       G Rj  x€L
 4      G Rj  x€L
 #  L L5i)z±Claim + redeliver in one call. Stable shape for tests/external callers; the startup path
calls the halves separately so the DB half runs inline before the abandonable send task.N)rö   rú   r`   s   &r&   Ú_redeliver_pending_obligationsÚ2GatewayStartupMixin._redeliver_pending_obligations
  s-   é € ð ×8Ñ8¸t×?^Ñ?^Ó?`×9`Óa×aÐaÑ9`Ñaùs   ‚6¡2¢6­4®6´6c               ó$   € V ^8„  d   QhRRRRRR/# )r   rE   r   r.  r0  r"   r‡   r$   )r%   s   "r&   r'   rL     s)   € ÷ Cñ CØ ðCØ.;ðCà	ñCr(   c             ƒ  ó–  "  €  ^ RI HpHp \        P                  ! V4      G Rj  x€L
 '       g   ^ # \        P                  ! WAP
                  VR7      G Rj  x€L
 pT'       g   ^ # T P                  TRR7      G Rj  x€L
 pT Uu0 uF  qwR,          kK  	  ppT FO  pTR,          T9  g   K  T P                  TR,          R	TP                  R
4      ;'       g    RR7      G Rj  x€L
  KQ  	  T P                  T4      G Rj  x€L
 #  Là L°  \         d'    \        P                  RTP
                  RR7        ^ # i ; i LÁu upi  L` LE5i)zþReplay one adapter identity's transient failures after reconnect: the startup sweep cannot
claim live-owner rows, so ``send_path_degraded`` responses would otherwise stay failed until
the next restart. Best-effort; reuses the startup redelivery contract.)r  Úsweep_failed_for_runtimeNr8  z7runtime delivery ledger sweep failed after %s reconnectTr‰   )rÿ   r+  z+failed to release runtime delivery claim %srk  rl  rm  )r  r  rv  ro   rÌ   rD   r   rU   r�   r  r,  rC   rö   )	ra   rE   r.  r  rv  r÷   r  r  Úsendable_idss	   &&$      r&   r>  Ú>GatewayStartupMixin._redeliver_failed_obligations_for_platform  s1  é € ð		ßXÜ ×*Ò*¨>Ó:×:Ö:ÙÜ#×-Ò-Ð.FÏÉÐ`gÔh×hˆG÷ Ùà×KÑKÈGÐeiÐKÓj×jˆÙ8@ÓA¹°˜O×,Ð,¹ˆÐAÛˆCØ�?Õ#¨<Ö7Ø×7Ñ7Ø˜Õ(Ð*WØŸ'™' ,Ó/×GÐGÐ3Gð 8ó ÷ ò ñ ð ×8Ñ8¸ÓB×BÐBñ' ;áhøÜô 	Ü�L‰LØIÈ8Ï>É>Ðdhð ô ò ð		úñ kùÚAññ Cùs¢   ‚E	„!D
 ¥D¦	D
 °E	²%D
 ÁDÁD
 ÁE	Á$E	Á<D>Á=E	ÂE ÂE	Â-+E	ÃE	Ã$EÃ%E	ÄEÄE	ÄD
 ÄD
 Ä
-D;Ä7E	Ä:D;Ä;E	Å E	ÅE	c               ó   € V ^8„  d   QhRR/# )r   r"   úOptional[list]r$   )r%   s   "r&   r'   rL   ,  s   € ÷ ñ ¸>ñ r(   c                óH  €  V P                   P                  ;_uu_ 4        V P                   P                  4        V P                   P                  P	                  4        Uu. uF{  pVP
                  '       g   K  VP                  '       d   K+  VP                  f   K;  VP                  V P                  9   g   KX  Ve   VP                  P                  V8X  g   Ky  VNK}  	  ppRRR4       X'       d9    ^ RIHp T P!                  4       w  rgpTP#                  YgTR7      '       d   R#  T# T# u upi   + '       g   i     LW; i  \         d"   p\        P                  RT4        Rp?R# Rp?ii ; i  \         d"   p\        P%                  RT4        Rp?T# Rp?ii ; i)z”Snapshot resume-pending entries (optionally scoped to ``platform``); None when
enumeration failed or the restart-loop breaker tripped for this boot.Nz/Failed to enumerate resume-pending sessions: %s)Úrestart_loop_guard)Úmax_gap_secondsz$Restart-loop guard check skipped: %s)Úsession_storeÚ_lockÚ_ensure_loaded_lockedÚ_entriesÚvaluesÚresume_pendingÚ	suspendedÚoriginÚresume_reasonÚ_AUTO_RESUME_REASONSrE   r   rU   r�   Úgatewayr|  Ú_restart_loop_guard_configÚcheck_and_recordr�   )	ra   rE   rF   Ú
candidatesré   Ú_rlgÚ_max_restartsÚ_windowÚ_max_gaps	   &&       r&   Ú_resume_pending_candidatesÚ.GatewayStartupMixin._resume_pending_candidates,  sm  € ð	Ø×#Ñ#×)×)Ó)Ø×"Ñ"×8Ñ8Ô:à'+×'9Ñ'9×'BÑ'B×'IÑ'IÔ'KóÙ'K˜eØ×+Õ+ô à!ŸO�Oô ð Ÿ™ô ð ×+Ñ+¨t×/HÑ/HÑHô	 ð
 "Ò)¨U¯\©\×-BÑ-BÀhÑ-N÷ �EÑ'Kð ð ÷ *÷ ðJÝ>Ø37×3RÑ3RÓ3TÑ0�¨Ø×(Ñ(¨ÐQYÐ(×ZÒZÙð [ð ÐˆzÐùò+÷ *×)ûô ô 	Ü�N‰NÐLÈcÔRÝûð	ûô ô JÜ—‘ÐCÀS×IÐIØÐûðJús}   ‚E  AD3Á!D.Á:D.ÂD.ÂD.Â;D.ÃD.Ã"D3Ã$E Ã52E5 Ä.D3Ä3E	Ä>E ÅE ÅE2ÅE-Å-E2Å5F!Æ FÆF!c               ó    € V ^8„  d   QhRRRR/# )r   rg   r\   r"   r!   r$   )r%   s   "r&   r'   rL   I  s   € ÷ ñ °Cð ÀDñ r(   c                óÄ   €  V P                  V4      '       d   R# \        P                  RV4       R#   \         d"   p\        P                  RY4        Rp?R# Rp?ii ; i)zäValidate the session owner against the CURRENT allowlist: a session created before the
allowlist existed (or whose owner was since removed) must not silently receive a full agent
response just because it carries a resume marker.Tz^Skipping auto-resume for %s: session owner is no longer authorized under the current allowlistz;Skipping auto-resume for %s: authorization check failed: %sNF)Ú_is_user_authorized_for_sourcerU   r�   r   )ra   rg   r€   ré   s   &&& r&   Ú_resume_owner_authorizedÚ,GatewayStartupMixin._resume_owner_authorizedI  s`   € ð	lØ×2Ñ2°6×:Ò:ÙÜ�N‰Nð@ØALôñ øô ô 	lÜ�N‰NÐXÐZe×kÐkÙûð	lús   ‚3 ›3 ³A¾AÁAc               ó   € V ^8„  d   QhRR/# r†   r$   )r%   s   "r&   r'   rL   X  s   € ÷ 8ñ 8À#ñ 8r(   c           
     ó&  aa€ ^ RI HpHpHp V! 4       pV P	                  V4      pVf   ^ # ^ pV EF?  o^ RIHpHo \        ;QJ d&    VV3R lV! V 4       4       F  '       g   K   RM	  RM! VV3R lV! V 4       4       4      '       d   K\  SP                  ;'       g    SP                  p	V! W•R7      '       g   K�  V P                  SP                  4      '       d   K°  V P                  S4      p
V P                  V
4      pVfD   \        P!                  RSP                  \#        V
P$                  R	V
P$                  4      4       EK  V P'                  SP                  V
4      '       g   EK>  V P)                  SP                  4      pW,P*                  n        \.        P.                  ! 4       VP*                  n        V P3                  4        \5        R
\6        P8                  V
RR7      pV P;                  \<        P>                  ! V PA                  W½SP                  4      4      4      p\#        V RR4      '       d+   \#        V RR4      pVf	   . ;qðn!        VPE                  V4       V^,          pEKB  	  V'       d   \        PG                  RV4       V# )aW  Auto-continue fresh restart-interrupted sessions: synthesize an empty-text turn (the
``_is_resume_pending`` injection path owns the wording). Sessions whose adapter is offline stay
``resume_pending`` for the reconnect watcher, which re-calls this scoped to that ``platform``;
sessions with a running agent are skipped so none is resumed twice.)ri   Ú_auto_continue_freshness_windowÚ_is_fresh_gateway_interruptionN)Úall_authoritiesÚholds_admissionc              3  óJ   <"  € T F  pS! VSP                   4      x € K  	  R # 5iró   )Ú
session_id)r  Ú	authorityrF   rœ  s   & €€r&   r  ÚHGatewayStartupMixin._schedule_resume_pending_sessions.<locals>.<genexpr>i  s#   øé € ÐgÑQfÀI‘? 9¨e×.>Ñ.>×?Ð?ÓQfùs   ƒ #TF)Úwindow_secsz5Skipping auto-resume for %s: adapter not ready for %srD   r  )ÚtextÚmessage_typer€   ÚinternalrÚ   rØ   z;Scheduled auto-resume for %d restart-interrupted session(s))$r.   ri   r™  rš  r�  Úgateway.session_authoritiesr›  rœ  ÚanyÚlast_resume_marked_atÚ
updated_atÚ_is_session_runningrg   Ú_restored_sourceÚ_delivery_adapter_forrU   r�   rl   rE   r•  Ú_session_staterr   rs   r®   Ú
started_tsÚ_persist_active_agentsr   r   ÚTEXTrÏ   ro   rû   rx   rØ   r~   rV   )ra   rE   ri   r™  rš  Úwindowr‹  Ú	scheduledr›  r]  r€   re   Ú_resume_staterf   rv   r¿   rF   rœ  s   &&              @@r&   Ú!_schedule_resume_pending_sessionsÚ5GatewayStartupMixin._schedule_resume_pending_sessionsX  s  ù€ ÷
	
ñ 	
ñ 1Ó2ˆØ×4Ñ4°XÓ>ˆ
ØÒÙØˆ	ÜˆE÷ Uß‹sÕgÑQ`ÐaeÔQfÓg�s�sŠsÕgÑQ`ÐaeÔQfÓg×gÒgÙð ×0Ñ0×DÐD°E×4DÑ4DˆFÙ1°&×MÓMÙà×'Ñ'¨×(9Ñ(9×:Ò:ÙØ×*Ñ*¨5Ó1ˆFØ×0Ñ0°Ó8ˆGØŠÜ—‘ØKÈU×M^ÑM^Ü˜FŸO™O¨W°f·o±oÓFôò Ø×0Ñ0°×1BÑ1BÀF×KÒKÚð !×/Ñ/°×0AÑ0AÓBˆMØ'>×ÑÔ$Ü,0¯IªI«KˆM×ÑÔ)Ø×'Ñ'Ô)ä  b´{×7GÑ7GÐPVÐaeÔfˆEØ×/Ñ/Ü×#Ò# D×$BÑ$BÀ7ÐSX×SdÑSdÓ$eÓfóˆDô �tÐ;¸U×CÒCÜ Ð&>ÀÓE�Ø’=Ø:<Ð<�EÔ7Ø—‘˜TÔ"Ø˜�N‹IñQ  ÷R Ü�K‰KÐUÐW`ÔaØÐr(   c               ó   € V ^8„  d   QhRR/# ©r   r"   r!   r$   )r%   s   "r&   r'   rL   ’  s   € ÷ Zñ Z tñ Zr(   c                	ó†   € V P                   ;'       g/    V P                  ;'       g    V P                  P                  4       # ró   )Ú_restart_requestedÚ	_drainingÚ_shutdown_eventr:  r`   s   &r&   Ú_startup_should_abortÚ)GatewayStartupMixin._startup_should_abort’  s1   € Ø×&Ñ&×YÐY¨$¯.©.×YÐY¸D×<PÑ<P×<WÑ<WÓ<YÐYr(   c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   •  s   € ÷ ?ñ ?ÀDñ ?r(   c              ƒ  ó
  "  € \        \        P                  RVP                  4      ;_uu_ 4        VP	                  4       G Rj  x€L
  RRR4       V P                  W4      G Rj  x€L
  R#  L'  + '       g   i     L-; i L5i)zFCancel an adapter's background tasks (best-effort) then disconnect it.u'   âœ— %s background-task cancel error: %sN)r   r¬   r¹   rD   Úcancel_background_tasksÚ_safe_adapter_disconnect)ra   re   rE   s   &&&r&   Ú_startup_teardown_adapterÚ-GatewayStartupMixin._startup_teardown_adapter•  s^   é € äœWŸ]™]Ð,UÐW_×WeÑWe×fÕfØ×1Ñ1Ó3×3Ð3÷ gà×+Ñ+¨GÓ>×>Ò>ñ 4÷ g×fúá>ùs:   ‚.B°A.ÁA,ÁA.Á	BÁ%BÁ&BÁ,A.Á.A>	Á9	BÚqueuedTc               ó    € V ^8„  d   QhRRRR/# )r   rÃ  r!   r"   rn   r$   )r%   s   "r&   r'   rL   ›  s    € ÷ tñ tÐRVð tÐbfñ tr(   c          	     ó.   € V P                  WV^^VR7      # )zW``_failed_platforms`` entry for a platform that failed at startup (first retry in 30s).)ra  rB  rÃ  )Ú_reconnect_queue_entry)ra   rE   re   Úplatform_configrÃ  s   &&&&$r&   Ú_startup_retry_entryÚ(GatewayStartupMixin._startup_retry_entry›  s!   € à×*Ñ*¨8¸oÐXYÐacÐlrÐ*ÓsÐsr(   c               ó$   € V ^8„  d   QhRRRRRR/# )r   re   zOptional[BasePlatformAdapter]rE   zOptional[Platform]r"   r!   r$   )r%   s   "r&   r'   rL   Ÿ  s$   € ÷ ñ Ø4ðØGYðà	ñr(   c              ƒ  ó¬  "  € V P                  4       '       g   R# Ve   Ve   V P                  W4      G Rj  x€L
  V P                  p\        P                  ! 4       pVe   W4Jd   VG Rj  x€L
  R# V P
                  P                  4       '       g;   V P                  V P                  V P                  V P                  R7      G Rj  x€L
  R#  L– Ld L
5i)zCClean up and exit startup when restart/shutdown begins mid-startup.FN)ÚrestartÚdetached_restartÚservice_restartT)r»  rÁ  Ú
_stop_taskro   Úcurrent_taskrº  r:  Ústopr¸  Ú_restart_detachedÚ_restart_via_service)ra   re   rE   Ú	stop_taskrÐ  s   &&&  r&   Ú$_abort_startup_if_shutdown_requestedÚ8GatewayStartupMixin._abort_startup_if_shutdown_requestedŸ  sÇ   é € ð ×)Ñ)×+Ò+ÙØÒ 8Ò#7Ø×0Ñ0°ÓC×CÐCØ—O‘Oˆ	Ü×+Ò+Ó-ˆØÒ  YÓ%BØ�OˆOñ ð ×%Ñ%×,Ñ,×.Ò.Ø—)‘)Ø×/Ñ/À$×BXÑBXØ $× 9Ñ 9ð ó ÷ ð ñ ñ Dñ ñùs9   ‚5C·C¸3CÁ+CÁ,%CÂ5CÃCÃCÃCÃCc               ó    € V ^8„  d   QhRRRR/# )r   r¦   zasyncio.AbstractEventLoopr"   r#   r$   )r%   s   "r&   r'   rL   ²  s   € ÷ ^ñ ^Ð0Ið ^Èdñ ^r(   c                ór  € ^ RI HpHp \        V RR4      pVe   \        VRR4      '       g   R# \        V RR4      f;   \	        \
        P                  RRR7      ;_uu_ 4        V! V4      V n        RRR4       \        V R	R4      pVe   VP                  4       '       g]    V! V\        \        VR
\        4      4      \        \        VR\        4      4      \        \        VR\        4      4      R7      V n        R# R#   + '       g   i     L•; i  \         d    \         P#                  RRR7        R# i ; i)z©Arm the selector floor and out-of-loop watchdog before adapters. Disabled entirely with
``gateway.loop_watchdog: false`` in config.yaml (config-only knob).

See #69089.
)Ú_arm_loop_floor_timerÚstart_loop_liveness_watchdogr¢   NÚloop_watchdogTÚ_loop_floor_timer_handlez&Failed to arm gateway loop floor timerr‰   Ú_loop_liveness_watchdogÚloop_watchdog_probe_interval_sÚloop_watchdog_probe_timeout_sÚloop_watchdog_max_strikes)Úprobe_intervalÚprobe_timeoutÚmax_strikesz.Failed to start gateway loop liveness watchdog)Úgateway.shutdown_watchdogrÙ  rÚ  rl   r   r¬   r¹   rÜ  Úis_aliverÁ   r   r   r‡   r   rÝ  r   rU   r�   )ra   r¦   rÙ  rÚ  r¢   Úwatchdogs   &&    r&   Ú_start_loop_liveness_guardsÚ/GatewayStartupMixin._start_loop_liveness_guards²  s  € ÷ 	bÜ˜˜x¨Ó.ˆØÒ¤g¨f°oÀt×&LÒ&LÙÜ�4Ð3°TÓ:ÒBÜ ¤§¡Ð0XÐcg×hÖhÙ0EÀdÓ0K�Ô-÷ iä˜4Ð!:¸DÓAˆØÒ 8×#4Ñ#4×#6Ò#6ð^á/KØÜ#(¬ØÐ @ÔBbó*ó $ô #(¬ØÐ ?ÔA`ó)ó #ô !$¤GØÐ ;Ô=^ó%ó !ô0�Ö,ñ $7÷ i×hûô$ ô ^Ü—‘ÐMÐX\�×]ð^ús   Á"C=Â AD Ã=D	Ä"D6Ä5D6c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   Ò  s   € ÷ -ñ -¨Dñ -r(   c                óþ   € R Fb  w  rp\        WR4      p\        WR4       Vf   K$  \        \        P                  RVRR7      ;_uu_ 4        \        WB4      ! 4        RRR4       Kd  	  R#   + '       g   i     Ky  ; i)u«   Disarm lifetime liveness guards before shutdown can load the loop â€” including the
heartbeat writer, which would otherwise make a draining gateway look healthy to probes.NzFailed to %sTr‰   ))rÝ  rÑ  z#stop gateway loop liveness watchdog)rÜ  Úcancelzcancel gateway loop floor timer)Ú_loop_heartbeat_taskrë  z"cancel gateway loop heartbeat task)rl   Úsetattrr   r¬   r¹   )ra   ÚattrÚmethodÚwhatÚguards   &    r&   Ú_stop_loop_liveness_guardsÚ.GatewayStartupMixin._stop_loop_liveness_guardsÒ  sh   € ó#
ÑˆD˜$ô
 ˜D¨Ó-ˆEÜ�D Ô%ØÔ Ü$¤W§]¡]°NÀDÐSW×XÖXÜ˜EÔ*Ô,÷ YÑXó#
÷ Y×XÐXús   ÁA+Á+A<c               ó   € V ^8„  d   QhRR/# r†   r$   )r%   s   "r&   r'   rL   à  s   € ÷ ñ À3ñ r(   c              ƒ  óv   "  € V P                   P                  4       G Rj  x€L
 pVP                  4        V#  L5i)z¬Discard orphan turn markers before consuming a clean-exit receipt. Raises (fail closed):
continuing with the old receipt would let a later unclean exit masquerade as clean.N)r  Údiscard_active_turn_markersÚunlink)ra   Úmarker_pathÚ	discardeds   && r&   Ú_consume_clean_shutdown_markerÚ2GatewayStartupMixin._consume_clean_shutdown_markerà  s6   é € ð ×2Ñ2×NÑNÓP×Pˆ	Ø×ÑÔØÐñ Qùs   ‚9 7¡9c               ó   € V ^8„  d   QhRR/# )r   r"   ztuple[int, int]r$   )r%   s   "r&   r'   rL   ç  s   € ÷ !ñ !°ñ !r(   c              ƒ  óú  "  € ^ RI Hp ^ ;r#\        R	\        \        RV! RR4      4      ^,          4      4      p\	        \
        P                  R4      ;_uu_ 4        V P                  V4      G Rj  x€L
 pRRR4       \	        \
        P                  R4      ;_uu_ 4        V P                  P                  VR7      G Rj  x€L
 pRRR4       W#3#  L^  + '       g   i     Ld; i L$  + '       g   i     Y#3# ; i5i)
up  Recover only the turns the dead process left marked: one whose reply is already in the
transcript is owed delivery, not a new answer; any other resumes once. An unmarked session
finished its turn (the marker is held until the reply is ledgered), so nothing re-runs it â€”
the old 120 s recency sweep re-answered every recently active chat. Returns (resumed,
ledgered).)Ú
_float_envç      ð?ÚHERMES_AGENT_TIMEOUTi  z/Crash-left reply recovery on startup failed: %sNz0Exact active-turn recovery on startup failed: %s)Úmax_age_secondsi  )
r.   rþ  Úmaxr‡   r   r¬   r­   Ú_ledger_crash_left_repliesr  Úrecover_interrupted_turns)ra   rþ  ÚresumedÚledgeredÚmax_ages   &    r&   Ú_recover_unclean_sessionsÚ-GatewayStartupMixin._recover_unclean_sessionsç  sÉ   é € õ 	+ØÐˆÜ�gœs¤3 s©JÐ7MÈtÓ,TÓ#UÐXYÕ#YÓZÓ[ˆÜœWŸ_™_Ð._×`Õ`Ø!×<Ñ<¸WÓE×EˆH÷ aäœWŸ_™_Ð.`×aÕaØ ×4Ñ4×NÑNÐ_fÐNÓg×gˆG÷ bàÐ Ð ñ F÷ a×`úñ h÷ bÖaàÐ Ð üsZ   ‚AC;ÁCÁ0CÁ1CÁ5*C;Â C&Â?C$Ã C&ÃC;ÃCÃC!	ÃC;Ã$C&Ã&C8	Ã1
C;c               ó    € V ^8„  d   QhRRRR/# )r   r  r‡   r"   r$   )r%   s   "r&   r'   rL   ö  s   € ÷ !ñ !Àð !Èñ !r(   c              ƒ  ó:  "  € ^ RI HpHpHp \        P
                  ! V4      G Rj  x€L
 p\        P                  ! 4       V,
          pV P                  P                  ;_uu_ 4        V P                  P                  4        V P                  P                  P                  4        Uu. uF—  pVP                  '       g   K  VP                  '       g   K+  VP                  '       g   K?  VP                  '       d   KS  VP                   VP"                  VP                  VP                  VP                  VP$                  3NK™  	  ppRRR4       ^ p	X EF!  w  r«rÍrïVP'                  4       pVV8  d   K!  T P)                  V P*                  P-                  V4      G Rj  x€L
 VV4      pVe   V'       d   V'       g   Kk  V'       do   \        P
                  ! VV! V
RV 2V4      V
\/        \1        VP2                  RVP2                  4      4      VP4                  VP6                  VVVR7	      G Rj  x€L
  V P*                  P9                  W¬4      G Rj  x€L
 '       g   EK  V'       g   EK  V	^,          p	EK$  	  V	#  ELSu upi   + '       g   i     ELE; i Lù Li LH5i)a-  Settle every marked turn whose final reply was persisted and clear its marker, so
auto-resume does not regenerate it: a reply live delivery would have suppressed is owed
nothing, any other goes to the delivery ledger for the boot sweep. Without the ledger a
presentable reply stays marked and resumes.)Úcompute_obligation_idr  Úrecord_crash_left_replyNzcrash:rD   )r+  rg   rE   r�   r^  r[  ÚsinceÚadapter_profile)r  r  r  r  ro   rÌ   r®   r~  r  r€  r�  r‚  Úactive_turn_tokenÚactive_turn_started_atr…  r„  rg   rž  Útransport_profileÚ	timestampÚ_crash_left_replyr  Úload_transcriptr\   rl   rE   r�   r^  Úclear_turn_active)ra   r  r  r  r  Ú	ledger_onÚcutoffÚeÚmarkedr  rC  rž  ÚtokenÚ
started_atr…  r.  Ústartedr¢  s   &&                r&   r  Ú.GatewayStartupMixin._ledger_crash_left_repliesö  s2  é € ÷
 	kÑjÜ!×+Ò+¨NÓ;×;ˆ	Ü—’“˜Õ.ˆØ×Ñ×%×%Ó%Ø×Ñ×4Ñ4Ô6ð ×+Ñ+×4Ñ4×;Ñ;Ô=óñ >�AØ×&Õ&ô&ð ,-×+CÕ+Cô&ð IJÏÍô&ð Z[×YdÕYdô&�—‘ §¡¨a×.AÑ.AÀ1×C[ÑC[Ð]^×]eÑ]eØ×$Ñ$ó&á=ð ð ÷ &ð ˆÜCIÑ?ˆC˜U°Ø ×*Ñ*Ó,ˆGØ˜ÔÙØ×)Ñ)°×0HÑ0H×0XÑ0XÐYcÓ0d×*dØ*1°6ó;ˆDàŠ|§¯YÙßÜ×'Ò'Ø+Ù"7¸¸vÀeÀWÐ=MÈtÓ"TÐbeÜ ¤¨¯©¸'À6Ç?Á?Ó!SÓTÐ^d×^lÑ^lØ$×.Ñ.¸ÀGÐ]dô	f÷ fð fð
 ×-Ñ-×?Ñ?ÀÓK×K×KÑK×PTÒPTØ˜A•“ñ DJð  ˆò7 <ùò÷ &×%Ð%úñ +eñ
fñ
 Lùs£   ‚$J¦I9§>JÁ%AJÂ&I<Â?I<ÃI<Ã'I<Ã;AI<ÅJÅAJÆJ
ÆJÆ2JÆ:	JÇA)JÈ-JÈ."JÉJÉJÉJÉ)JÉ<JÊJ	Ê
JÊJÊJc               ó$   € V ^8„  d   QhRRRRRR/# )r   ÚhistoryrÙ   r  rÁ   r"   r0  r$   )r%   s   "r&   r'   rL     s&   € ÷ !{ñ !{¨ð !{¸ð !{È-ñ !{r(   c                óÈ  € ^ RI Hp ^ RIHpHpHp ^ RIHp ^ RIH	p	 ^ RI
Hp
 ^ RIHp V Uu. uF  qÌP                  R4      R9  g   K  VNK  	  ppV'       d
   VR,          M/ pVP                  R4      R8w  gc   VP                  R	4      '       gL   \        VP                  R
4      \         4      '       d'   V! VP                  R4      4      ;'       g    ^ V8  d   R# \#        R \%        V4       4       / 4      pV! VP                  R4      4      '       dZ    V P'                  V4      pT;_uu_ 4        V
! VP                  R4      VP2                  4      '       d    RRR4       R#  RRR4       V! VR
,          4      '       dR   T! VP                  R4      VP                  R4      ;'       g    / P                  R4      4      pV'       d   R# V	! 4       # V! V! VP2                  VR
,          4      4      P5                  4       ;'       g    R# u upi   \(         d1    \*        P-                  RTP.                  RR7       \1        4       p EL$i ; i  + '       g   i     Lñ; i)a˜  What a crash-left turn owes, judged as live delivery would have: ``None`` when it never
persisted a final reply after *started*; ``""`` when nothing would have been presented (a
silence marker on a machinery turn or on a turn the adapter reported as not addressed to the
bot, a muted diagnostic wake); else the text to send, with any other bare silence marker
replaced by the same notice the live path sends.)Ú_strip_media_directives)Úis_intentional_silence_responseÚis_machinery_display_kindÚsilence_allowed)Ú _sanitize_gateway_final_response)Ú_unexpected_silence_reply)Údiagnostic_turn_muted)Úcoerce_epochÚroleÚ	assistantÚ
tool_callsr[  r  Nc              3  óT   "  € T F  qP                  R 4      R8X  g   K  Vx € K   	  R# 5i)r*  ÚuserN)rC   )r  Úms   & r&   r  Ú8GatewayStartupMixin._crash_left_reply.<locals>.<genexpr>,  s!   é € ÐOÑ"3˜Q·u±u¸V³}ÈÑ7N—q’qÓ"3ùs   ‚(ž
(Údisplay_kindz(Crash-left reply: no routed scope for %sTr‰   Údisplay_metadatar  Úreply_expected)Úsession_metaÚsysteméÿÿÿÿ)Úgateway.platforms.baser"  Úgateway.response_filtersr#  r$  r%  r.   r&  Úgateway.run_turnr'  Úgateway.warning_notificationsr(  Úhermes_cli.timefmtr)  rC   rm   r\   ÚnextÚreversedÚ _media_delivery_scope_for_sourcer   rU   r�   r�   r   rE   Ústrip)ra   r   r  r…  r"  r#  r$  r%  r&  r'  r(  r)  r/  ÚvisibleÚlastÚpromptÚscopeÚ	silent_oks   &&&&              r&   r  Ú%GatewayStartupMixin._crash_left_reply  sè  € õ 	C÷	
ñ 	
õ 	AÝ>ÝGÝ3Ù%ÓY™g˜¯©¨v«Ð>XÑ)X—1�1™gˆÐYß%ˆw�rŽ{¨2ˆØ�H‰H�VÓ Ô+¨t¯x©x¸×/EÒ/EÌZÐX\×X`ÑX`ÐajÓXkÔmp×MqÒMqÙ  §¡¨+Ó!6Ó7×<Ð<¸1ÀÔGÙÜÑO¤(¨7Ô"3ÓOÐQSÓTˆÙ$ V§Z¡Z°Ó%?×@Ò@ð&Ø×=Ñ=¸fÓE�÷ ’Ù(¨¯©Ð4FÓ)GÈÏÉ×YÒYØ÷ ‘ØY÷ ñ +¨4°	­?×;Ò;Ù'Ø—
‘
˜>Ó*¨V¯Z©ZÐ8JÓ-K×-QÐ-QÈr×,VÑ,VÐWgÓ,hójˆIç"�2ÐCÑ(AÓ(CÐCÙ&Ñ'GÈÏÉÐY]Ð^gÕYhÓ'iÓj×pÑpÓr×zÐzÐvzÐzùò' Zøô ô &Ü—‘ÐGÈÏÉÐbf�ÔgÜ#›“ð&ú÷ —ús)   ­HÁ	HÄH Ä3*IÈ7IÉIÉI!	c                 ó&  € ^ RI p ^ RIHp VP                  4       pVf   VP	                  4       pVf   \        R4      hVP                  P                  4       pVP                  R4      '       d   VP                  R4      '       d   \        R4      hV# )zBStart the local Group Chat worker without importing the dashboard.N©Úmethods_groupsz.Group Chat worker has no bound session backendr_   ÚstoppingzGroup Chat worker did not start)	Útui_gateway.serverÚtui_gatewayrH  Úget_hosted_room_serviceÚstart_hosted_room_serviceÚRuntimeErrorÚruntimeÚstatusrC   )rK  rH  ÚservicerP  s       r&   Ú_start_hosted_room_worker_syncÚ2GatewayStartupMixin._start_hosted_room_worker_sync<  s|   € ó 	"Ý.Ø ×8Ñ8Ó:ˆØŠ?Ø$×>Ñ>Ó@ˆGØŠ?ÜÐOÓPÐPØ—‘×'Ñ'Ó)ˆØ�z‰z˜)×$Ò$¨¯
©
°:×(>Ò(>ÜÐ@ÓAÐAØˆr(   c              ƒ  	ó¬   "  € \        V R R4      e   ^ RIHp V! V 4      G Rj  x€L
 # \        P                  ! V P
                  4      G Rj  x€L
 #  L, L5i)Úsession_authorityN)Úensure_hosted_service)rl   Úgateway.session_hosted_servicerV  ro   rÌ   rR  )ra   rV  s   & r&   Ú_ensure_hosted_room_workerÚ.GatewayStartupMixin._ensure_hosted_room_workerK  sH   é € Ü�4Ð,¨dÓ3Ò?ÝLÙ.¨tÓ4×4Ð4Ü×&Ò& t×'JÑ'JÓK×KÐKñ 5ÙKùs!   ‚!A£A¤'AÁAÁAÁAc               ó    € V ^8„  d   QhRRRR/# )r   ÚintervalrÁ   r"   r#   r$   )r%   s   "r&   r'   rL   Q  s   € ÷ *ñ *¸%ð *È$ñ *r(   c              ƒ  óª   "  € V P                   '       d9   V P                  4       G Rj  x€L
  \        P                  ! V4      G Rj  x€L
  KJ  R#  L& L
5i)z>Keep the room worker alive for the messaging gateway lifetime.N)r6  rX  ro   Úsleep)ra   r[  s   &&r&   Ú_hosted_room_worker_watcherÚ/GatewayStartupMixin._hosted_room_worker_watcherQ  s=   é € à�m�mˆmØ×1Ñ1Ó3×3Ð3Ü—-’- Ó)×)Ò)ñ Ù3Ù)ùs&   ‚A•A¨A©AÁAÁ	AÁAc               ó    € V ^8„  d   QhRRRR/# )r   rº   rÁ   r"   r!   r$   )r%   s   "r&   r'   rL   W  s   € ÷ añ a°eð aÀdñ ar(   c              ƒ  ó¾   "  € \        V RR4      e   ^ RIHp V! WR7      G Rj  x€L
 # ^ RIHp \
        P                  ! VP                  VR7      G Rj  x€L
 #  L4 L5i)zAPause room execution durably without interrupting accepted turns.rU  N)Ústop_hosted_servicerÆ   rG  )rl   rW  rb  rK  rH  ro   rÌ   Ústop_hosted_room_service)ra   rº   rb  rH  s   &&  r&   Ú_stop_hosted_room_workerÚ,GatewayStartupMixin._stop_hosted_room_workerW  sO   é € ä�4Ð,¨dÓ3Ò?ÝJÙ,¨TÔC×CÐCÝ.Ü×&Ò& ~×'NÑ'NÐX_Ô`×`Ð`ñ Dá`ùs!   ‚"A¤A¥/AÁAÁAÁAc               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   _  s   € ÷ /ñ /¨Dñ /r(   c                óª  € \        \        P                  RRR7      ;_uu_ 4        \        V RR4      pVe"   VP	                  4       '       g    RRR4       R# \
        P                  ! \        \        \        V RR4      R7      4      ;q n	        RVn
        \        V R	R4      pVe   V P                  W24       RRR4       R#   + '       g   i     R# ; i)
zÃStart the loop-liveness heartbeat task (idempotent, best-effort). An asyncio task so a
frozen loop stops refreshing ``state/gateway.heartbeat``; cancelled with the others in stop().

See #66892.
z&Failed to start gateway loop heartbeatTr‰   rì  NÚ_gateway_started_atg        )Ú
interval_sÚ
start_timerJ  )r   r¬   r¹   rl   r·   ro   rû   r   r   rì  Ú_hermes_supervised_watcherrM  )ra   Ú_existing_hbrv   Ú_bgs   &   r&   Ú_start_loop_heartbeat_taskÚ.GatewayStartupMixin._start_loop_heartbeat_task_  s¶   € ô œWŸ]™]Ð,TÐ_c×dÖdÜ" 4Ð)?ÀÓFˆLØÒ'°×0AÑ0A×0CÒ0CØ÷ eÑdô 07×/BÒ/BÜ&Ü;Ü& tÐ-BÀCÓHôó0ð ˆDÔ,ð /3ˆDÔ+Ü˜$Ð 3°TÓ:ˆCØŠØ×#Ñ# CÔ.÷ e×d×dÒdús   ¥'CÁCÁACÃC	c                ó0  € ^ RI Hp \        V P                  RR4      ;'       g/    \        P
                  P                  \        V! 4       4      R4      p\        P                  ! VRR7       \        \        P
                  P                  VR4      RR	R
7      # )zMOpen (append) ``<log_dir>/gateway_faulthandler.log``, creating the directory.rŸ   Úlog_dirNÚlogsT)Úexist_okzgateway_faulthandler.logÚazutf-8)Úencoding)
r.   r5   rl   r¢   rS   ÚpathÚjoinr\   ÚmakedirsÚopen)ra   r5   rq  s   &  r&   Ú_open_faulthandler_logÚ*GatewayStartupMixin._open_faulthandler_logu  se   € å/Ü˜$Ÿ+™+ y°$Ó7×gÐg¼2¿7¹7¿<¹<ÌÉOÓL]ÓH^Ð`fÓ;gˆÜ
�Š�G dÕ+Ü”B—G‘G—L‘L Ð*DÓEÀsÐU\Ô]Ð]r(   c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   |  s   € ÷ ñ ¨Tñ r(   c           	     ój  €  \         P                  ! 4        \        \        RR4      pTeo   \        \         R4      '       dW   \        \        P                  RRR7      ;_uu_ 4        \         P                  ! YP                  4       RR	R
7       RRR4       R# R# R#   \        \        \        3 dm    \        \        P                  RRR7      ;_uu_ 4        \         P                  ! T P                  4       RR7       RRR4        Kñ    + '       g   i      EL; ii ; i  + '       g   i     R# ; i)zLEnable faulthandler (stderr or a log file) plus the SIGUSR2 stack-dump hook.z!faulthandler.enable() unavailableTr‰   )ÚfileÚall_threadsNÚSIGUSR2Úregisterz*Could not set up faulthandler file loggingF)r~  r  Úchain)ÚfaulthandlerÚenablerN  Ú
ValueErrorÚOSErrorr   r¬   r¹   rz  rl   ÚsignalÚhasattrr�  )ra   Ú_sigusr2s   & r&   Ú_start_install_faulthandlerÚ/GatewayStartupMixin._start_install_faulthandler|  sä   € ð	Zô ×ÒÔ!ô œ6 9¨dÓ3ˆØÒ¤G¬L¸*×$EÒ$EÜ ¤§¡Ð0\Ðgk×lÖlÜ×%Ò%Ø×#>Ñ#>Ó#@ÈdÐZ_õ÷ mÑlñ %FÑøô œj¬'Ð2ô 	ZÜ ¤§¡Ð0SÐ^b×cÖcÜ×#Ò#¨×)DÑ)DÓ)FÐTXÕY÷ d×c×cÔcúð	Zú÷ m×lÐlús5   ‚B Á&(D!Â:DÃ'DÃ=DÄDÄDÄDÄ!D2	c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   ‘  s   € ÷ @fñ @f°dñ @fr(   c           	   ƒ  ó  "  €  \         P                  ! 4       V n        V P                  eV   T P	                  V P                  4       \        \        P                  RRR7      ;_uu_ 4        ^ RIH	p V! 4        RRR4       \        P                  RV P                  P                  4       V P                  4        V P                  4        V P!                  4        \#        \$        4      ;_uu_ 4        \&        P(                  ! RR4      pVP+                  4       R9   d   \        P                  R	4       M\        P-                  R
V4       RRR4       \#        \$        4      ;_uu_ 4        ^ RIHp V! 4       pV'       d   VR8w  d   \        P                  RV4       RRR4        ^ RIHp \         P6                  ! VRRRRRR7      G Rj  x€L
 pV'       g   \        P-                  R4       \        \        P                  RRR7      ;_uu_ 4        ^ RIHp ^ RIH p T! T! 4       4      T n!        \E        T PB                  RR4      '       d   \        P                  R4       RRR4       \        \        P                  RRR7      ;_uu_ 4        ^ RI#H$p	H%p
 T
! T	! 4       4      pT'       d,   \        P-                  RT4       \        P-                  R4       RRR4       R#   \         d    RT n         ELØi ; i  + '       g   i     ELŠ; i  + '       g   i     ELÌ; i  + '       g   i     ELŽ; i ELk  \$         d    \        P9                  RRR7        ELqi ; i  + '       g   i     EL	; i  + '       g   i     R# ; i5i)zTBind the gateway loop, disarm the startup watchdog, and log the startup environment.NzStartup watchdog disarm failedTr‰   )Údisarm_startup_watchdogzSession storage: %sÚHERMES_REDACT_SECRETSÚtruez^Secret redaction: ENABLED (tool output, logs, and chat responses are scrubbed before delivery)zÆSecret redaction: DISABLED (HERMES_REDACT_SECRETS=%s). API keys and tokens may appear verbatim in chat output, session JSONs, and logs. Set security.redact_secrets: true in config.yaml to re-enable.)Úget_active_profile_namer  zActive profile: %s)Úwrite_runtime_statusÚstartingç       @)Úgateway_stateÚexit_reasonÚclear_profile_platformsÚreload_existingÚwait_timeoutz3Timed out persisting initial gateway runtime statusz+Initial gateway runtime-status write failedz)gateway health OTLP export startup failed©Úload_config)Ústart_gateway_health_exportÚenabledFz#Gateway health OTLP export: enabledz1security advisory check failed at gateway startup)Údetect_compromisedÚgateway_log_messagez%szCRun `hermes doctor` on the gateway host for full remediation steps.>   Ú1ÚonÚyesr�  )&ro   r¡   Ú_gateway_looprN  rç  r   r¬   r¹   Úhermes_startup_watchdogrŽ  rU   rV   r¢   Úsessions_dirÚ#_start_log_systemd_timing_alignmentÚ _start_log_retired_session_resetrX   r   r   rS   rT   Úlowerr�   Úhermes_cli.profilesr‘  Úgateway.statusr’  rÌ   r�   rR   r›  Ú&agent.monitoring.gateway_health_exportrœ  Ú_gateway_health_export_runtimerl   Úhermes_cli.security_advisoriesrž  rŸ  )ra   rŽ  Ú_redact_rawr‘  r  r’  Ú	persistedr›  rœ  rž  rŸ  Ú_adv_msgs   &           r&   Ú_start_log_startup_environmentÚ2GatewayStartupMixin._start_log_startup_environment‘  s˜  é € ð	&Ü!(×!9Ò!9Ó!;ˆDÔð ×ÑÒ)Ø×,Ñ,¨T×-?Ñ-?Ô@ô !¤§¡Ð0PÐ[_×`Ö`ÝKÙ'Ô)÷ aô 	�‰Ð)¨4¯;©;×+CÑ+CÔDØ×0Ñ0Ô2Ø×-Ñ-Ô/Ø×ÑÔ ô ”i× Õ äŸ)š)Ð$;¸VÓDˆKØ× Ñ Ó"Ð&@Ô@Ü—‘ð>õô
 —‘ð3à4?ô÷ !ô ”i× Õ ÝCÙ.Ó0ˆHß˜H¨	Ô1Ü—‘Ð0°(Ô;÷	 !ð
	WÝ;Ü%×/Ò/Ø$Ø(Ø Ø(,Ø $Ø ô÷ ˆI÷ Ü—‘ÐTÔUô œWŸ]™]Ð,WÐbf×gÖgÝ5ÝZÙ2MÉkËmÓ2\ˆDÔ/Ü�t×:Ñ:¸IÀu×MÒMÜ—‘ÐAÔB÷ hô œWŸ]™]Ð,_Ðjn×oÖoß^Ù*Ñ+=Ó+?Ó@ˆHßÜ—‘˜t XÔ.Ü—‘ÐdÔe÷ pÑoøôo ô 	&Ø!%ˆD×ð	&ú÷ a×`Ð`ú÷ !× Ð ú÷ !× Ð úòøô ô 	WÜ�L‰LÐFÐQUˆL×Vð	Wúçg×gÐgú÷ p×oÐoüsà   ‚N
„K! žAN
Á+K:Á9A9N
Ã2ALÅN
Å*3L"ÆN
Æ&%L9 ÇL6ÇL9 ÇL9 Ç-$N
ÈAM"É",N
ÊA	M6Ë
N
Ë!K7Ë3N
Ë6K7Ë7N
Ë:L	Ì	N
ÌL	Ì	N
Ì"L3	Ì-	N
Ì6L9 Ì9"MÍN
ÍMÍN
Í"M3	Í-	N
Í6N	Î	N
c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   Ó  s   € ÷ Vñ V°$ñ Vr(   c                óà  € \        \        P                  RRR7      ;_uu_ 4        ^ RIHp ^ RIHp ^ RIHpH	pH
p V! \        V P                  P                  4      4       UUu. uF   w  rgV! V! V4      4      ;p'       g   K  Wh3NK"  	  p	ppV	'       d8   V! 4       '       g+   V	 F$  w  pw  r«\        P                  RWc! W«4      4       K&  	  RRR4       R# u uppi   + '       g   i     R# ; i)	z�Warn per served profile whose config still declares an idle/daily ``session_reset``,
unless the plugin that honours it is enabled. Never raises.z"retired session_reset check failedTr‰   )Úread_yaml_layers)Úprofiles_to_serve)Úformat_noticeÚreset_plugin_enabledÚretired_reset_policyzProfile %s: %sN)r   r¬   r¹   Úgateway.config_loaderrµ  r©  r¶  Ú#hermes_cli.session_reset_retirementr·  r¸  r¹  r!   r¢   r�   rU   r�   )ra   rµ  r¶  r·  r¸  r¹  rI  r    ÚfoundÚhitsrv  Úmodes   &           r&   r§  Ú4GatewayStartupMixin._start_log_retired_session_resetÓ  sÃ   € ô œWŸ]™]Ð,PÐ[_×`Ö`Ý>Ý=ßuÑuÙ4EÄdÈ4Ï;É;×KiÑKiÓFjÔ4kô PÑ4k¡j dÙ!5Ñ6FÀtÓ6LÓ!MÐM˜ÓMô "�T“MÑ4kˆDñ PçÑ0×2Ò2Û*.Ñ&�D™,˜4Ü—N‘NÐ#3°T¸=ÈÓ;TÖUñ +/÷ aÑ`ùóP÷	 a×`Ð`ús)   ¥?CÁ$C
ÂC
Â
CÂ"*CÃCÃC-	c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   à  s   € ÷ ñ °Tñ r(   c                ó°  € \        \        P                  R4      ;_uu_ 4        ^ RIHp V! V P
                  \        V R\        4      4      pVek   VP                  R4      '       dT   \        P                  RVP                  RR4      VR	,          VR
,          VP                  R\        4      VR,          4       RRR4       R#   + '       g   i     R# ; i)z¬Warn when systemd's TimeoutStopSec does not cover the drain window (a unit file from before
an upgrade may encode the old default, so SIGKILL hits mid-drain). Never raises.z)check_systemd_timing_alignment failed: %s)Úcheck_systemd_timing_alignmentÚ_cron_drain_timeoutNÚmismatcha(  Stale systemd unit detected: %s has TimeoutStopSec=%.0fs but drain_timeout=%.0fs cron_drain_timeout=%.0fs (expected >=%.0fs). systemd may SIGKILL the gateway mid-drain. Run `hermes gateway install --force` to regenerate the unit, or shorten agent.restart_drain_timeout / agent.cron_drain_timeout.Úunitz	(unknown)Útimeout_stop_secÚdrain_timeoutÚcron_drain_timeoutÚexpected_min)r   r¬   r¹   Úgateway.shutdown_forensicsrÂ  Ú_restart_drain_timeoutrl   r   rC   rU   r�   )ra   rÂ  Ú
_alignments   &  r&   r¦  Ú7GatewayStartupMixin._start_log_systemd_timing_alignmentà  sª   € ô œWŸ]™]Ð,W×XÕXÝQÙ7Ø×+Ñ+Ü˜Ð3Ô5WÓXóˆJð Ò%¨*¯.©.¸×*DÒ*DÜ—‘ðNð —N‘N 6¨;Ó7¸ÐDVÕ9WØ˜Õ/Ø—N‘NÐ#7Ô9[Ó\Ø˜~Õ.ô	÷ Y×X×XÒXús   £ACÁ'ACÃC	c              #  	ó*   "  € T F	  q R 2x € K  	  R# 5i)Ú_ALLOWED_USERSNr$   ©r  r  s   & r&   r  ÚGatewayStartupMixin.<genexpr>ü  s   é € Ð'_ÑF^À¨#¨^Õ(<ÓF^ùó   ‚c              #  	ó*   "  € T F	  q R 2x € K  	  R# 5i)Ú_ALLOW_ALL_USERSNr$   rÐ  s   & r&   r  rÑ     s   é € Ð#]ÑD\¸q cÐ)9Õ$:ÓD\ùrÒ  c               ó   € V ^8„  d   QhRR/# r¶  r$   )r%   s   "r&   r'   rL     s   € ÷ ,ñ ,¨Dñ ,r(   c           	     óH  aa€ ^ RI HpHp \        V P                  4      pR.V P
                  Op\        \        4      ;_uu_ 4        ^ RIH	o . SP                  4       O\        RV3R lV P                  P                  P                  4        4       4      O Uu. uF  pVP                  R8X  g   K  VNK  	  ppY6 Uu. uF"  qUP                   '       g   K  VP                   NK$  	  up,          pYF Uu. uF"  qUP"                  '       g   K  VP"                  NK$  	  up,          pRRR4       \$        P&                  \$        P(                  \$        P*                  0o\,        ;QJ dA    V3R lV P                  P                  P                  4        4       F  '       g   K   RM6	  R	M2! V3R lV P                  P                  P                  4        4       4      pV'       dŠ   \,        ;QJ d    R
 V 4       F  '       g   K   RM	  R	M! R
 V 4       4      '       gP   \,        ;QJ d    R V 4       F  '       g   K   RM	  R	M! R V 4       4      '       g   \.        P1                  R4       V! V P                  4      pV'       d}   VP3                  R^4      ^ ,          p	\5        \%        V	4      4      ;'       g    R^,          p
\.        P7                  RT	T
;'       g    R4       V! RVR7       V P9                  V4       R# R	# u upi u upi u upi   + '       g   i     ELö; i)zHWarn about missing allowlists; return True when startup must be refused.)Ú"_own_policy_open_startup_violationÚ_write_runtime_status_quietÚGATEWAY_ALLOW_ALL_USERSr=   Nc              3  ó†   <"  € T F6  w  rVP                   '       g   K  SP                  VP                  4      x € K8  	  R # 5iró   )r�  rC   rD   )r  r  Úcfgr>   s   &  €r&   r  ÚAGatewayStartupMixin._start_check_access_policy.<locals>.<genexpr>  s8   øé € ð WkÙ=Z±6°1Ð^a×^iÕ^iÔ.Ð!×%Ñ% a§g¡g×.Ð.Ó=Zùs
   ƒAž#AÚpluginc              3  óZ   <"  € T F   w  rVP                   ;'       d    VS9  x € K"  	  R # 5iró   )r�  )r  rE   rÛ  Únon_messagings   &  €r&   r  rÜ    s+   øé € ð 
ÙOl¹m¸hˆC�K‰K×9Ð9˜H¨MÑ9Ô9ÓOlùs   ƒ+�+TFc              3  óN   "  € T F  p\         P                  ! V4      x € K  	  R # 5iró   )rS   rT   ©r  Úvs   & r&   r  rÜ    s   é € Ð$H¹<°a¤R§Y¢Y¨q§\ \»<ùs   ‚#%c              3  ór   "  € T F-  p\         P                  ! VR 4      P                  4       R9   x € K/  	  R# 5i)r  N>   r   r¢  r�  )rS   rT   r¨  rá  s   & r&   r  rÜ    s.   é € ð U
ÙFTÀŒB�IŠI�a˜Ó×"Ñ"Ó$Ð(<Ö<Ãnùs   ‚57a4  No env user allowlists configured. Messaging platforms default to pairing/allowlist policies and will deny unknown senders unless you configure platform allowlists (e.g., TELEGRAM_ALLOWED_USERS=your_id) or explicitly opt in with GATEWAY_ALLOW_ALL_USERS=true plus dm_policy/group_policy: open on the platform.Ú:zuRefusing to start: %s has dm_policy/group_policy set to 'open' but neither GATEWAY_ALLOW_ALL_USERS nor %s is enabled.za platform allow-all flagÚstartup_failed©r•  r–  )NNN)r.   r×  rØ  rÙ   Ú_BUILTIN_ALLOWED_USERS_VARSÚ_BUILTIN_ALLOW_ALL_VARSr   r   rB   r>   Úloaded_entriesÚfilterr¢   Ú	platformsr!  r€   Úallowed_users_envr@   r   ÚLOCALÚ
API_SERVERÚWEBHOOKr¦  rU   r�   ÚsplitrH   r(  Ú_request_clean_exit)ra   r×  rØ  Úallowed_varsÚallow_all_varsr  ÚentriesÚhas_messagingÚreasonÚplatform_valuer@   rß  r>   s   &          @@r&   Ú_start_check_access_policyÚ.GatewayStartupMixin._start_check_access_policy  s�  ù€ ÷	
ô ˜D×<Ñ<Ó=ˆØ3ÐS°d×6RÑ6RÐSˆÜ”i× Õ ÝCð#mÐ$5×$DÑ$DÓ$Fð #mÌÐPTô WkØ=A¿[¹[×=RÑ=R×=XÑ=XÔ=ZóWkó Jlñ #mó )ñ #m˜Qà—8‘8˜xÑ'÷ �qñ #mˆGð )ð ¸'ÓY¹'°Q×EXÕEXÔ0˜Q×0Ô0¹'ÑYÕYˆLØ¸ÓS¹°1Ç?Å?œ˜qŸœ¹ÑSÕSˆN÷ !ô "Ÿ™¬×)<Ñ)<¼h×>NÑ>NÐOˆß›ô 
ØOSÏ{É{×OdÑOd×OjÑOjÔOló
ŸŸšô 
ØOSÏ{É{×OdÑOd×OjÑOjÔOló
ó 
ˆ÷ §£Ñ$H¹<Ó$H§§¢Ñ$H¹<Ó$H×!HÒ!H×QTÓQTñ U
ÙFTóU
×QT×QTÒQTñ U
ÙFTóU
÷ R
ò R
ô �N‰NðEôñ 4°D·K±KÓ@ˆßØ#Ÿ\™\¨#¨qÓ1°!Õ4ˆNÜ-¬h°~Ó.FÓG×]Ð]ÐK]Ð_`ÕaˆMÜ�L‰LðIØJXØ×<Ð<Ð!<ôñ
 (Ð6FÐTZÕ[Ø×$Ñ$ VÔ,ÙÙùòA)ùò ZùÚS÷ !× Ð úsI   ÁALÂLÂ1LÂ7LÂ=L
ÃL
Ã%LÃ2L
Ä
L
Ä	LÌLÌL!	c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   1  s   € ÷ Dñ D°ñ Dr(   c                 ó¸  € \        \        P                  RRR7      ;_uu_ 4        ^ RIHp  ^ RIHp V! 4        V ! 4        RRR4        ^ RIHpH	pH
pHp V! 4        V! 4       '       d#   \        P                  RV! 4       4       V! 4        \         P#                  4        R#   + '       g   i     Li; i  \         d    \        P                  R	RR7        LMi ; i)
zWPlugin discovery, relay registration and shell-hook/webhook registration. Never raises.z*plugin discovery failed at gateway startupTr‰   )Údiscover_plugins)Úsweep_pending_plugin_deletesN)Úregister_relay_adapterÚ	relay_urlÚself_provision_relayÚsend_relay_policyz*relay adapter registered (connector at %s)z4relay adapter registration failed at gateway startup)r   r¬   r­   Úhermes_cli.pluginsrü  Úhermes_cli.plugins_cmd_removerý  Úgateway.relayrþ  rÿ  r   r  rU   rV   r   r�   rJ   Ú%_register_launch_profile_config_hooks)rü  rý  rþ  rÿ  r   r  s         r&   Ú#_start_register_plugins_relay_hooksÚ7GatewayStartupMixin._start_register_plugins_relay_hooks0  s¥   € ô
 œWŸ_™_Ð.ZÐei×jÖjÝ;ÝRÙ(Ô*ÙÔ÷	 kð	b÷ó ñ !Ô"Ù%×'Ò'Ü—‘ÐHÉ)Ë+ÔVá!Ô#ô 	×AÑAÖC÷' k×jûô" ô 	bÜ�N‰NÐQÐ\`ˆNÖað	bús#   ¥B!Á	B4 Á)"B4 Â!B1	Â4"CÃCc               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   K  s   € ÷ dñ d°4ñ dr(   c                 ó@  € ^ RI Hp  V ! 4       '       g(   \        P                  R\        P
                  R7       R# ^ RIHp ^ RIH	p V! V! 4       4      ;_uu_ 4        \        P                  R\        P
                  R7       RRR4       R#   + '       g   i     R# ; i)af  The launch profile's ``hooks:`` block, registered under ITS runtime scope when multiplexing.

Startup runs before any turn scope exists and ``get_secret`` fails closed outside a scope
while multiplexing is on, so the launch profile needs the scope secondaries already get
(``_start_secondary_profile_adapters``) or its ``secret_env`` targets cannot resolve.
)Úis_multiplex_activez9shell-hook/webhook registration failed at gateway startuprµ   Nr*   )Úget_process_hermes_home)
Úagent.secret_scoper
  rJ   Ú_register_config_hooksr¬   r­   r.   r+   r6   r  )r
  r+   r  s      r&   r  Ú9GatewayStartupMixin._register_launch_profile_config_hooksJ  sw   € õ 	;Ù"×$Ò$Ü×6Ñ6ØKÔSZ×SbÑSbð 7ô dáÝ6Ý<Ù#Ñ$;Ó$=×>Õ>Ü×6Ñ6ØKÔSZ×SbÑSbð 7ô d÷ ?×>×>Ò>ús   Á&BÂB	c               ó$   € V ^8„  d   QhRRRRRR/# )r   Úfail_fmtr\   r¶   r‡   r"   r#   r$   )r%   s   "r&   r'   rL   ^  s'   € ÷ Cñ C¨ð CÀð CÐY]ñ Cr(   c               ó¶   €  ^ RI Hp ^ RIHp ^ RIHp V! 4       pV! VRR7       V! V4       R#   \
         d    \        P                  ! Y.TO5RR/   R# i ; i)a¸  Register declarative shell hooks + outbound webhooks from the CURRENT scope's config.

The gateway never prompts (register_from_config defaults to ``interactive=False``), even
when a hidden console makes stdin look like a TTY, so consent must come from the allowlist,
--accept-hooks, HERMES_ACCEPT_HOOKS, or hooks_auto_accept: true; ``accept_hooks=False`` lets
register_from_config resolve env + config.
Never raises (logged at ``level``).
rš  )Úregister_from_configF)Úaccept_hooksrŠ   TN)rR   r›  Úagent.shell_hooksr  Úagent.outbound_webhooksr   rU   ræ   )r  r¶   Ú	fail_argsr›  r  Úregister_outbound_webhooksÚ
_hooks_cfgs   &$*    r&   r  Ú*GatewayStartupMixin._register_config_hooks]  sQ   € ð	CÝ5Ý>ÝbÙ$›ˆJÙ  ¸%Õ@Ù& zÖ2øÜô 	CÜ�JŠJ�uÐB¨ÒB¸TÕBð	Cús   ‚+/ ¯%AÁAc               ó   € V ^8„  d   QhRR/# r†   r$   )r%   s   "r&   r'   rL   q  s   € ÷ ñ È#ñ r(   c                óô  € \        V P                  RR4      '       g   ^ # ^ RIHpHp ^ RIHp V! 4       P                  4       p^ pV! V P                  4       F_  w  rx\        V4      P                  4       V8X  d   K%   V! \        V4      / 4      ;_uu_ 4        WaP                  4       ,          pRRR4       Ka  	  V#   + '       g   i     Kv  ; i  \         d    \        P                  RTRR7        KŸ  i ; i)	z Replay every SERVED secondary profile's ``processes.json`` under its own scope.
The launch profile's file was already read by ``recover_from_checkpoint`` above.r�   F)Ú_multiplex_profile_homesr+   rŸ   Nz1Process checkpoint recovery for profile %r failedTr‰   )rl   r¢   r.   r  r+   r6   r5   r7   r   Úrecover_from_checkpointr   rU   r�   )	ra   Úprocess_registryr  r+   r5   Úlaunch_homeÚ	recoveredÚprofile_nameÚprofile_homes	   &&       r&   Ú&_recover_secondary_process_checkpointsÚ:GatewayStartupMixin._recover_secondary_process_checkpointsq  sÓ   € ô �t—{‘{Ð$8¸%×@Ò@ÙßPÝ4Ù%Ó'×/Ñ/Ó1ˆØˆ	Ù*BÀ4Ç;Á;Ö*OÑ&ˆLÜ�LÓ!×)Ñ)Ó+¨{Ô:ÙðqÙ+¬D°Ó,>À×CÕCØ×!IÑ!IÓ!KÕK�I÷ DÑCñ	 +Pð Ð÷	 D×CÐCûäô qÜ—‘ÐRÐT`Ðko�×pðqús0   Á=CÂB<Â.CÂ<CÃCÃCÃ#C7Ã6C7c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   „  s   € ÷ 2Qñ 2Q°4ñ 2Qr(   c              ƒ  óš  "  € ^ RI Hp V P                  4        \        \        P
                  RRR7      ;_uu_ 4        ^ RIHp V P                  V! 4       4       RRR4       T P                  P                  4        \        \        P
                  R4      ;_uu_ 4        ^ RIHp VP                  4       pW@P                  V4      ,          pV'       d   \        P!                  R	V4       RRR4       \        \        P
                  R
4      ;_uu_ 4        ^ RIHp V! XP&                  4       RRR4       VR,          pVP)                  4       '       dO   \        P!                  R4        V P+                  V4      G Rj  x€L
 pT'       d   \        P!                  RT4       MEV P3                  4       G Rj  x€L
 w  ršWš,           '       d   \        P!                  RWš,           Wš4       \        \        P4                  R4      ;_uu_ 4        V P7                  4       pV'       d   \        P9                  RV4       RRR4       R#   + '       g   i     ELñ; i  + '       g   i     ELu; i  + '       g   i     ELF; i Lÿ  \,         d(   p\        P/                  RT4       \1        R4      ThRp?ii ; i Lÿ  + '       g   i     R# ; i5i)zPPlugins, relay, hooks, then crash/clean-exit recovery of processes and sessions.©Ú_hermes_homez"plugin re-wire subscription failedTr‰   )Úget_plugin_managerNzProcess checkpoint recovery: %s©r  z5Recovered %s background process(es) from previous runz2Could not restore async delegation completions: %s)Úrestore_undelivered_completionsz.clean_shutdownu?   Previous gateway exited cleanly â€” skipping session suspensionzrClean-start marker cleanup failed; refusing startup so the clean-exit receipt cannot mask a later unclean exit: %sz#clean-start recovery cleanup failedz>Discarded %d orphan active-turn marker(s) after clean shutdownz^Recovered %d interrupted turn(s) from previous run (%d to resume, %d reply(ies) owed delivery)zStuck-loop detection failed: %sz'Auto-suspended %d stuck-loop session(s))r.   r(  r  r   r¬   r­   r  r)  Ú_subscribe_plugin_rewireÚhooksÚdiscover_and_loadÚtools.process_registryr  r  r#  rU   rV   Útools.async_delegationr+  Úcompletion_queueÚexistsrú  r   r(  rN  r  r¹   Ú_suspend_stuck_loop_sessionsr�   )ra   r(  r)  r  r   r+  Ú_clean_markerrù  ré   r  r  Ústucks   &           r&   Ú_start_recover_previous_runÚ/GatewayStartupMixin._start_recover_previous_run„  s  é € å,Ø×0Ñ0Ô2äœWŸ_™_Ð.RÐ]a×bÖbÝ=Ø×)Ñ)Ñ*<Ó*>Ô?÷ cð 	�
‰
×$Ñ$Ô&ô œWŸ_™_Ð.O×PÕPÝ?Ø(×@Ñ@ÓBˆIØ×DÑDÐEUÓVÕVˆIßÜ—‘ÐSÐU^Ô_÷ Qô œWŸ_™_Ð.b×cÕcÝNÙ+Ð,<×,MÑ,MÔN÷ dð
 %Ð'8Õ8ˆØ×Ñ×!Ò!Ü�K‰KÐYÔZðSØ"&×"EÑ"EÀmÓ"T×T�	÷ Ü—‘Ð\Ð^gÔhøà&*×&DÑ&DÓ&F× FÑˆGØ×!Ô!Ü—‘ð%Ø&-Õ&8¸'ôô
 œWŸ]™]Ð,M×NÕNà×5Ñ5Ó7ˆEßÜ—‘ÐHÈ%ÔP÷	 OÑN÷S c×bÐbú÷ Q×PÐPú÷ d×cÐcúñ UøÜô SÜ—‘ðNØORôô #Ð#HÓIÈsÐRûðSúñ !G÷ O×NÐNüsµ   ‚;K½IÁAKÂAIÃ**KÄI*Ä-&KÅKÅ*J  Å>I>Å?J  ÆKÆ*KÆ5J5Æ6AKÈ	/J7È8
KÉI	É	KÉI'	É!	KÉ*I;	É5	KÉ>J  Ê J2Ê"J-Ê-J2Ê2KÊ7K	Ë	Kc               ó   € V ^8„  d   QhRR/# )r   r"   ztuple[bool, int, list, list]r$   )r%   s   "r&   r'   rL   ¸  s   € ÷ 7^ñ 7^Ð2Nñ 7^r(   c              ƒ  ó>  "  € ^ RI Hp ^ RIHp ^ pV P	                  4       p. p. pV P
                  P                  P                  4        EFÂ  w  rxV P                  4       G Rj  x€L
 '       d   RW5V3u # VP                  '       g   K?  V'       dB   V! Wx4      '       g4   \        P                  RVP                  4       VP                  V4       Kˆ  V^,          pV P                  Wx4      p	V	'       gõ   VP                  \        P                   P#                  4        U
u0 uF  qªP                  kK  	  up
9   d"   \        P%                  RVP                  4       M \        P%                  RVP                  4       V P'                  Wx4      pT P)                  VP                  V'       d   RMR	R
V! W{R7      RR7       V'       d!   V P+                  VRV4      V P,                  V&   EKž  V P/                  V	4       VP                  WxV	34       EKÅ  	  RW5V3#  EL³u up
i 5i)z–Create + wire an adapter per enabled platform (no connects). Returns
(aborted, enabled_platform_count, multiplex_skipped_platforms, pending_connects).)Ú_platform_has_bot_credential)Ú_adapter_unavailable_messageNTz–Skipping %s on default profile: no bot credential in this profile's secrets. Secondary multiplexed profiles that provide the token will still connect.zNo adapter available for %szpNo adapter for '%s' -- is the plugin installed? (platform is enabled in config.yaml but no plugin registered it)ÚretryingÚfatalÚadapter_unavailable)r<  )Úplatform_stateÚ
error_codeÚerror_messageÚneeds_attentionF)r.   r:  Úgateway.run_adaptersr;  Ú_multiplex_onr¢   rë  r!  rÕ  r�  rU   rV   rD   r~   Ú_create_adapterr   Ú__members__r‚  r�   Ú_adapter_may_healÚ_update_platform_runtime_statusrÈ  Ú_failed_platformsÚ_wire_adapter_handlers)ra   r:  r;  Úenabled_platform_countrD  Ú_multiplex_skipped_platformsÚ_pending_connectsrE   rÇ  re   r/  Úhealss   &           r&   Ú_start_prefilter_platformsÚ.GatewayStartupMixin._start_prefilter_platforms¸  sà  é € õ 	=ÝEØ!"ÐØ×*Ñ*Ó,ˆØ79Ð$ØÐØ)-¯©×)>Ñ)>×)DÑ)D×)FÑ%ˆHØ×>Ñ>Ó@×@Ö@ØÐ3ÐSdÐdÒdØ"×*×*Ð*Ù÷ Ñ%AÀ(×%\Ò%\Ü—‘ð<à=E¿^¹^ôð
 -×3Ñ3°HÔ=ÙØ" aÕ'Ð"Ø×*Ñ*¨8ÓEˆGßà—>‘>´x×7KÑ7K×7RÑ7RÔ7TÓ%UÑ7T°!§g¤gÑ7TÑ%UÔUÜ—N‘NÐ#@À(Ç.Á.ÕQä—N‘Nð[Ø\d×\jÑ\jôð ×.Ñ.¨xÓI�Ø×4Ñ4Ø—N‘NÇ±:ÈGØ4Ù">¸xÔ"XØ$(ð	 5ô ÷ Ø7;×7PÑ7PÐQYÐ[_ÐapÓ7q�D×*Ñ*¨8Ñ4Úð ×'Ñ'¨Ô0Ø×$Ñ$ hÀÐ%I×Jñ[ *Gð\ Ð,ÐL]Ð]Ð]ò[ Aùò, &Vùs8   ‚A HÁ"HÁ#	HÁ-HÂ	HÂBHÄHÄ2C$HÈHc               ó    € V ^8„  d   QhRRRR/# )r   rM  rÙ   r"   rz  r$   )r%   s   "r&   r'   rL   ñ  s   € ÷ +ñ +¸dð +À~ñ +r(   c              ƒ  óÔ  a "  € V 3R lpV'       g   . # V UUUu/ uF&  w  r4p\         P                  ! V! W4V4      4      W4V3bK(  	  pppp\        V4      pV'       dF   \         P                  ! VRR7      G Rj  x€L
 w  r‡V'       g   K4  S P	                  4       '       g   KL  M7V U	u. uF*  q™P                  4       ;'       g    V	P                  4       NK,  	  up	# V F  p	V	P                  4        K  	  \         P                  ! VRR/ G Rj  x€L
  V U	u. uFW  p	W—9  g   K  V	P                  4       '       d   K#  V	P                  4       e   K7  V	P                  4       ^,          R8X  g   KU  V	NKY  	  p
p	. VOV
O F7  p	S P                  Wi,          ^,          Wi,          ^ ,          4      G Rj  x€L
  K9  	  S P                  4       G Rj  x€L
  R# u upppi  EL]u up	i  LÑu up	i  L8 L5i)z¯Connect the pre-filtered adapters concurrently. Returns the raw per-platform results, or
None when a restart/shutdown aborted startup mid-connect (adapters already torn down).c              “  ón  <"  € SP                  W 4      G Rj  x€L
 '       d   WVRR3# \        P                  RV P                  4       SP	                  V P                  RRRR7        SP                  W 4      G Rj  x€L
 pYY'       d   RR3# RR3#  Lz L  \         d   pYTRT3u Rp?# Rp?ii ; i5i)	zCConnect a single platform; never let one block the others (#83791).NÚabortedzConnecting to %s...Ú
connecting©r?  r@  rA  rå   ÚokÚfailed)rÕ  rU   rV   rD   rH  Ú%_connect_initial_adapter_with_timeoutr   )r  Úp_cfgÚadprW  Ú_excra   s   &&&  €r&   Ú_connect_one_startupÚHGatewayStartupMixin._start_connect_pending.<locals>._connect_one_startupô  s¼   øé € à×>Ñ>¸sÓF×FÖFØ  y°$Ð7Ð7Ü�K‰KÐ-¨q¯w©wÔ7Ø×0Ñ0Ø—‘¨ÀÐUYð 1ô ð:Ø×EÑEÀcÓM×M�ð ˜E®2 4¸TÐBÐB°8¸TÐBÐBñ Gñ NøÜô :Ø  {°DÐ9Õ9ûð:üsW   ƒB5˜B™	B5£AB5Á)B Á=BÁ>B ÂB5ÂB ÂB2Â"B-Â'B2Â(B5Â-B2Â2B5gš™™™™™©?rÆ   NrÅ   TrW  )ro   r˜   rÀ   rÉ   r»  rå   re  rë  rÈ   rä   rÁ  rÕ  )ra   rM  r]  r  Úcrt  Ú	_task_mapÚ_pending_tasksÚ_doneÚ_tÚ_connected_oks   f&         r&   Ú_start_connect_pendingÚ*GatewayStartupMixin._start_connect_pendingñ  s¿  øé € õ	C÷ !ØˆIñ ^oõ
Ù]nÑPYÐQRÐWXŒG×!Ò!Ñ"6°q¸QÓ"?Ó@À1ÈÀ)ÒKÑ]nð 	ò 
ô ˜Y›ˆßÜ*1¯,ª,°~ÈtÔ*T×$TÑ!ˆEß‰~ $×"<Ñ"<×">Ô">Øá<EÓF¹I°b—L‘L“N×1Ð1 b§i¡i£kÒ1¹IÑFÐFã ˆBØ�I‰IŽKñ !ä�nŠn˜nÐEÀÑE×EÐEñ #ó
Ù"�2ØÑ'ô Ø02·±·ô ØCEÇ<Á<Ã>ô Ø^`×^gÑ^gÓ^iÐjkÕ^lÐptÑ^t÷ ˆB™ð 	ð 
ð 4�NÐ3 ]Ó3ˆBØ×0Ñ0°µ¸qÕ1AÀ9Å=ÐQRÕCSÓT×TÒTñ 4à×7Ñ7Ó9×9Ð9Ùùô-
ò
 %Uùò Gñ 	Fùò
ñ
 UÙ9ùsš   ƒG(š,GÁG(ÁG(Á8GÁ9G(Â	G(Â!G(Â&GÃGÃ5G(ÄGÄG(ÄGÄ!GÄ9GÅGÅ+GÅ1:G(Æ+G$Æ,G(ÇG&ÇG(ÇG(ÇG(Ç&G(c               ó$   € V ^8„  d   QhRRRRRR/# )r   rß   r\   Ústartup_retryable_errorsrÙ   r"   r#   r$   )r%   s   "r&   r'   rL     s)   € ÷ iñ iØ;>ðiØZ^ðià	ñir(   c                óÂ   € V P                  VP                  RRVR7       VP                  VP                   RV 24       V P                  WV4      V P                  V&   R# )zTMark a platform ``retrying`` with ``message`` and queue it in ``_failed_platforms``.r<  NrV  ú: )rH  rD   r~   rÈ  rI  )ra   rE   re   rÇ  rß   rh  s   &&&&&&r&   Ú _startup_queue_transient_failureÚ4GatewayStartupMixin._startup_queue_transient_failure  sc   € ð 	×,Ñ,Ø�N‰N¨:À$ÐV]ð 	-ô 	
ð 	!×'Ñ'¨8¯>©>Ð*:¸"¸W¸IÐ(FÔGØ+/×+DÑ+DÀXÐXgÓ+hˆ×Ñ˜xÓ(r(   c               ó(   € V ^8„  d   QhRRRRRRRR/# )r   Ú_rawrÙ   rh  Ústartup_nonretryable_errorsr"   r‡   r$   )r%   s   "r&   r'   rL   (  s,   € ÷ 9ñ 9Øð9Ø48ð9ØW[ð9à	ñ9r(   c           	   ƒ  óü  "  € ^ pV EFh  p\        V\        4      '       d   \        P                  RV4       K2  Vw  rgr‰p
V	R8X  d   KA  V	R8X  dZ   \        P                  RVP                  V
4       V P                  Wv4      G Rj  x€L
  V P                  WgV\        V
4      V4       K¡  V	R8X  d’   V P                  Wg4       V^,          pVP                  pT P                  VP                  V'       d   RMRRV'       d   VP                  MRR	7       \        P                  R
VP                  V'       d   RMR4       EK9  \        P                  RVP                  4       V P                  Wv4      G Rj  x€L
  VP                  '       g   V P                  WgVRV4       EK›  VP                  ;'       d    \!        VP"                  4      '       * pT P                  VP                  V'       d   RMRVP"                  VP$                  R	7       V'       d   TMTpVP'                  VP                   RVP$                   24       V'       g   EKG  V P)                  WgVRR7      V P*                  V&   EKk  	  V#  ELò EL5i)z†Apply connect outcomes to shared state single-threaded (exactly as the original serial
loop did); returns the connected adapter count.z$Unexpected startup connect error: %srT  rå   u   âœ— %s error: %sNrW  r<  Ú	connectedrV  u   âœ“ %s connected%sz (degraded)r  u   âœ— %s failed to connectzfailed to connectr=  rj  F)rÃ  )rm   r   rU   r(  rD   rÀ  rk  r\   Ú_publish_primary_adapterrl  rH  ÚDEGRADED_STATUS_MESSAGErV   r�   Úhas_fatal_errorÚfatal_error_retryabler   Úfatal_error_codeÚfatal_error_messager~   rÈ  rI  )ra   rn  rh  ro  Úconnected_countÚ_itemrE   re   rÇ  Úoutcomeré   Ú	_degradedÚ
_retryablerD  s   &&&&          r&   Ú _start_aggregate_connect_resultsÚ4GatewayStartupMixin._start_aggregate_connect_results(  s7  é € ð
 ˆÜˆEÜ˜%¤×+Ò+ä—‘ÐCÀUÔKÙØ?DÑ<ˆH˜¸Ø˜)Ô#ÙØ˜+Ô%Ü—‘Ð2°H·N±NÀCÔHð ×3Ñ3°GÓF×FÐFØ×5Ñ5Ø ¼¸C»ÐBZôñ Ø˜$ŒØ×-Ñ-¨hÔ@Ø 1Õ$�à#×6Ñ6�	Ø×4Ñ4Ø—N‘NÇ±:ÐP[ÐhlßEN '×"AÒ"AÐTXð 5ô ô —‘Ð3°X·^±^×V_Á]ÐegÔhÚä�N‰NÐ8¸(¿.¹.ÔIà×/Ñ/°ÓB×BÐBØ×*×*Ð*à×5Ñ5Ø Ð8KÐMeôò ð !×6Ñ6×sÐsÔ?YÐZa×ZrÑZrÓ?sÔ;sˆJØ×0Ñ0Ø—‘¿Z©zÈWØ"×3Ñ3À7×C^ÑC^ð 1ô ÷ 2<Ñ-ÐA\ˆFØ�M‰M˜XŸ^™^Ð,¨B¨w×/JÑ/JÐ.KÐLÔMßŠzØ37×3LÑ3LØ ¸uð 4Mó 4�×&Ñ& xÔ0ña ðf ÐòO Gò& CùsO   ‚BI<ÂI6ÂA9I<Ã?5I<Ä5?I<Å4I9Å5I<Æ)I<Æ58I<Ç.&I<È3I<É)I<É9I<c               ó    € V ^8„  d   QhRRRR/# )r   rö  r\   r"   r#   r$   )r%   s   "r&   r'   rL   c  s   € ÷ 2ñ 2°ð 2¸ñ 2r(   c                ól   € ^ RI Hp V! RVR7       \        V n        V P	                  V4       RV n        R# )zIRecord a fatal-config startup failure (exit 78) and request a clean exit.©rØ  rå  ræ  FN)r.   rØ  r   Ú
_exit_coderñ  rÚ   )ra   rö  rØ  s   && r&   Ú_startup_fail_fatal_configÚ.GatewayStartupMixin._startup_fail_fatal_configc  s.   € å;Ù#Ð2BÐPVÕWÜ8ˆŒØ× Ñ  Ô(Ø,1ˆÖ)r(   c               ó$   € V ^8„  d   QhRRRRRR/# )r   rx  r‡   rL  rÙ   r"   ztuple[bool, int]r$   )r%   s   "r&   r'   rL   k  s$   € ÷ #&ñ #&Ø"ð#&ØBFð#&à	ñ#&r(   c              ƒ  óJ  a"  € ^ RI Hp ^ RIHp VP	                  4         YP                  4       G Rj  x€L
 ,          pRT n
        T F•  o\        ;QJ d7    T3R	 lT P                  P                  4        4       F  '       g   K   RM,	  RM(! T3R	 lT P                  P                  4        4       4      '       d   Ku  \        P                  R
SP                   4       K—  	  T P#                  4        F  p\        P                  T4       K  	  RT3#  LÜ  T dO   p\        P                  R\        T4      4       T P                  \        T4      4       RT3u Rp?RT n
        # Rp?i\         d$   p\        P                  RTRR7        Rp?ELPRp?ii ; i  RT n
        i ; i5i)zTBring up multiplexed secondary-profile adapters. Returns (aborted, connected_count).)ÚMultiplexConfigErrorr*  Nz$Gateway multiplexer config error: %sTFz,Secondary-profile adapter startup failed: %sr‰   c              3  ó.   <"  € T F
  pSV9   x € K  	  R # 5iró   r$   )r  Ú_profile_mapÚ_skippeds   & €r&   r  Ú@GatewayStartupMixin._start_secondary_profiles.<locals>.<genexpr>…  s   øé € ÐdÑDc°L�x <Ö/ÓDcùs   ƒuÄ   %s is enabled but no profile (default or secondary) provided a bot credential for it â€” the platform is not being served. Add its token to the profile that should own it, or disable the platform.)r.   r‡  r/  r  Úrestore_completionsÚ!_start_secondary_profile_adaptersrU   r(  r\   rƒ  Ú _platform_lock_takeover_on_startr   r¦  r  r‚  r�   rD   Ú!_unserved_shared_ingress_warnings)ra   rx  rL  r‡  Ú_prr  Ú_linerŠ  s   &&&    @r&   Ú_start_secondary_profilesÚ-GatewayStartupMixin._start_secondary_profilesk  sL  øé € õ 	5ÝBð 	×ÑÔ!ð	:Ø×%KÑ%KÓ%M×MÕMˆOð 5:ˆDÔ1ó 5ˆHß“3ÔdÀD×DZÑDZ×DaÑDaÔDcÓd—3—3’3ÔdÀD×DZÑDZ×DaÑDaÔDcÓd×dÔdÜ—‘ð7à8@¿¹öñ 5ð ×;Ñ;Ö=ˆEÜ�N‰N˜5Ö!ñ >à�oÐ%Ð%ñ1  NøØ#ô 	)ä�L‰LÐ?ÄÀQÃÔHØ×+Ñ+¬C°«FÔ3Ø˜Ð(Ô(ð
 5:ˆDÕ1ûô	 ô 	[Ü�L‰LÐGÈÐUYˆL×ZÒZûð	[ûð 5:ˆDÕ1üs{   ƒF#¡D ´Dµ
D ¿AF#Â3F#Â=AF#ÄD ÄFÄ<E#ÅFÅF ÅF#Å#FÅ0FÅ1FÆ	F ÆFÆF Æ	F Æ F#c          
     ó,   € V ^8„  d   QhRRRRRRRRRR/# )	r   rx  r‡   rK  rh  rÙ   ro  r"   r!   r$   )r%   s   "r&   r'   rL   �  s=   € ÷ Gñ GØ"ðGØ<?ðGØ[_ðGà%)ðGð 
ñGr(   c                óÄ  € ^ RI Hp V^ 8w  dA   V'       d7   RV n        \        P	                  R\        V4      RP                  V4      4       R# V'       dC   V'       g;   RP                  V4      p\        P	                  RV4       V P                  V4       R# V'       d7   RV n        \        P	                  R\        V4      RP                  V4      4       V^ 8:  d-   \        P                  R4       \        P                  R	4       R# V'       d:   \        P                  R
\        V4      RP                  V4      4       V! RRR7       \        P                  RV4       R# )a  Log/degrade when a configured platform failed to start; return True when startup must exit.

The SHARED gate for every platform, not the api_server path: a configured platform that never
came up must leave a loud, observable trace (ERROR + a ``degraded`` runtime state) even while
sibling platforms serve normally. One WARNING next to "Gateway running with N platform(s)" let
a gateway with no API server at all look healthy for half an hour (api_server lost the bind
race against the gateway it was replacing, and nothing retried).
r�  TuÊ   %d configured platform(s) failed to start and are parked (fix the reported error, then `hermes gateway restart`): %s. The gateway is DEGRADED â€” it serves the remaining platform(s) with those unserved.z; Fz0Gateway hit a non-retryable startup conflict: %szf%d platform(s) fatally misconfigured and parked: %s. Staying alive so retryable platforms can recover.zNo messaging platforms enabled.z5Gateway will continue running for cron job execution.uS   Gateway started with no connected platforms â€” %d platform(s) queued for retry: %sr^   Nræ  a  No adapter could be created for any of the %d configured platform(s). Check that required dependencies are installed and credentials are set. Gateway will continue for cron job execution; platforms whose plugin may still register are queued for background retry.)
r.   rØ  rZ   rU   r(  rË   rw  rƒ  r�   rV   )ra   rx  rK  rh  ro  rØ  rö  s   &&&&&  r&   Ú_start_handle_no_connectionsÚ0GatewayStartupMixin._start_handle_no_connections�  s+  € õ 	<Ø˜aÔß*ð 26�Ô.Ü—‘ðAô Ð3Ó4°d·i±iÐ@[Ó6\ô	ñ ß&×/GØ—Y‘YÐ:Ó;ˆFÜ�L‰LÐKÈVÔTØ×+Ñ+¨FÔ3Ùß&ð .2ˆDÔ*Ü�L‰LðDäÐ/Ó0°$·)±)Ð<WÓ2Xôð " QÔ&Ü�N‰NÐ<Ô=Ü�K‰KÐOÔPÙß#ä�N‰NØeÜÐ,Ó-¨t¯y©yÐ9QÓ/Rôñ (°jÈdÕSô 	�‰ð
/ð 1Gô		
ñ r(   c               ó    € V ^8„  d   QhRRRR/# ©r   rx  r‡   r"   r#   r$   )r%   s   "r&   r'   rL   Ù  s   € ÷ !7ñ !7À#ð !7È$ñ !7r(   c           	   ƒ  óÞ  a	"  € ^ RI Ho	  V P                  4       G Rj  x€L
  T P                  V P                  R4       V P                  4        ^ RI	H
p V P                  4        V! V 4      G Rj  x€L
  \        V P                  P                  4      pV'       d   \        P                  RV4       V P                  P!                  R	R
V P"                   Uu. uF  qDP$                  NK  	  up/4      G Rj  x€L
  V^ 8”  d   \        P                  RV4       \'        \(        P*                  R4      ;_uu_ 4        ^ RIHp V! V P"                  4      G Rj  x€L
 p\1        R VP3                  R
/ 4      P5                  4        4       4      p\        P                  RV4       RRR4       V P7                  4       G Rj  x€L
 pV'       gU   \8        ;QJ d    V	3R lR 4       F  '       g   K   RM	  RM! V	3R lR 4       4      '       d   V P;                  4        R# R# R#  EL  \         d    \        P                  RRR7        EL$i ; i ELÛu upi  EL] Lÿ  + '       g   i     L¿; i L®5i)zPRoom worker, heartbeat, gateway:startup hook, channel directory, /update notice.r'  NznGroup Chat worker failed to start; mutating Group Chat commands will fail closed until supervision recovers itTr‰   Úhosted_room_worker)Úrestore_heartbeat_watchesz%s hook(s) loadedzgateway:startuprë  z#Gateway running with %s platform(s)z"Channel directory build failed: %s)Úbuild_channel_directoryc              3  ó8   "  € T F  p\        V4      x € K  	  R # 5iró   )rË   )r  Úchss   & r&   r  ÚCGatewayStartupMixin._start_post_connect_services.<locals>.<genexpr>ò  s   é € ÐWÑ/V¨œ3˜sŸ8˜8Ó/Vùó   ‚z%Channel directory built: %d target(s)c              3  óR   <"  € T F  pSV,          P                  4       x € K  	  R # 5iró   )r2  )r  rI  r(  s   & €r&   r  r   ö  s)   øé € ð  
áP�ð ˜DÕ ×(Ñ(×*Ð*ÛPùs   ƒ$'F)z.update_pending.jsonz.update_pending.claimed.json)r.   r(  rX  r   rU   r(  Ú_spawn_supervisedr^  rn  Úgateway.run_heartbeat_restorerœ  Ú_start_heartbeat_pollerrË   r-  Úloaded_hooksrV   Úemitr  rD   r   r¬   r­   Úgateway.channel_directoryr�  ÚsumrC   r‚  Ú_send_update_notificationr¦  Ú#_schedule_update_notification_watch)
ra   rx  rœ  Ú
hook_countr  r�  Ú	directoryÚch_countÚnotifiedr(  s
   &&       @r&   Ú_start_post_connect_servicesÚ0GatewayStartupMixin._start_post_connect_servicesÙ  sá  øé € å,ð	Ø×1Ñ1Ó3×3Ð3ð 	×Ñ˜t×?Ñ?ÐAUÔVØ×'Ñ'Ô)ÝKØ×$Ñ$Ô&Ù'¨Ó-×-Ð-Ü˜Ÿ™×0Ñ0Ó1ˆ
ßÜ�K‰KÐ+¨ZÔ8Ø�j‰j�o‰oÐ/°+ÐQU×Q^ÒQ^Ó?_ÑQ^ÈAÇÄÑQ^Ñ?_Ð1`Óa×aÐaØ˜QÔÜ�K‰KÐ=¸ÔOäœWŸ_™_Ð.R×SÕSÝIÙ5°d·m±mÓD×DˆIÜÑW¨y¯}©}¸[È"Ó/M×/TÑ/TÔ/VÓWÓWˆHÜ�K‰KÐ?ÀÔJ÷	 Tð ×7Ñ7Ó9×9ˆßŸC›Cô  
áPó 
ŸCŸCšCô  
áPó 
÷ 
ò 
ð ×4Ñ4Ö6ñ	
‰xò3 4øÜô 	Ü�L‰LðAØKOð ÷ ð	úò 	.ùò @`Òañ E÷ T×Súñ :ùs³   ƒI-‹H" žHŸH" £AI-Á0IÁ1A&I-ÃIÃ+I-Ã6IÃ7AI-Ä:IÅIÅA
IÆ!I-Æ<I+Æ=I-Ç	
I-ÇI-Ç+I-È	I-ÈH" È""IÉI-ÉIÉI-ÉI-ÉIÉI(	É#	I-c               ó    € V ^8„  d   QhRRRR/# r™  r$   )r%   s   "r&   r'   rL   ü  s   € ÷ 0+ñ 0+¸#ð 0+À$ñ 0+r(   c           
   ƒ  óŒ  a "  € ^ RI HpHp ^ RIHp S P                  V4      G Rj  x€L
  V^ 8”  d   \        P                  ! R4      G Rj  x€L
  V! 4       '       d   RS n        S P                  V! 4       R7      G Rj  x€L
  \        \        P                  R4      ;_uu_ 4        V! S 4       RRR4       S P                  4        S P                  4       G Rj  x€L
  ^ RIHp V! S 4      G Rj  x€L
  S P#                  4       G Rj  x€L
  ^ R	IHp V! S \        P(                  ! 4       4       \        \        P*                  R
4      ;_uu_ 4        ^ RIHp VP0                  p. Vn        \3        V4       F…  w  ršS P5                  V
3V 3R llRV
P7                  R4       2RR7       \8        P;                  RV
P7                  R4      4       V	^d,          ^c8X  g   Kg  \        P                  ! ^ 4      G Rj  x€L
  K‡  	  RRR4       R#  ELâ ELÀ EL�  + '       g   i     ELl; i ELL EL9 EL$ L8  + '       g   i     R# ; i5i)zWPost-connect wiring: services, boot notifications, startup restore, recovered watchers.)Ú%_planned_restart_notification_pendingÚ_restart_notification_pending)Úrecover_gateway_pendingNrÿ  T)rî   z#Pending-message recovery failed: %s)Úrecover_gateway_native_sessions)Úinstall_cron_store_noticesz!Recovered watcher setup error: %sr*  c                ó&   <€ SP                  V 4      # ró   )Ú_run_process_watcher)Úwra   s   &€r&   r  Ú:GatewayStartupMixin._start_finish_wiring.<locals>.<lambda>'  s   ø€  d×&?Ñ&?ÀÔ&Br(   zprocess_watcher:rž  F)rÌ  z(Resumed watcher for recovered process %s)r.   r´  rµ  Úgateway.shutdown_flushr¶  r°  ro   r]  Ú_booted_from_restartrý   r   r¬   r­   r³  rÜ   Úgateway.run_runtimer·  Ú&_send_session_db_warning_notificationsÚgateway.cron_store_noticesr¸  r¡   ÚERRORr/  r  Úpending_watchersÚ	enumerater£  rC   rU   rV   )ra   rx  r´  rµ  r¶  r·  r¸  r  ÚwatchersÚiÚwatchers   f&         r&   Ú_start_finish_wiringÚ(GatewayStartupMixin._start_finish_wiringü  s×  øé € çdÝBØ×/Ñ/°Ó@×@Ð@à˜QÔÜ—-’- Ó$×$Ð$ñ )×*Ò*Ø(,ˆDÔ%ð
 ×,Ñ,Ù1VÓ1Xð -ó 
÷ 	
ð 	
ô œWŸ_™_Ð.S×TÕTÙ# DÔ)÷ Uð 	×.Ñ.Ô0Ø×*Ñ*Ó,×,Ð,ÝGÙ-¨dÓ3×3Ð3ð ×9Ñ9Ó;×;Ð;ÝIÙ" 4¬×)AÒ)AÓ)CÔDô œWŸ]™]Ð,O×PÕPÝ?Ø'×8Ñ8ˆHØ02ÐÔ-Ü'¨Ö1‘
�Ø×&Ñ&Ø$ÖBØ& w§{¡{°<Ó'@Ð&AÐBÈEð 'ô ô —‘ÐFÈÏÉÐT`ÓHaÔbØ�s•7˜b–=Ü!Ÿ-š-¨Ó*×*Ò*ñ 2÷	 QÑPòC 	Aò %ò	
÷ U×TÐTúò
 	-â3ò 	<ñ  +÷ Q×PÐPüs³   ƒ#I¦H§$IÁHÁIÁ!IÁ>HÁ?&IÂ%	HÂ.+IÃH%ÃIÃ/H(Ã0IÄH+ÄAIÅBH0ÇH0Ç5H.
Ç6H0Ç>IÈIÈIÈH"	È
IÈ(IÈ+IÈ.H0È0I	È;	Ic               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   8  s   € ÷ Uñ U°$ñ Ur(   c                óN  a a€ S P                    F&  pS P                  \        S V4      VR,          4       K(  	  S P                  '       dK   \        P                  R\        S P                  4      RP                  R S P                   4       4      4       S P                  4        S P                   F&  pS P                  \        S V4      VR,          4       K(  	  ^ RI
Ho S P                  VV 3R lR4        S P                  4       '       dB   \        P                  RS P                  4       4       S P                  S P                  R	4       MS P                  4         S P                  S P$                  R4       R#   \          d    \        P#                  R
RR7        LBi ; i)z4Spawn the long-lived supervised background watchers.:é   NNz;Starting reconnection watcher for %d failed platform(s): %sz, c              3  ó8   "  € T F  qP                   x € K  	  R # 5iró   r  rÐ  s   & r&   r  ÚGGatewayStartupMixin._start_spawn_background_watchers.<locals>.<genexpr>?  s   é € Ð6_ÑH^À1·w¶wÓH^ùr¡  )Úruntime_downgrade_watcherc                 ó   <€ S ! S4      # ró   r$   )rÏ  ra   s   €€r&   r  ÚFGatewayStartupMixin._start_spawn_background_watchers.<locals>.<lambda>G  s   ø€ Ñ'@ÀÔ'Fr(   rÏ  u?   scale-to-zero: armed (idle timeout %.0fs) â€” watching for idleÚscale_to_zero_watcherz*scale-to-zero: arm check failed at startupTr‰   Údrain_control_watcherN)Ú_PRE_RECONNECT_WATCHERSr£  rl   rI  rU   rV   rË   rw  Ú_spawn_reconnect_watcherÚ_POST_RECONNECT_WATCHERSÚgateway.runtime_downgrade_exitrÏ  Ú_scale_to_zero_should_armÚ#_scale_to_zero_idle_timeout_secondsÚ_scale_to_zero_watcherÚ#_log_scale_to_zero_not_armed_reasonr   r�   Ú_drain_control_watcher)ra   rï  rÏ  s   f @r&   Ú _start_spawn_background_watchersÚ4GatewayStartupMixin._start_spawn_background_watchers8  sQ  ù€ à×2Ô2ˆFØ×"Ñ"¤7¨4°Ó#8¸&À½*ÖEñ 3à×!×!Ð!Ü�K‰KØMÜ�D×*Ñ*Ó+¨T¯Y©YÑ6_È×H^ÒH^Ó6_Ó-_ôð 	×%Ñ%Ô'Ø×3Ô3ˆFØ×"Ñ"¤7¨4°Ó#8¸&À½*ÖEñ 4åLØ×ÑÕFÐHcÔdð	VØ×-Ñ-×/Ò/Ü—‘ØUØ×<Ñ<Ó>ôð ×&Ñ& t×'BÑ'BÐD[Õ\ð ×8Ñ8Õ:ð
 	×Ñ˜t×:Ñ:Ð<SÖTøô	 ô 	VÜ�L‰LÐEÐPTˆLÖUð	Vús   Ã9E? ÄA E? ÅE? Å?"F$Æ#F$c               ó   € V ^8„  d   QhRR/# r2   r$   )r%   s   "r&   r'   rL   Z  s   € ÷ Uñ U¨tñ Ur(   c               ƒ  óÎ   "  €  ^ RI Hp  V ! RR7      G Rj  x€L
 '       g   \        P                  R4       R# R#  L#  \         d    \        P                  RRR7        R# i ; i5i)	zLBound startup on the latest diagnostic snapshot, never on filesystem health.©Úflush_runtime_status_asyncr”  rÆ   Nz/Timed out flushing final startup runtime statusz)Final startup runtime-status flush failedTr‰   )rª  râ  rU   r�   r   r�   rá  s    r&   Ú_start_flush_runtime_statusÚ/GatewayStartupMixin._start_flush_runtime_statusY  sP   é € ð	UÝAÙ3¸CÔ@×@Ö@Ü—‘ÐPÖQó Aøäô 	UÜ�L‰LÐDÈtˆL×Tð	Uüs5   ‚A%„< –:—	< ¡< ¶A%º< ¼"A"ÁA%Á!A"Á"A%c               ó   € V ^8„  d   QhRR/# r¶  r$   )r%   s   "r&   r'   rL   c  s   € ÷ 5ñ 5˜Tñ 5r(   c              ƒ  ó°   "  €  V P                  4       G Rj  x€L
 V P                  4       G Rj  x€L
  #  L L  T P                  4       G Rj  x€L 
  i ; i5i)z7Start the gateway and all configured platform adapters.N)Ú_start_implrã  r`   s   &r&   ÚstartÚGatewayStartupMixin.startc  sI   é € ð	5Ø×)Ñ)Ó+×+ð ×2Ñ2Ó4×4Ñ4ñ	 ,ñ 5ø�$×2Ñ2Ó4×4Ò4üs?   ‚A„8 —4˜8 ›A®6¯A´8 ¶A¸AÁAÁAÁAc               ó   € V ^8„  d   QhRR/# r¶  r$   )r%   s   "r&   r'   rL   l  s   € ÷ ;ñ ; 4ñ ;r(   c              ƒ  	ó  "  € \         P                  R 4       V P                  4        V P                  4       G Rj  x€L
  V P	                  4       G Rj  x€L
 '       d   R# V P                  4       '       d   R# V P                  4       G Rj  x€L
  RV n        . V n        . V n	        V P                  4        . p. pRV n        V P                  4       G Rj  x€L
 w  r4rVV'       d   R# V P	                  4       G Rj  x€L
 '       d   R# V P                  V4      G Rj  x€L
 pVf   R# V P                  WrV4      G Rj  x€L
 pV P	                  4       G Rj  x€L
 '       d   R# V P                  W…4      G Rj  x€L
 w  r8V'       d   R# V P!                  W„W!4      '       d   R# V P	                  4       G Rj  x€L
 '       d   R# V P"                  V P$                  n        V P'                  4        RV n        V P+                  4        V P-                  V P/                  4       4       V P1                  V4      G Rj  x€L
  V P3                  4        ^ RIHp	 V	! RRR7       \         P                  R4       R#  EL3 EL ELé EL¤ EL‚ ELd ELG EL2 EL LØ LX5i)zStarting Hermes Gateway...NTF)Úrecord_process_readyÚgateway_boot)rN  zPress Ctrl+C to stop)rU   rV   rŠ  r±  rÕ  rø  r6  rÚ   r|   rØ   rš   rZ   rO  re  r}  r’  r–  r  Údelivery_routerÚ_wire_teams_pipeline_runtimer6  Ú _install_plugin_message_injectorÚ_update_runtime_statusrb   rÈ  rÝ  Ú/hermes_cli.observability.shared_metrics_startuprì  )
ra   ro  rh  Ú_abortedrK  rL  rM  rn  rx  rì  s
   &         r&   rç  ÚGatewayStartupMixin._start_impll  s;  é € Ü�‰Ð0Ô1Ø×(Ñ(Ô*Ø×1Ñ1Ó3×3Ð3Ø×:Ñ:Ó<×<Ö<ÙØ×*Ñ*×,Ò,ÙØ×.Ñ.Ó0×0Ð0ð -1ˆÔ)Ø&(ˆÔ#Ø&(ˆÔ#ð 	×"Ñ"Ô$Ø13Ð#Ø.0Ð Ø).ˆÔ&ð ×1Ñ1Ó3×3ñ	
ØÐ.JçÙØ×:Ñ:Ó<×<Ö<ÙØ×0Ñ0Ð1BÓC×CˆØŠ<ÙØ $× EÑ EØÐ,Gó!
÷ 
ˆð ×:Ñ:Ó<×<Ö<ÙØ*.×*HÑ*HØó+
÷ %
Ñ!ˆ÷ ÙØ×,Ñ,ØÐ5M÷
ò 
ñ Ø×:Ñ:Ó<×<Ö<ÙØ(,¯©ˆ×ÑÔ%Ø×)Ñ)Ô+ØˆŒØ×-Ñ-Ô/ð 	×#Ñ# D×$7Ñ$7Ó$9Ô:Ø×'Ñ'¨Ó8×8Ð8Ø×-Ñ-Ô/ÝXÙ˜^¸Õ=Ü�‰Ð*Ô+Ùòq 	4Ú<ò 	1ò 4ò =âCò
ò =ò%
ñ =ñ 	9ùsã   ‚9J»I.¼JÁI1Á	JÁJÁ6JÂI4ÂAJÃI7Ã$JÃ8I:Ã9	JÄJÄI=ÄJÄ9J Ä:JÅJÅ	JÅJÅ2JÅ3=JÆ0J	Æ1	JÆ;A7JÈ2JÈ3<JÉ1JÉ4JÉ7JÉ:JÉ=JÊ JÊJÊJÊ	JÊJc                  ól   € ] tR tRt$ RtR]R&   R]R&   R]R&   R]R	&   R]R
&   R]R&   R]R&   R]R&   RtR# )Ú'GatewayStartupMixin._HandoffDestinationi©  z)Resolved destination for one handoff row.r   rE   r\   Úplatform_namer   Ú	transportr    Úhome_chat_idr0  Úeffective_thread_idr   r€   Úhandoff_configr$   N)r    Ú
__module__Ú__qualname__Ú__firstlineno__Ú__doc__Ú__annotations__Ú__static_attributes__r$   r(   r&   Ú_HandoffDestinationrö  ©  s3   ‡ á7ØÓØÓØ‹Ø‹	ØÓØ*Ó*ØÓØ×r(   r  c               ó   € V ^8„  d   QhRR/# )r   r!  r0  r$   )r%   s   "r&   r'   rL   µ  s   € ÷ fñ f°=ñ fr(   c                ób  € ^ RI Hp V'       d   VR8X  d   V P                  V P                  3# V P                  ;'       g    / P                  V4      pV'       g   \        RV R24      h V! 4       V3#   \         d0   p\        P                  RTRR7       \        RT R	T 24      ThR
p?ii ; i)uû   Return (config, adapters) for the profile that queued the handoff. For a secondary
profile the watcher already entered _profile_runtime_scope, so a fresh load resolves THAT
profile's config; fail closed â€” self.config would deliver to the WRONG chat.)Úload_gateway_configr  z	profile 'z&' has no live adapters in this gatewayzqHandoff: could not load config for profile %s; failing the handoff instead of delivering via the primary's configTr‰   z#could not load config for profile 'z': N)
r.   r  r¢   r  r  rC   rN  r   rU   r(  )ra   r!  r  Ú	secondaryré   s   &&   r&   Ú_handoff_resolve_scopeÚ*GatewayStartupMixin._handoff_resolve_scopeµ  s¼   € õ 	4ß˜|¨yÔ8Ø—;‘; §¡Ð-Ð-Ø×+Ñ+×1Ð1¨r×6Ñ6°|ÓDˆ	ßÜ ¨<¨.Ð8^Ð_Ó`Ð`ð	fÙ&Ó(¨)Ð3Ð3øÜô 	fÜ�L‰Lð6Ø7CÈdð ô ô Ð!DÀ\ÀNÐRUÐVYÐUZÐ[Ó\ÐbeÐeûð	fús   Á+A4 Á4B.Á?*B)Â)B.c               ó$   € V ^8„  d   QhRRRRRR/# )r   r  údict[str, Any]r!  r0  r"   rö  r$   )r%   s   "r&   r'   rL   È  s)   € ÷ J
ñ J
Ø!ðJ
Ø1>ðJ
à	0ñJ
r(   c              ƒ  óÀ  "  € ^ RI Hp VR,          pVP                  R4      ;'       g    RP                  4       P	                  4       pV'       g   \        R4      h \        V4      pT P                  T4      w  rxT! YgT4      p	T	'       g   \        RT R	24      hTP                  T4      p
T
'       d   T
P                  '       g   \        R
T R24      h\        T
P                  4      pTP                  R4      ;'       g
    TR,          p T	P                  P                  T\        RTR7      4      G Rj  x€L
 pT;'       g*    T
P&                  '       d   \        T
P&                  4      MRpT\        P(                  8H  ;'       d    \+        T4      p\-        T4      ;'       d    T'       * pT'       d   RMRpRpT\        P(                  8X  d   T'       g   RpT\        P.                  8X  db   TP1                  R4      '       d   RMRp\3        T	P                  RR4      pT
P4                  ;'       g    \7        T4      '       d	   T! T4      MRpT\        P8                  8X  d/   T P;                  T	P                  T4      G Rj  x€L
 '       d   RMRp\=        TT'       d)   T\        P>                  8X  d   T'       d   \        T4      MTT
P@                  TT'       d   TMRRYòTR7	      pT PC                  YeYšY¿TTR7      #   \        \        3 d    \        RT R24      hi ; i ELï  \          d&   p\"        P%                  RY^RR7       Rp Rp?ELRp?ii ; i LÕ5i)zSResolve platform, transport, home channel, thread and destination source for a row.)Úresolve_delivery_transportÚidÚhandoff_platformr  zhandoff_platform is emptyzunknown platform 'Ú'z
platform 'z' is not active in this gatewayzno home channel configured for z(; run /sethome on the desired chat firstÚtitleºNé   Nz$gateway.startup.handoff_thread_title)r  Nz/Handoff: create_handoff_thread raised on %s: %sTr‰   ÚthreadÚdmÚgroupÚDÚscope_id_for_chatzsystem:handoffÚHandoff)	rE   r�   Ú	chat_nameÚ	chat_typeÚuser_idÚ	user_namer^  r.  Úscope_id)rE   r÷  rø  r    rù  rú  r€   rû  )"Úgateway.deliveryr  rC   r?  r¨  rN  r   r…  ÚKeyErrorr  Úget_home_channelr�   r\   re   Úcreate_handoff_threadr   r   rU   r�   r^  ÚTELEGRAMr	   r!   ÚSLACKÚ
startswithrl   r  ÚcallableÚMATRIXÚ_handoff_home_is_dmr   ÚDISCORDrI  r  )ra   r  r!  r  Úcli_session_idr÷  rE   rû  Úhandoff_adaptersrø  r    rù  Ú	cli_titleÚnew_thread_idré   rú  Úis_telegram_private_chatÚ	is_threadr  r  Úscope_for_chatÚdest_sources   &&&                   r&   Ú_handoff_resolve_destinationÚ0GatewayStartupMixin._handoff_resolve_destinationÈ  s  é € õ 	@Ø˜T�ˆØŸ™Ð!3Ó4×:Ð:¸×AÑAÓC×IÑIÓKˆßÜÐ:Ó;Ð;ð	FÜ Ó.ˆHð ,0×+FÑ+FÀ|Ó+TÑ(ˆñ /¨xÐIYÓZˆ	ßÜ ¨M¨?Ð:YÐZÓ[Ð[Ø×.Ñ.¨xÓ8ˆß˜4Ÿ<Ÿ<˜<ÜØ1°-°Ð@hÐióð ô ˜4Ÿ<™<Ó(ˆà—G‘G˜GÓ$×:Ð:¨°rÕ(:ˆ	ð	!Ø"+×"3Ñ"3×"IÑ"IØœaÐ FÈiÔXó#÷ ˆMð ,×`Ð`ÀtÇ~Ç~À~´°D·N±NÔ0CÐ[_Ðð œ×)Ñ)Ñ)×_Ð_Ô.QÐR^Ó._ð 	!ô ˜Ó'×HÐHÐ0HÔ,Hˆ	ß )‘H¨tˆ	ØˆØ”x×(Ñ(Ô(×1Ið  ˆIØ”x—~‘~Ô%ð !-× 7Ñ 7¸× <Ò <™À'ˆIÜ$ Y×%6Ñ%6Ð8KÈTÓRˆNØ—}‘}×lÐlÌÐR`×IaÒIa©¸Ô)EÐgkˆHØ”x—‘Ô&ð '+×&>Ñ&>¸y×?PÑ?PÐR^Ó&_× _Ö _™ÐelˆIä#Øç˜h¬(×*:Ñ*:Ô:×?Rô Ð+Ô,àØ—i‘iØß$<‘LÐBRØÐ+>Øô

ˆð ×'Ñ'ØÀiØ%ÐWbØ)ð (ó 
ð 	
øôw œHÐ%ô 	FÜÐ!3°M°?À!ÐDÓEÐEð	Fúò"øô ô 	!Ü�L‰LÐJÈMÐimˆLÔnØ ŽMûð	!úñ4 !`ùsÂ   ‚AMÁMÁL Á(AMÂ4MÃ;MÄ
MÄ*L) Ä7L&Ä8L) Ä<MÅMÅ0MÆ	MÆ'MÆ7"MÇ-MÈ-MÈ6AMÊMÊ	MÊ.MË MË "MÌ!L#Ì#MÌ&L) Ì)MÌ4MÍMÍMÍMc               ó    € V ^8„  d   QhRRRR/# )r   rù  r\   r"   r!   r$   )r%   s   "r&   r'   rL     s   € ÷ Cñ C¸ð CÀñ Cr(   c              ƒ  óî   "  €  V P                  V4      G Rj  x€L
 p\	        T\
        4      ;'       d    TP                  R4      R8H  #  L0  \         d    \        P                  RTRR7        R# i ; i5i)uŽ   Whether the home chat is a DM by the adapter's own ``get_chat_info`` (``type: "dm"``);
unknown/failed â†’ not a DM, the common handoff target.Nz$Handoff: get_chat_info failed for %sTr‰   Frç   r  )Úget_chat_infor   rU   r�   rm   rn   rC   )re   rù  rV   s   && r&   r'  Ú'GatewayStartupMixin._handoff_home_is_dm  sl   é € ð	Ø ×.Ñ.¨|Ó<×<ˆDô ˜$¤Ó%×BÐB¨$¯(©(°6Ó*:¸dÑ*BÐBñ	 =øÜô 	Ü�L‰LÐ?ÀÐX\ˆLÔ]Úð	üs<   ‚A5„A ˜A	™A �A5´A5Á	A Á#A2Á.A5Á1A2Á2A5c               ó    € V ^8„  d   QhRRRR/# )r   r!  r0  r"   r\   r$   )r%   s   "r&   r'   rL     s   € ÷ 
ñ 
°}ð 
Èñ 
r(   c                ó|  € VP                   P                  P                  VP                  4      pV'       d   VP                  M/ pV'       d
   VR8w  d   TMRpVf�    \        V P                  RV P                  4      p\        VRR4      p\        V4      '       dA   V! VP                  4      p\        V\        4      '       d   VP                  4       '       d   Tp\        VP                  VP                  RR4      VP                  R	R
4      VR7      #   \         d    \        P                  RRR7        L]i ; i)a€  Destination session_key by the adapters' own rules. Thread keys omit user_id so the next
message shares it. Namespaced to the queuing profile (else a multiplexed gateway builds
``agent:main:...`` while the profile's adapter routes on ``agent:<profile>:...``); the store
resolver is only the root fallback. The isinstance check is load-bearing: a Mock store returns
a truthy MagicMock.r  NÚ_storeÚ_resolve_profile_for_keyz,Handoff: could not resolve profile namespaceTr‰   Úgroup_sessions_per_userÚthread_sessions_per_userF)r;  r<  r.  )rû  rë  rC   rE   Úextrarl   r  r%  r€   rm   r\   r?  r   rU   r�   r   )	ra   Údestr!  Úplatform_cfgr=  Úhandoff_profileÚstoreÚresolverÚresolveds	   &&&      r&   Ú_handoff_session_keyÚ(GatewayStartupMixin._handoff_session_key  s  € ð ×*Ñ*×4Ñ4×8Ñ8¸¿¹ÓGˆß&2�×"Ò"¸ˆß+7¸LÈIÔ<U™,Ð\`ˆØÒ"ð
\Ü × 8Ñ 8¸(ÀD×D\ÑD\Ó]�Ü" 5Ð*DÀdÓK�ô ˜H×%Ò%Ù'¨¯©Ó4�HÜ! (¬C×0Ò0°X·^±^×5EÒ5EØ*2˜ô !Ø�K‰K°·±Ð;TÐVZÓ1[Ø%*§Y¡YÐ/IÈ5Ó%QÐ[jô
ð 	
øô ô \Ü—‘ÐKÐVZ�Ö[ð\ús   ÁA<D ÃD Ä"D;Ä:D;c               ó$   € V ^8„  d   QhRRRRRR/# )r   r  r
  r!  r0  r"   r#   r$   )r%   s   "r&   r'   rL   9  s'   € ÷ 2Nñ 2N¨.ð 2NÈð 2NÐaeñ 2Nr(   c              ƒ  óZ  "  € VR,          pV P                  W4      G Rj  x€L
 pV P                  WB4      pV P                  P                  VP                  4      G Rj  x€L
  V P                  P                  WSRR7      G Rj  x€L
 pVf   \        RV RV 24      hV P                  V4       V P                  V4       VP                  R4      ;'       g
    VR,          p\        R	V R
2VP                  RR7      p\        P                  RW4P                  VP                  P                  VP                   V4       V P#                  V4      G Rj  x€L
 p	V	'       g   R# VP                   '       d   RVP                   /MRp
 VP$                  P'                  VP(                  \+        VP                  P                  4      Wš4      G Rj  x€L
 p\/        TRR4      '       g   \        R\1        T4       24      hR#  ELÜ EL¡ EL L² L;  \,         d   p\        RT 24      ThRp?ii ; i5i)u  Execute one handoff row; raises on failure (caller marks failed). ``profile_name`` (None =
root) is the profile whose store queued it â€” load-bearing under multiplex: secondaries live in
``_profile_adapters`` and the key must be namespaced ``agent:<profile>:...`` or nobody reads it.r  NF)Úpreserve_prompt_pinzcould not switch session key u    â†’ r  r  z([Session was just handed off from CLI ("z¿") to this channel. The full prior conversation history is loaded above. Briefly confirm you're working here and summarize what we were working on, so the user can continue from this device.]T)r¢  r€   r¤  ub   Handoff: dispatching synthetic turn for CLI session %s â†’ %s (home=%s, thread=%s, session_key=%s)r^  zadapter.send failed: r`  )r1  rD  r  Úget_or_create_sessionr€   Úswitch_sessionrN  Ú_evict_cached_agentrt   rC   r   rU   rV   r÷  r    r�   rú  Ú_handle_messagerø  rc  rE   r\   r   rl   r   )ra   r  r!  r)  r>  rg   Úswitchedr+  Úsynthetic_eventÚresponse_textÚsend_metadatare  ré   s   &&&          r&   Ú_process_handoffÚ$GatewayStartupMixin._process_handoff9  s  é € ð ˜T�ˆØ×6Ñ6°sÓI×IˆØ×/Ñ/°ÓCˆà×&Ñ&×<Ñ<¸T¿[¹[ÓI×IÐIà×1Ñ1×@Ñ@Ø¸Uð Aó 
÷ 
ˆð ÒÜÐ!>¸{¸mÈ5ÐQ_ÐP`ÐaÓbÐbð 	× Ñ  Ô-Ø×)Ñ)¨+Ô6Ø—G‘G˜GÓ$×:Ð:¨°rÕ(:ˆ	Ü&à;¸I¸;ð GJð Kð
 —;‘;Øô	
ˆô 	�‰ð3à×.Ñ.°·	±	×0AÑ0AÀ4×C[ÑC[Ð]hô	
ð #×2Ñ2°?ÓC×Cˆßáð DH×C[×C[ÐC[˜ d×&>Ñ&>Ñ?Ðaeˆð	GØŸ>™>×.Ñ.Ø—‘œs 4§9¡9×#4Ñ#4Ó5°}ó÷ ˆFô
 �v˜y¨$×/Ò/ÜÐ!6´{À6Ó7JÐ6KÐLÓMÐMñ 0òY Jò 	Jò
ñ4 Dñøô ô 	GÜÐ!6°s°eÐ<Ó=À3ÐFûð	Güs�   ‚H+ G<¡=H+ÁG?Á$H+ÂHÂAH+ÃA;H+ÅHÅH+ÅH+Å3H+ÆAH	 ÇHÇH	 Ç-H+Ç?H+ÈH+ÈH+ÈH	 È	H(ÈH#È#H(È(H+)r¾  r‚  r4  rK  r¬  r£  rÜ  rì  rÝ  rŽ  r6  rZ   rÚ   r|   rØ   r—   )rl  ró   )NN)rÿ  )g      @)r"  r(  ÚWHATSAPPÚWHATSAPP_CLOUDr#  ÚSIGNALÚEMAILÚSMSÚ
MATTERMOSTr&  ÚDINGTALKÚFEISHUÚWECOMÚWECOM_CALLBACKÚWEIXINÚBLUEBUBBLESÚQQÚYUANBAO)ÚSIGNAL_GROUP_ALLOWED_USERSÚTELEGRAM_GROUP_ALLOWED_USERSÚTELEGRAM_GROUP_ALLOWED_CHATSÚGATEWAY_ALLOWED_USERS)Ú_session_housekeeping_watcherÚ_model_catalog_refresh_watcherÚ_session_stall_watcherÚ_kanban_notifier_watcherÚ_kanban_dispatcher_watcher)Ú_handoff_watcherÚ_async_delegation_watcherÚ_loop_wakeup_watcherÚ_profile_reconcile_watcher)Zr    rü  rý  rþ  rÿ  ÚstaticmethodrX   rZ   r   rb   rx   rƒ   r‘   rš   r§   r™   r»   r¬   r­   r¸   rÜ   rÍ   rý   r  rú   r,  rO  rS  rö   rb  rr  r>  r�  r•  r³  r»  rÁ  rÈ  rÕ  rç  rò  rú  r  r  r  rR  rX  r^  rd  rn  rz  rŠ  r±  r§  r¦  Ú_ALLOWLIST_ENV_PLATFORMSÚtuplerç  rè  rø  r  r  r¹   r  r#  r6  rO  re  rk  r}  rƒ  r’  r–  r°  rÈ  rÔ  rÖ  rÝ  rã  rè  rç  ÚdataclassesÚ	dataclassr  r  r1  r'  rD  rQ  r  r$   r(   r&   rJ   rJ   N   s  ‡ ÙQàôMó ðMð ',Ð˜tÓ+õKõ?õ$õõ8[òHõ&õ
ð"à—_‘_ðà49÷õ,`ðB ð
¸W¿_¹_ö 
ó ð
õ
ð>Ø8=÷õ*)ðV ö
@ó ð
@ð-2Èt÷ -2õ^Uõ-õ^õ8bð
CØ>B÷C÷:õ:÷8õtZõ?ðtÐY]÷ t÷õ&^õ@-õõ!õ!õF!{ðF ñó ðòL÷*÷aõ/ò,^õõ*@fõDVõð. Ð÷
 #( %Ñ'_ÑF^Ó'_§%¡%Ñ'_ÑF^Ó'_Ó"_ð cõ #Ð÷ $˜eÑ#]ÑD\Ó#]Ÿe™eÑ#]ÑD\Ó#]Ó]Ðõ,ð\ ôDó ðDð2 ôdó ðdð$ ðCÀwÇ}Á}ö Có ðCõ&õ&2Qõh7^õr+õZiõ9õv2õ#&õJGõR!7õF0+ðhÐð ÐõUðB ôUó ðUõ5õ;ðz ×Ñ÷	ð 	ó ð	õfõ&J
ðX ôCó ðCõ
÷42Nó 2Nr(   rJ   )7rÿ  Ú
__future__r   ro   rq  rƒ  r¬   rS   r‡  r®   Ú
contextlibr   r   Úcontextvarsr   Úpathlibr   Ú
agent.i18nr   Úgateway.configr   r  r	   r7  r
   Úgateway.platforms.eventr   r   Úgateway.sessionr   r   Úgateway.restartr   r   r   Úgateway.run_shutdownr   r   rä  r   r   r   r   r   Útypingr   r   r   r   Ú	getLoggerrU   r0   r9   rH   rJ   r$   r(   r&   Ú<module>r     s—   ðñõ #ã Û Û Û Û 	Û Û ß ,Ý $Ý Ý Ý #Ý @Ý 6ß =ß <÷ñ ÷ >÷õ ÷ .Ó -ð 
×	Ò	˜=Ó	)€ðÀ÷ õ
#õG÷]Nó ]Nr(   