@@ -64,15 +64,34 @@ public static void CheckAndExecute<T> (
64
64
throw new InvalidOperationException ( $ "No handler available for `{ typeof ( T ) } `") ;
65
65
}
66
66
67
+ // There is a race here where a completion session may have triggered on the UI thread
68
+ // but the task to compute the completion items is still running. This can cause the
69
+ // completion to be dismissed before the items are computed.
70
+ //
71
+ // We mitigate this by checking if a session is open and attempting to wait for it.
67
72
if ( textView != null ) {
68
73
if ( textView . Properties . TryGetProperty ( typeof ( IAsyncCompletionSession ) , out IAsyncCompletionSession session ) ) {
69
74
if ( EnableDebugTrace ) {
70
75
LogTrace ( "Session open" ) ;
71
76
RegisterTraceHandlers ( session ) ;
72
77
}
73
- //ensure the computation is completed before we continue typing
78
+
79
+ // The first time we see the session, wait for a short time to allow it to initialize,
80
+ // otherwise completion will dismiss via TryDismissSafelyAsync if the snapshot is updated
81
+ // before the session is initialized.
82
+ //
83
+ // This wait is not necessary on my local machine, but it mitigates nondeterministic
84
+ // failures on GitHub Actions CI.
85
+ //
86
+ // Note that polling IAsyncCompletionSessionOperations.IsStarted does not help.
87
+ if ( IsGithubActions && ! session . Properties . TryGetProperty ( HasWaitedForCompletionToInitializeKey , out bool hasWaited ) ) {
88
+ session . Properties . AddProperty ( HasWaitedForCompletionToInitializeKey , true ) ;
89
+ Thread . Sleep ( 500 ) ;
90
+ }
91
+
92
+ // Block until the computation is updated before we run more actions. This makes the
93
+ // test reliable on my local machine.
74
94
session . GetComputedItems ( CancellationToken . None ) ;
75
- LogTrace ( "Session open" ) ;
76
95
}
77
96
} else {
78
97
LogTrace ( "Session not open" ) ;
@@ -81,6 +100,10 @@ public static void CheckAndExecute<T> (
81
100
82
101
const string TraceID = "CommandServiceExtensions.Trace" ;
83
102
103
+ static readonly object HasWaitedForCompletionToInitializeKey = new ( ) ;
104
+
105
+ static readonly bool IsGithubActions = Environment . GetEnvironmentVariable ( "GITHUB_ACTIONS" ) != null ;
106
+
84
107
static void LogTrace ( string message ) => Console . WriteLine ( $ "{ TraceID } : { message } ") ;
85
108
86
109
static void RegisterTraceHandlers ( IAsyncCompletionSession session )
0 commit comments