11# protolink/registry/registry.py
2+ import time
23from typing import Any
34
45from protolink .client import RegistryClient
56from protolink .models import AgentCard
7+ from protolink .server import RegistryServer
68from protolink .transport import HTTPRegistryTransport , RegistryTransport
79from protolink .utils .logging import get_logger
10+ from protolink .utils .renderers import to_registry_status_html
811
912
1013class Registry :
@@ -28,49 +31,66 @@ def __init__(self, transport: RegistryTransport | None = None, url: str | None =
2831
2932 # Create default HTTP transport if none provided
3033 if transport is None :
31- transport = HTTPRegistryTransport (url = url )
32-
33- self .transport = transport
34- self .client = RegistryClient (self .transport )
34+ if url is None :
35+ raise ValueError ("At least one of transport or url must be provided" )
36+ else :
37+ self .logger .info (f"Creating default HTTPRegistryTransport using the provided URL: { url } " )
38+ transport = HTTPRegistryTransport (url = url )
3539
3640 # Local store for agent cards
3741 self ._agents : dict [str , AgentCard ] = {}
3842
39- # Wire server-side handlers
40- self .transport ._register_local = self ._register_local
41- self .transport ._unregister_local = self ._unregister_local
42- self .transport ._discover_local = self ._discover_local
43+ self .start_time : float | None = None
44+
45+ # Setup registry client
46+ self ._client = RegistryClient (transport )
47+
48+ # Setup registry server
49+ self ._server = RegistryServer (
50+ transport ,
51+ register_handler = self .handle_register ,
52+ unregister_handler = self .handle_unregister ,
53+ discover_handler = self .handle_discover ,
54+ status_handler = self .handle_status_html ,
55+ )
4356
4457 # ------------------------------------------------------------------
45- # Lifecycle
58+ # Registry Server Lifecycle
4659 # ------------------------------------------------------------------
4760
4861 async def start (self ) -> None :
4962 """Start the registry server via the transport."""
50- await self .transport .start ()
63+ if self ._server :
64+ try :
65+ await self ._server .start ()
66+ except Exception as e :
67+ self .logger .exception (f"Unexpected error during server start: { e } " )
68+ raise
69+ self .start_time = time .time ()
5170
5271 async def stop (self ) -> None :
5372 """Stop the registry server via the transport."""
54- await self .transport .stop ()
73+ if self ._server :
74+ await self ._server .stop ()
5575
5676 # ------------------------------------------------------------------
5777 # Client API (agents call these)
5878 # ------------------------------------------------------------------
5979
6080 async def register (self , card : AgentCard ) -> None :
61- await self .client .register (card )
81+ await self ._client .register (card )
6282
6383 async def unregister (self , agent_url : str ) -> None :
64- await self .client .unregister (agent_url )
84+ await self ._client .unregister (agent_url )
6585
6686 async def discover (self , filter_by : dict [str , Any ] | None = None ) -> list [AgentCard ]:
67- return await self .client .discover (filter_by )
87+ return await self ._client .discover (filter_by )
6888
6989 # ------------------------------------------------------------------
7090 # Server-side handlers
7191 # ------------------------------------------------------------------
7292
73- async def _register_local (self , card : AgentCard ) -> None :
93+ async def handle_register (self , card : AgentCard ) -> None :
7494 self ._agents [card .url ] = card
7595
7696 self .logger .info (
@@ -81,10 +101,10 @@ async def _register_local(self, card: AgentCard) -> None:
81101 },
82102 )
83103
84- async def _unregister_local (self , agent_url : str ) -> None :
104+ async def handle_unregister (self , agent_url : str ) -> None :
85105 self ._agents .pop (agent_url , None )
86106
87- async def _discover_local (self , filter_by : dict [str , Any ] | None = None ) -> list [AgentCard ]:
107+ async def handle_discover (self , filter_by : dict [str , Any ] | None = None ) -> list [AgentCard ]:
88108 if not filter_by :
89109 return list (self ._agents .values ())
90110
@@ -93,6 +113,14 @@ def match(card: AgentCard) -> bool:
93113
94114 return [c for c in self ._agents .values () if match (c )]
95115
116+ def handle_status_html (self ) -> str :
117+ """Return the registry's status as HTML.
118+
119+ Returns:
120+ HTML string with registry status information
121+ """
122+ return to_registry_status_html ("Registry" , "HTTP" , self ._agents , self .start_time )
123+
96124 # ------------------------------------------------------------------
97125 # Utilities
98126 # ------------------------------------------------------------------
0 commit comments