@@ -6,8 +6,8 @@ import * as fse from 'fs-extra';
66import * as os from 'os' ;
77import * as path from 'path' ;
88import * as semver from 'semver' ;
9- import { CodeActionContext , commands , CompletionItem , ConfigurationTarget , Diagnostic , env , EventEmitter , ExtensionContext , extensions , IndentAction , InputBoxOptions , languages , MarkdownString , QuickPickItemKind , RelativePattern , TextDocument , TextEditorRevealType , UIKind , Uri , ViewColumn , window , workspace , WorkspaceConfiguration } from 'vscode' ;
10- import { CancellationToken , CodeActionParams , CodeActionRequest , Command , CompletionRequest , DidChangeConfigurationNotification , ExecuteCommandParams , ExecuteCommandRequest , LanguageClientOptions , RevealOutputChannelOn } from 'vscode-languageclient' ;
9+ import { CodeActionContext , commands , CompletionItem , ConfigurationTarget , Diagnostic , env , EventEmitter , ExtensionContext , extensions , IndentAction , InputBoxOptions , languages , MarkdownString , QuickPickItemKind , Range , RelativePattern , SnippetString , SnippetTextEdit , TextDocument , TextEditorRevealType , UIKind , Uri , ViewColumn , window , workspace , WorkspaceConfiguration , WorkspaceEdit } from 'vscode' ;
10+ import { CancellationToken , CodeActionParams , CodeActionRequest , CodeActionResolveRequest , Command , CompletionRequest , DidChangeConfigurationNotification , ExecuteCommandParams , ExecuteCommandRequest , LanguageClientOptions , RevealOutputChannelOn } from 'vscode-languageclient' ;
1111import { LanguageClient } from 'vscode-languageclient/node' ;
1212import { apiManager } from './apiManager' ;
1313import { ClientErrorHandler } from './clientErrorHandler' ;
@@ -235,6 +235,7 @@ export async function activate(context: ExtensionContext): Promise<ExtensionAPI>
235235 extractInterfaceSupport : true ,
236236 advancedUpgradeGradleSupport : true ,
237237 executeClientCommandSupport : true ,
238+ snippetEditSupport : true ,
238239 } ,
239240 triggerFiles,
240241 } ,
@@ -303,7 +304,60 @@ export async function activate(context: ExtensionContext): Promise<ExtensionAPI>
303304 } , ( error ) => {
304305 return client . handleFailedRequest ( CodeActionRequest . type , token , error , [ ] ) ;
305306 } ) ;
306- }
307+ } ,
308+
309+ resolveCodeAction : async ( item , token , next ) => {
310+ const client : LanguageClient = standardClient . getClient ( ) ;
311+ const documentUris = [ ] ;
312+ const snippetEdits = [ ] ;
313+ const resolveCodeAction = async ( item , token ) => {
314+ return client . sendRequest ( CodeActionResolveRequest . type , client . code2ProtocolConverter . asCodeActionSync ( item ) , token ) . then ( async ( result ) => {
315+ if ( token . isCancellationRequested ) {
316+ return item ;
317+ }
318+ const docChanges = result . edit . documentChanges ;
319+ for ( const editType of docChanges ) {
320+ if ( "textDocument" in editType ) {
321+ for ( const edit of editType . edits ) {
322+ if ( "snippet" in edit ) {
323+ documentUris . push ( editType . textDocument . uri ) ;
324+ snippetEdits . push ( new SnippetTextEdit ( asRange ( ( edit as any ) . range ) , new SnippetString ( ( edit as any ) . snippet . value ) ) ) ;
325+ }
326+ }
327+ }
328+ }
329+ const codeAction = await client . protocol2CodeConverter . asCodeAction ( result , token ) ;
330+ const docEdits = codeAction . edit . entries ( ) ;
331+ const newWorkspaceEdit = new WorkspaceEdit ( ) ;
332+ for ( const doc of docEdits ) {
333+ const uri = doc [ 0 ] ;
334+ if ( documentUris . includes ( uri . toString ( ) ) ) {
335+ const editList = [ ] ;
336+ for ( const edit of doc [ 1 ] ) {
337+ let isSnippet = false ;
338+ snippetEdits . forEach ( ( snippet , index ) => {
339+ if ( edit . range . isEqual ( snippet . range ) && documentUris [ index ] === uri . toString ( ) ) {
340+ editList . push ( snippet ) ;
341+ isSnippet = true ;
342+ }
343+ } ) ;
344+ if ( ! isSnippet ) {
345+ editList . push ( edit ) ;
346+ }
347+ }
348+ newWorkspaceEdit . set ( uri , editList ) ;
349+ } else {
350+ newWorkspaceEdit . set ( uri , doc [ 1 ] ) ;
351+ }
352+ }
353+ codeAction . edit = newWorkspaceEdit ;
354+ return codeAction ;
355+ } , ( error ) => {
356+ return client . handleFailedRequest ( CodeActionResolveRequest . type , token , error , item ) ;
357+ } ) ;
358+ } ;
359+ return resolveCodeAction ( item , token ) ;
360+ } ,
307361 } ,
308362 revealOutputChannelOn : RevealOutputChannelOn . Never ,
309363 errorHandler : new ClientErrorHandler ( extensionName ) ,
@@ -1187,4 +1241,8 @@ function registerRestartJavaLanguageServerCommand(context: ExtensionContext) {
11871241 } ) ) ;
11881242}
11891243
1244+ function asRange ( value ) {
1245+ return value ? new Range ( value . start . line , value . start . character , value . end . line , value . end . character ) : undefined ;
1246+ }
1247+
11901248
0 commit comments