@@ -9,8 +9,8 @@ namespace ts.Completions {
9
9
}
10
10
export type Log = ( message : string ) => void ;
11
11
12
- const enum SymbolOriginInfoKind { ThisType , SymbolMemberNoExport , SymbolMemberExport , Export }
13
- type SymbolOriginInfo = { kind : SymbolOriginInfoKind . ThisType } | { kind : SymbolOriginInfoKind . SymbolMemberNoExport } | SymbolOriginInfoExport ;
12
+ const enum SymbolOriginInfoKind { ThisType , SymbolMemberNoExport , SymbolMemberExport , Export , Promise }
13
+ type SymbolOriginInfo = { kind : SymbolOriginInfoKind . ThisType } | { kind : SymbolOriginInfoKind . Promise } | { kind : SymbolOriginInfoKind . SymbolMemberNoExport } | SymbolOriginInfoExport ;
14
14
interface SymbolOriginInfoExport {
15
15
kind : SymbolOriginInfoKind . SymbolMemberExport | SymbolOriginInfoKind . Export ;
16
16
moduleSymbol : Symbol ;
@@ -22,6 +22,9 @@ namespace ts.Completions {
22
22
function originIsExport ( origin : SymbolOriginInfo ) : origin is SymbolOriginInfoExport {
23
23
return origin . kind === SymbolOriginInfoKind . SymbolMemberExport || origin . kind === SymbolOriginInfoKind . Export ;
24
24
}
25
+ function originIsPromise ( origin : SymbolOriginInfo ) : boolean {
26
+ return origin . kind === SymbolOriginInfoKind . Promise ;
27
+ }
25
28
26
29
/**
27
30
* Map from symbol id -> SymbolOriginInfo.
@@ -264,6 +267,12 @@ namespace ts.Completions {
264
267
replacementSpan = createTextSpanFromNode ( isJsxInitializer , sourceFile ) ;
265
268
}
266
269
}
270
+ if ( origin && originIsPromise ( origin ) && propertyAccessToConvert ) {
271
+ if ( insertText === undefined ) insertText = name ;
272
+ const awaitText = `(await ${ propertyAccessToConvert . expression . getText ( ) } )` ;
273
+ insertText = needsConvertPropertyAccess ? `${ awaitText } ${ insertText } ` : `${ awaitText } .${ insertText } ` ;
274
+ replacementSpan = createTextSpanFromBounds ( propertyAccessToConvert . getStart ( sourceFile ) , propertyAccessToConvert . end ) ;
275
+ }
267
276
268
277
if ( insertText !== undefined && ! preferences . includeCompletionsWithInsertText ) {
269
278
return undefined ;
@@ -313,7 +322,7 @@ namespace ts.Completions {
313
322
log : Log ,
314
323
kind : CompletionKind ,
315
324
preferences : UserPreferences ,
316
- propertyAccessToConvert ?: PropertyAccessExpression | undefined ,
325
+ propertyAccessToConvert ?: PropertyAccessExpression ,
317
326
isJsxInitializer ?: IsJsxInitializer ,
318
327
recommendedCompletion ?: Symbol ,
319
328
symbolToOriginInfoMap ?: SymbolOriginInfoMap ,
@@ -984,7 +993,7 @@ namespace ts.Completions {
984
993
if ( ! isTypeLocation &&
985
994
symbol . declarations &&
986
995
symbol . declarations . some ( d => d . kind !== SyntaxKind . SourceFile && d . kind !== SyntaxKind . ModuleDeclaration && d . kind !== SyntaxKind . EnumDeclaration ) ) {
987
- addTypeProperties ( typeChecker . getTypeOfSymbolAtLocation ( symbol , node ) ) ;
996
+ addTypeProperties ( typeChecker . getTypeOfSymbolAtLocation ( symbol , node ) , ! ! ( node . flags & NodeFlags . AwaitContext ) ) ;
988
997
}
989
998
990
999
return ;
@@ -999,13 +1008,14 @@ namespace ts.Completions {
999
1008
}
1000
1009
1001
1010
if ( ! isTypeLocation ) {
1002
- addTypeProperties ( typeChecker . getTypeAtLocation ( node ) ) ;
1011
+ addTypeProperties ( typeChecker . getTypeAtLocation ( node ) , ! ! ( node . flags & NodeFlags . AwaitContext ) ) ;
1003
1012
}
1004
1013
}
1005
1014
1006
- function addTypeProperties ( type : Type ) : void {
1015
+ function addTypeProperties ( type : Type , insertAwait ?: boolean ) : void {
1007
1016
isNewIdentifierLocation = ! ! type . getStringIndexType ( ) ;
1008
1017
1018
+ const propertyAccess = node . kind === SyntaxKind . ImportType ? < ImportTypeNode > node : < PropertyAccessExpression | QualifiedName > node . parent ;
1009
1019
if ( isUncheckedFile ) {
1010
1020
// In javascript files, for union types, we don't just get the members that
1011
1021
// the individual types have in common, we also include all the members that
@@ -1016,14 +1026,25 @@ namespace ts.Completions {
1016
1026
}
1017
1027
else {
1018
1028
for ( const symbol of type . getApparentProperties ( ) ) {
1019
- if ( typeChecker . isValidPropertyAccessForCompletions ( node . kind === SyntaxKind . ImportType ? < ImportTypeNode > node : < PropertyAccessExpression | QualifiedName > node . parent , type , symbol ) ) {
1029
+ if ( typeChecker . isValidPropertyAccessForCompletions ( propertyAccess , type , symbol ) ) {
1020
1030
addPropertySymbol ( symbol ) ;
1021
1031
}
1022
1032
}
1023
1033
}
1034
+
1035
+ if ( insertAwait && preferences . includeCompletionsWithInsertText ) {
1036
+ const promiseType = typeChecker . getPromisedTypeOfPromise ( type ) ;
1037
+ if ( promiseType ) {
1038
+ for ( const symbol of promiseType . getApparentProperties ( ) ) {
1039
+ if ( typeChecker . isValidPropertyAccessForCompletions ( propertyAccess , promiseType , symbol ) ) {
1040
+ addPropertySymbol ( symbol , /* insertAwait */ true ) ;
1041
+ }
1042
+ }
1043
+ }
1044
+ }
1024
1045
}
1025
1046
1026
- function addPropertySymbol ( symbol : Symbol ) {
1047
+ function addPropertySymbol ( symbol : Symbol , insertAwait ?: boolean ) {
1027
1048
// For a computed property with an accessible name like `Symbol.iterator`,
1028
1049
// we'll add a completion for the *name* `Symbol` instead of for the property.
1029
1050
// If this is e.g. [Symbol.iterator], add a completion for `Symbol`.
@@ -1040,12 +1061,20 @@ namespace ts.Completions {
1040
1061
! moduleSymbol || ! isExternalModuleSymbol ( moduleSymbol ) ? { kind : SymbolOriginInfoKind . SymbolMemberNoExport } : { kind : SymbolOriginInfoKind . SymbolMemberExport , moduleSymbol, isDefaultExport : false } ;
1041
1062
}
1042
1063
else if ( preferences . includeCompletionsWithInsertText ) {
1064
+ addPromiseSymbolOriginInfo ( symbol ) ;
1043
1065
symbols . push ( symbol ) ;
1044
1066
}
1045
1067
}
1046
1068
else {
1069
+ addPromiseSymbolOriginInfo ( symbol ) ;
1047
1070
symbols . push ( symbol ) ;
1048
1071
}
1072
+
1073
+ function addPromiseSymbolOriginInfo ( symbol : Symbol ) {
1074
+ if ( insertAwait && preferences . includeCompletionsWithInsertText && ! symbolToOriginInfoMap [ getSymbolId ( symbol ) ] ) {
1075
+ symbolToOriginInfoMap [ getSymbolId ( symbol ) ] = { kind : SymbolOriginInfoKind . Promise } ;
1076
+ }
1077
+ }
1049
1078
}
1050
1079
1051
1080
/** Given 'a.b.c', returns 'a'. */
0 commit comments