@@ -76,6 +76,7 @@ async def search_calendar_events(
7676 limit ,
7777 )
7878 except ValueError as exception :
79+ # Model-generated tool arguments are reported as a structured result, not a tool exception.
7980 return _input_validation_result (exception )
8081 return await _search_calendar_events (
8182 nc ,
@@ -96,6 +97,7 @@ async def _search_calendar_events(
9697 term_groups : list [list [str ]],
9798 result_limit : int ,
9899) -> dict :
100+ """Discover, select, query and aggregate calendars while preserving partial failures."""
99101 failures = []
100102 try :
101103 calendars , failed_discovery_responses = await _list_event_calendars (nc )
@@ -142,6 +144,7 @@ async def _search_calendar_events(
142144 event .pop ("_uid" , None )
143145 event .pop ("_calendar_href" , None )
144146 result_truncated = len (sorted_events ) > result_limit
147+ # Discovery, selection, query or processing limits make absence unreliable.
145148 truncated = resource_truncated or result_truncated
146149 complete = not failures and not truncated
147150 result = {
@@ -184,6 +187,7 @@ async def _search_selected_calendars(
184187 events = []
185188 failures = []
186189 resource_truncated = False
190+ # Bound the full request and processing lifetime to cap concurrent DAV work and parsed response data.
187191 semaphore = asyncio .Semaphore (MAX_CONCURRENT_CALENDAR_QUERIES )
188192 query_body = calendar_query_body (bounds )
189193 calendar_results = await asyncio .gather (
@@ -217,6 +221,7 @@ async def _search_calendar(
217221 async with semaphore :
218222 try :
219223 xml_text = await _calendar_report (nc , calendar , query_body )
224+ # XML parsing and recurrence expansion are synchronous and may be expensive.
220225 return await asyncio .to_thread (
221226 _process_calendar_response ,
222227 xml_text ,
@@ -236,6 +241,7 @@ def _process_calendar_response(
236241 bounds : SearchBounds ,
237242 term_groups : list [list [str ]],
238243) -> tuple [list [dict ], list [dict ], bool ]:
244+ """Process one calendar response without letting a bad resource discard its other events."""
239245 resources , failed_resources , resource_truncated = parse_calendar_data (xml_text )
240246 failures = []
241247 if failed_resources :
@@ -265,6 +271,7 @@ def _process_calendar_response(
265271 event ["_calendar_href" ] = calendar .href
266272 events .extend (resource_events )
267273 except Exception :
274+ # One malformed or unsupported resource must not make the calendar's successful matches disappear.
268275 parse_failures += 1
269276 if parse_failures :
270277 failures .append (
@@ -287,6 +294,7 @@ async def is_available(nc: AsyncNextcloudApp):
287294
288295
289296async def _list_event_calendars (nc : AsyncNextcloudApp ) -> tuple [list [CalendarCollection ], int ]:
297+ """Follow CalDAV principal discovery to the current user's event calendars."""
290298 principal_response = await nc ._session .adapter_dav .request (
291299 "PROPFIND" ,
292300 "/" ,
@@ -336,6 +344,7 @@ def _dav_headers(depth: str) -> dict[str, str]:
336344
337345
338346def _same_origin_dav_path (nc : AsyncNextcloudApp , href : str ) -> str :
347+ # WebCal subscriptions are read from Nextcloud's cached DAV collection, never from their external URL.
339348 target = urlsplit (href )
340349 endpoint = urlsplit (nc ._session .cfg .endpoint )
341350 if target .scheme and (target .scheme , target .netloc ) != (endpoint .scheme , endpoint .netloc ):
0 commit comments