@@ -3,9 +3,13 @@ use std::{collections::HashSet, sync::Arc};
3
3
use pg_base_db:: { Change , DocumentChange , PgLspPath } ;
4
4
use pg_commands:: ExecuteStatementCommand ;
5
5
use pg_diagnostics:: Diagnostic ;
6
+ use pg_hover:: HoverParams ;
6
7
use pg_workspace:: Workspace ;
7
8
use tokio:: sync:: RwLock ;
8
- use tower_lsp:: lsp_types:: { CodeAction , InlayHint , Range } ;
9
+ use tower_lsp:: lsp_types:: {
10
+ CodeAction , CodeActionOrCommand , CompletionItem , CompletionItemKind , CompletionList , Hover ,
11
+ HoverContents , InlayHint , MarkedString , Position , Range ,
12
+ } ;
9
13
10
14
use crate :: { db_connection:: DbConnection , utils:: line_index_ext:: LineIndexExt } ;
11
15
@@ -133,21 +137,15 @@ impl Session {
133
137
. collect ( )
134
138
}
135
139
136
- pub async fn get_available_code_actions (
140
+ pub async fn get_available_code_actions_or_commands (
137
141
& self ,
138
142
path : PgLspPath ,
139
143
range : Range ,
140
- ) -> Option < Vec < CodeAction > > {
144
+ ) -> Option < Vec < CodeActionOrCommand > > {
141
145
let ide = self . ide . read ( ) . await ;
142
- let doc = ide. documents . get ( & path) ;
143
- if doc. is_none ( ) {
144
- return None ;
145
- }
146
+ let doc = ide. documents . get ( & path) ?;
146
147
147
- let db = self . db . read ( ) . await ;
148
- if db. is_none ( ) {
149
- return None ;
150
- }
148
+ let db = self . db . read ( ) . await ?;
151
149
152
150
let doc = doc. unwrap ( ) ;
153
151
let range = doc. line_index . offset_lsp_range ( range) . unwrap ( ) ;
@@ -162,20 +160,11 @@ impl Session {
162
160
"Execute '{}'" ,
163
161
ExecuteStatementCommand :: trim_statement( stmt. text. clone( ) , 50 )
164
162
) ;
165
- CodeAction {
166
- title : title. clone ( ) ,
167
- kind : None ,
168
- edit : None ,
169
- command : Some ( Command {
170
- title,
171
- command : format ! ( "pglsp.{}" , cmd. id( ) ) ,
172
- arguments : Some ( vec ! [ serde_json:: to_value( stmt. text. clone( ) ) . unwrap( ) ] ) ,
173
- } ) ,
174
- diagnostics : None ,
175
- is_preferred : None ,
176
- disabled : None ,
177
- data : None ,
178
- }
163
+ CodeActionOrCommand :: Command ( Command {
164
+ title,
165
+ command : format ! ( "pglsp.{}" , cmd. id( ) ) ,
166
+ arguments : Some ( vec ! [ serde_json:: to_value( stmt. text. clone( ) ) . unwrap( ) ] ) ,
167
+ } )
179
168
} )
180
169
. collect ( ) ;
181
170
@@ -184,13 +173,9 @@ impl Session {
184
173
185
174
pub async fn get_inlay_hints ( & self , path : PgLspPath , range : Range ) -> Option < Vec < InlayHint > > {
186
175
let ide = self . ide . read ( ) . await ;
187
- let doc = ide. documents . get ( & path) ;
188
- if doc. is_none ( ) {
189
- return None ;
190
- }
176
+ let doc = ide. documents . get ( & path) ?;
191
177
192
- let doc = doc. unwrap ( ) ;
193
- let range = doc. line_index . offset_lsp_range ( range) . unwrap ( ) ;
178
+ let range = doc. line_index . offset_lsp_range ( range) ?;
194
179
195
180
let schema_cache = ide. schema_cache . read ( ) . expect ( "Unable to get Schema Cache" ) ;
196
181
@@ -235,4 +220,87 @@ impl Session {
235
220
236
221
Some ( hints)
237
222
}
223
+
224
+ pub async fn get_available_completions (
225
+ & self ,
226
+ path : PgLspPath ,
227
+ position : Position ,
228
+ ) -> Option < CompletionList > {
229
+ let ide = self . ide . read ( ) . await ;
230
+
231
+ let doc = ide. documents . get ( & path) ?;
232
+ let offset = doc. line_index . offset_lsp ( position) ?;
233
+ let ( range, stmt) = doc. statement_at_offset_with_range ( & offset) ?;
234
+
235
+ let schema_cache = ide. schema_cache . read ( ) . expect ( "No Schema Cache" ) ;
236
+
237
+ let completion_items = pg_completions:: complete ( & CompletionParams {
238
+ position : pos - range. start ( ) - TextSize :: from ( 1 ) ,
239
+ text : stmt. text . as_str ( ) ,
240
+ tree : ide. tree_sitter . tree ( & stmt) . as_ref ( ) . map ( |x| x. as_ref ( ) ) ,
241
+ schema : & schema,
242
+ } )
243
+ . items
244
+ . into_iter ( )
245
+ . map ( |i| CompletionItem {
246
+ // TODO: add more data
247
+ label : i. data . label ( ) . to_string ( ) ,
248
+ label_details : None ,
249
+ kind : Some ( CompletionItemKind :: CLASS ) ,
250
+ detail : None ,
251
+ documentation : None ,
252
+ deprecated : None ,
253
+ preselect : None ,
254
+ sort_text : None ,
255
+ filter_text : None ,
256
+ insert_text : None ,
257
+ insert_text_format : None ,
258
+ insert_text_mode : None ,
259
+ text_edit : None ,
260
+ additional_text_edits : None ,
261
+ commit_characters : None ,
262
+ data : None ,
263
+ tags : None ,
264
+ command : None ,
265
+ } )
266
+ . collect ( ) ;
267
+
268
+ Some ( CompletionList {
269
+ is_incomplete : false ,
270
+ items : completion_items,
271
+ } )
272
+ }
273
+
274
+ pub async fn get_available_hover_diagnostics (
275
+ & self ,
276
+ path : PgLspPath ,
277
+ position : Position ,
278
+ ) -> Option < Hover > {
279
+ let ide = self . ide . read ( ) . await ;
280
+ let doc = ide. documents . get ( & path) ?;
281
+
282
+ let offset = doc. line_index . offset_lsp ( position) ?;
283
+
284
+ let ( range, stmt) = doc. statement_at_offset_with_range ( & offset) ?;
285
+ let range_start = range. start ( ) ;
286
+ let hover_range = doc. line_index . line_col_lsp_range ( range) ;
287
+
288
+ let schema_cache = ide. schema_cache . read ( ) . expect ( "No Schema Cache" ) ;
289
+
290
+ :: pg_hover:: hover ( HoverParams {
291
+ position : offset - range_start,
292
+ source : stmt. text . as_str ( ) ,
293
+ enriched_ast : ide
294
+ . pg_query
295
+ . enriched_ast ( & stmt)
296
+ . as_ref ( )
297
+ . map ( |x| x. as_ref ( ) ) ,
298
+ tree : ide. tree_sitter . tree ( & stmt) . as_ref ( ) . map ( |x| x. as_ref ( ) ) ,
299
+ schema_cache : schema_cache. clone ( ) ,
300
+ } )
301
+ . map ( |hover| Hover {
302
+ contents : HoverContents :: Scalar ( MarkedString :: String ( hover. content ) ) ,
303
+ range : hover_range,
304
+ } )
305
+ }
238
306
}
0 commit comments