1414 async_tasking_event ,
1515 async_tasking_event_iterator ,
1616 create_sub_task ,
17- threaded ,
1817)
1918from ....utils .logging import LoggingDescriptor
2019from ....utils .uri import Uri
@@ -92,6 +91,7 @@ def __init__(self, protocol: LanguageServerProtocol) -> None:
9291 self ._current_workspace_task : Optional [asyncio .Task [WorkspaceDiagnosticReport ]] = None
9392 self .in_get_document_diagnostics = Event (True )
9493 self .in_get_workspace_diagnostics = Event (True )
94+ self ._collect_full_diagnostics = False
9595
9696 def extend_capabilities (self , capabilities : ServerCapabilities ) -> None :
9797 if (
@@ -106,12 +106,17 @@ def extend_capabilities(self, capabilities: ServerCapabilities) -> None:
106106 work_done_progress = True ,
107107 )
108108
109- @async_tasking_event_iterator
110- async def collect (sender , document : TextDocument ) -> DiagnosticsResult : # NOSONAR
111- ...
109+ @property
110+ def collect_full_diagnostics (self ) -> bool :
111+ return self ._collect_full_diagnostics
112+
113+ async def set_collect_full_diagnostics (self , value : bool ) -> None :
114+ if self ._collect_full_diagnostics != value :
115+ self ._collect_full_diagnostics = value
116+ await self .refresh ()
112117
113118 @async_tasking_event_iterator
114- async def collect_stage2 (sender , document : TextDocument ) -> DiagnosticsResult : # NOSONAR
119+ async def collect (sender , document : TextDocument , full : bool ) -> DiagnosticsResult : # NOSONAR
115120 ...
116121
117122 @async_tasking_event
@@ -153,6 +158,8 @@ async def ensure_workspace_loaded(self) -> None:
153158 await self .on_workspace_loaded (self )
154159
155160 async def get_document_diagnostics (self , document : TextDocument ) -> RelatedFullDocumentDiagnosticReport :
161+ if self .collect_full_diagnostics :
162+ return await document .get_cache (self .__get_full_document_diagnostics )
156163 return await document .get_cache (self .__get_document_diagnostics )
157164
158165 async def __get_document_diagnostics (self , document : TextDocument ) -> RelatedFullDocumentDiagnosticReport :
@@ -163,6 +170,29 @@ async def __get_document_diagnostics(self, document: TextDocument) -> RelatedFul
163170 async for result_any in self .collect (
164171 self ,
165172 document ,
173+ full = False ,
174+ callback_filter = language_id_filter (document ),
175+ return_exceptions = True ,
176+ ):
177+ result = cast (DiagnosticsResult , result_any )
178+
179+ if isinstance (result , BaseException ):
180+ if not isinstance (result , asyncio .CancelledError ):
181+ self ._logger .exception (result , exc_info = result )
182+ else :
183+ diagnostics .extend (result .diagnostics or [])
184+
185+ return RelatedFullDocumentDiagnosticReport (items = diagnostics , result_id = str (uuid .uuid4 ()))
186+
187+ async def __get_full_document_diagnostics (self , document : TextDocument ) -> RelatedFullDocumentDiagnosticReport :
188+ await self .ensure_workspace_loaded ()
189+
190+ diagnostics : List [Diagnostic ] = []
191+
192+ async for result_any in self .collect (
193+ self ,
194+ document ,
195+ full = True ,
166196 callback_filter = language_id_filter (document ),
167197 return_exceptions = True ,
168198 ):
@@ -177,7 +207,6 @@ async def __get_document_diagnostics(self, document: TextDocument) -> RelatedFul
177207 return RelatedFullDocumentDiagnosticReport (items = diagnostics , result_id = str (uuid .uuid4 ()))
178208
179209 @rpc_method (name = "textDocument/diagnostic" , param_type = DocumentDiagnosticParams )
180- @threaded ()
181210 async def _text_document_diagnostic (
182211 self ,
183212 text_document : TextDocumentIdentifier ,
@@ -236,7 +265,6 @@ async def _get_diagnostics() -> Optional[RelatedFullDocumentDiagnosticReport]:
236265 self ._logger .debug (lambda : f"textDocument/diagnostic ready { text_document } " )
237266
238267 @rpc_method (name = "workspace/diagnostic" , param_type = WorkspaceDiagnosticParams )
239- @threaded ()
240268 async def _workspace_diagnostic (
241269 self ,
242270 identifier : Optional [str ],
@@ -272,7 +300,9 @@ async def _get_diagnostics() -> WorkspaceDiagnosticReport:
272300
273301 async def _get_partial_diagnostics () -> WorkspaceDiagnosticReport :
274302 async with self .parent .window .progress (
275- "Analyse Workspace" , progress_token = work_done_token , cancellable = False
303+ f"Analyse { 'full ' if self .collect_full_diagnostics else '' } Workspace" ,
304+ progress_token = work_done_token ,
305+ cancellable = False ,
276306 ) as progress :
277307
278308 async def _task (doc : TextDocument ) -> None :
@@ -285,7 +315,7 @@ async def _task(doc: TextDocument) -> None:
285315 else :
286316 name = path .relative_to (folder .uri .to_path ())
287317
288- progress .report (f"Analyse { name } " )
318+ progress .report (f"Analyse { 'full ' if self . collect_full_diagnostics else '' } { name } " )
289319
290320 doc_result = await self .get_document_diagnostics (doc )
291321
@@ -332,7 +362,9 @@ async def _task(doc: TextDocument) -> None:
332362 task = create_sub_task (_get_diagnostics () if partial_result_token is None else _get_partial_diagnostics ())
333363 self ._current_workspace_task = task
334364 try :
335- return await task
365+ result = await task
366+ await self .set_collect_full_diagnostics (True )
367+ return result
336368 except asyncio .CancelledError as e :
337369 self ._logger .debug ("workspace/diagnostic canceled" )
338370 raise JsonRPCErrorException (
@@ -350,6 +382,12 @@ def cancel_workspace_diagnostics(self) -> None:
350382 if self ._current_workspace_task is not None and not self ._current_workspace_task .done ():
351383 self ._current_workspace_task .cancel ()
352384
385+ def cancel_document_diagnostics (self , document : TextDocument ) -> None :
386+ task = self ._current_document_tasks .get (document , None )
387+ if task is not None :
388+ self ._logger .critical (lambda : f"textDocument/diagnostic canceled { document } " )
389+ task .cancel ()
390+
353391 async def get_analysis_progress_mode (self , uri : Uri ) -> AnalysisProgressMode :
354392 for e in await self .on_get_analysis_progress_mode (self , uri ):
355393 if e is not None :
0 commit comments