@@ -5,8 +5,11 @@ use std::{
5
5
} ;
6
6
use tracing:: info;
7
7
8
+ use async_lsp:: lsp_types:: ProgressParamsValue ;
8
9
use async_lsp:: lsp_types:: { CompletionItem , CompletionItemKind , PublishDiagnosticsParams , Url } ;
10
+ use std:: sync:: mpsc:: Sender ;
9
11
use tree_sitter:: Node ;
12
+ use walkdir:: WalkDir ;
10
13
11
14
use crate :: {
12
15
nodekind:: NodeKind ,
@@ -17,6 +20,7 @@ pub struct ProtoLanguageState {
17
20
documents : Arc < RwLock < HashMap < Url , String > > > ,
18
21
trees : Arc < RwLock < HashMap < Url , ParsedTree > > > ,
19
22
parser : Arc < Mutex < ProtoParser > > ,
23
+ parsed_workspaces : Arc < RwLock < HashSet < String > > > ,
20
24
}
21
25
22
26
impl ProtoLanguageState {
@@ -25,6 +29,7 @@ impl ProtoLanguageState {
25
29
documents : Default :: default ( ) ,
26
30
trees : Default :: default ( ) ,
27
31
parser : Arc :: new ( Mutex :: new ( ProtoParser :: new ( ) ) ) ,
32
+ parsed_workspaces : Arc :: new ( RwLock :: new ( HashSet :: new ( ) ) ) ,
28
33
}
29
34
}
30
35
@@ -146,83 +151,65 @@ impl ProtoLanguageState {
146
151
. collect ( )
147
152
}
148
153
149
- // #[allow(unused)]
150
- // pub fn add_workspace_folder_async(
151
- // &mut self,
152
- // workspace: WorkspaceFolder,
153
- // tx: Sender<ProgressParamsValue>,
154
- // ) {
155
- // let parser = self.parser.clone();
156
- // let tree = self.trees.clone();
157
- // let docs = self.documents.clone();
158
- //
159
- // let begin = ProgressParamsValue::WorkDone(WorkDoneProgress::Begin(WorkDoneProgressBegin {
160
- // title: String::from("indexing"),
161
- // cancellable: Some(false),
162
- // percentage: Some(0),
163
- // ..Default::default()
164
- // }));
165
- //
166
- // if let Err(e) = tx.send(begin) {
167
- // error!(error=%e, "failed to send work begin progress");
168
- // }
169
- //
170
- // thread::spawn(move || {
171
- // let files: Vec<_> = WalkDir::new(workspace.uri.path())
172
- // .into_iter()
173
- // .filter_map(|e| e.ok())
174
- // .filter(|e| e.path().extension().is_some())
175
- // .filter(|e| e.path().extension().unwrap() == "proto")
176
- // .collect();
177
- //
178
- // let total_files = files.len();
179
- // let mut current = 0;
180
- //
181
- // for file in files.into_iter() {
182
- // let path = file.path();
183
- // if path.is_absolute() && path.is_file() {
184
- // let Ok(content) = read_to_string(path) else {
185
- // continue;
186
- // };
187
- //
188
- // let Ok(uri) = Url::from_file_path(path) else {
189
- // continue;
190
- // };
191
- //
192
- // Self::upsert_content_impl(
193
- // parser.lock().expect("poison"),
194
- // &uri,
195
- // content,
196
- // docs.write().expect("poison"),
197
- // tree.write().expect("poison"),
198
- // );
199
- //
200
- // current += 1;
201
- //
202
- // let report = ProgressParamsValue::WorkDone(WorkDoneProgress::Report(
203
- // WorkDoneProgressReport {
204
- // cancellable: Some(false),
205
- // message: Some(path.display().to_string()),
206
- // percentage: Some((current * 100 / total_files) as u32),
207
- // },
208
- // ));
209
- //
210
- // if let Err(e) = tx.send(report) {
211
- // error!(error=%e, "failed to send work report progress");
212
- // }
213
- // }
214
- // }
215
- // let report =
216
- // ProgressParamsValue::WorkDone(WorkDoneProgress::End(WorkDoneProgressEnd {
217
- // message: Some(String::from("completed")),
218
- // }));
219
- //
220
- // info!(len = total_files, "workspace file parsing completed");
221
- // if let Err(e) = tx.send(report) {
222
- // error!(error=%e, "failed to send work completed result");
223
- // }
224
- // });
225
- // }
154
+ pub fn parse_all_from_workspace (
155
+ & mut self ,
156
+ workspace : PathBuf ,
157
+ progress_sender : Option < Sender < ProgressParamsValue > > ,
158
+ ) {
159
+ if self
160
+ . parsed_workspaces
161
+ . read ( )
162
+ . expect ( "poison" )
163
+ . contains ( workspace. to_str ( ) . unwrap_or_default ( ) )
164
+ {
165
+ return ;
166
+ }
167
+
168
+ let files: Vec < _ > = WalkDir :: new ( workspace. to_str ( ) . unwrap_or_default ( ) )
169
+ . into_iter ( )
170
+ . filter_map ( |e| e. ok ( ) )
171
+ . filter ( |e| e. path ( ) . extension ( ) . is_some ( ) )
172
+ . filter ( |e| e. path ( ) . extension ( ) . unwrap ( ) == "proto" )
173
+ . collect ( ) ;
174
+
175
+ let total_files = files. len ( ) ;
176
+
177
+ for ( idx, file) in files. into_iter ( ) . enumerate ( ) {
178
+ let path = file. path ( ) ;
179
+ if path. is_absolute ( ) && path. is_file ( ) {
180
+ if let Ok ( content) = std:: fs:: read_to_string ( path) {
181
+ if let Ok ( uri) = Url :: from_file_path ( path) {
182
+ if self . documents . read ( ) . expect ( "poison" ) . contains_key ( & uri) {
183
+ continue ;
184
+ }
185
+ self . upsert_content ( & uri, content, & [ ] , 1 ) ;
186
+
187
+ if let Some ( sender) = & progress_sender {
188
+ let percentage = ( ( idx + 1 ) as f64 / total_files as f64 * 100.0 ) as u32 ;
189
+ let _ = sender. send ( ProgressParamsValue :: WorkDone (
190
+ async_lsp:: lsp_types:: WorkDoneProgress :: Report (
191
+ async_lsp:: lsp_types:: WorkDoneProgressReport {
192
+ cancellable : None ,
193
+ message : Some ( format ! (
194
+ "Parsing file {} of {}" ,
195
+ idx + 1 ,
196
+ total_files
197
+ ) ) ,
198
+ percentage : Some ( percentage) ,
199
+ } ,
200
+ ) ,
201
+ ) ) ;
202
+ }
203
+ }
204
+ }
205
+ }
206
+ }
207
+
208
+ self . parsed_workspaces
209
+ . write ( )
210
+ . expect ( "poison" )
211
+ . insert ( workspace. to_str ( ) . unwrap_or_default ( ) . to_string ( ) ) ;
212
+ }
226
213
227
214
pub fn upsert_file (
228
215
& mut self ,
0 commit comments