private async Task <CodeRefactoring> GetRefactoringFromProviderAsync( Document document, TextSpan state, CodeRefactoringProvider provider, IExtensionManager extensionManager, bool isBlocking, CancellationToken cancellationToken) { cancellationToken.ThrowIfCancellationRequested(); if (extensionManager.IsDisabled(provider)) { return(null); } try { var actions = ArrayBuilder <(CodeAction action, TextSpan?applicableToSpan)> .GetInstance(); var context = new CodeRefactoringContext(document, state, // TODO: Can we share code between similar lambdas that we pass to this API in BatchFixAllProvider.cs, CodeFixService.cs and CodeRefactoringService.cs? (action, applicableToSpan) => { // Serialize access for thread safety - we don't know what thread the refactoring provider will call this delegate from. lock (actions) { actions.Add((action, applicableToSpan)); } }, isBlocking, cancellationToken); var task = provider.ComputeRefactoringsAsync(context) ?? Task.CompletedTask; await task.ConfigureAwait(false); var result = actions.Count > 0 ? new CodeRefactoring(provider, actions.ToImmutable()) : null; actions.Free(); return(result); } catch (OperationCanceledException) { // We don't want to catch operation canceled exceptions in the catch block // below. So catch is here and rethrow it. throw; } catch (Exception e) { extensionManager.HandleException(provider, e); } return(null); }
private async Task<CodeRefactoring> GetCodeRefactoringAsync( CodeRefactoringProvider provider, TestWorkspace workspace) { var document = GetDocument(workspace); var span = workspace.Documents.Single(d => !d.IsLinkFile && d.SelectedSpans.Count == 1).SelectedSpans.Single(); var actions = new List<CodeAction>(); var context = new CodeRefactoringContext(document, span, (a) => actions.Add(a), CancellationToken.None); await provider.ComputeRefactoringsAsync(context); return actions.Count > 0 ? new CodeRefactoring(provider, actions) : null; }
private async Task <CodeRefactoring> GetRefactoringFromProviderAsync( Document document, TextSpan state, CodeRefactoringProvider provider, IExtensionManager extensionManager, CancellationToken cancellationToken) { cancellationToken.ThrowIfCancellationRequested(); if (extensionManager.IsDisabled(provider)) { return(null); } try { var actions = new List <CodeAction>(); var context = new CodeRefactoringContext(document, state, // TODO: Can we share code between similar lambdas that we pass to this API in BatchFixAllProvider.cs, CodeFixService.cs and CodeRefactoringService.cs? a => { // Serialize access for thread safety - we don't know what thread the refactoring provider will call this delegate from. lock (actions) { actions.Add(a); } }, cancellationToken); var task = provider.ComputeRefactoringsAsync(context) ?? SpecializedTasks.EmptyTask; await task.ConfigureAwait(false); if (actions.Count > 0) { return(new CodeRefactoring(provider, actions)); } } catch (OperationCanceledException) { // We don't want to catch operation canceled exceptions in the catch block // below. So catch is here and rethrow it. throw; } catch (Exception e) { extensionManager.HandleException(provider, e); } return(null); }
private static void RefactoringSetup(TestWorkspace workspace, CodeRefactoringProvider provider, List<CodeAction> refactorings, out ICodeActionEditHandlerService editHandler, out EditorLayerExtensionManager.ExtensionManager extensionManager, out VisualStudio.Text.ITextBuffer textBuffer) { var document = GetDocument(workspace); var span = document.GetSyntaxRootAsync().Result.Span; var context = new CodeRefactoringContext(document, span, (a) => refactorings.Add(a), CancellationToken.None); provider.ComputeRefactoringsAsync(context).Wait(); var action = refactorings.Single(); editHandler = workspace.ExportProvider.GetExportedValue<ICodeActionEditHandlerService>(); extensionManager = document.Project.Solution.Workspace.Services.GetService<IExtensionManager>() as EditorLayerExtensionManager.ExtensionManager; textBuffer = document.GetTextAsync().Result.Container.GetTextBuffer(); }
private async Task<CodeRefactoring> GetRefactoringFromProviderAsync( Document document, TextSpan state, CodeRefactoringProvider provider, IExtensionManager extensionManager, CancellationToken cancellationToken) { cancellationToken.ThrowIfCancellationRequested(); if (extensionManager.IsDisabled(provider)) { return null; } try { var actions = new List<CodeAction>(); var context = new CodeRefactoringContext(document, state, // TODO: Can we share code between similar lambdas that we pass to this API in BatchFixAllProvider.cs, CodeFixService.cs and CodeRefactoringService.cs? a => { // Serialize access for thread safety - we don't know what thread the refactoring provider will call this delegate from. lock (actions) { actions.Add(a); } }, cancellationToken); var task = provider.ComputeRefactoringsAsync(context) ?? SpecializedTasks.EmptyTask; await task.ConfigureAwait(false); if (actions.Count > 0) { return new CodeRefactoring(provider, actions); } } catch (OperationCanceledException) { // We don't want to catch operation canceled exceptions in the catch block // below. So catch is here and rethrow it. throw; } catch (Exception e) { extensionManager.HandleException(provider, e); } return null; }
internal static string GetRefactoringResult(string language, CodeRefactoringProvider codeRefactoringProvider, string oldSource, TextSpan span, string equivalenceKey) { var document = CodeAnalysisHelper.CreateDocument(oldSource, language); var actions = new List<CodeAction>(); var context = new CodeRefactoringContext(document, span, (a) => actions.Add(a), CancellationToken.None); codeRefactoringProvider.ComputeRefactoringsAsync(context).Wait(); if (equivalenceKey != null) { document = CodeAnalysisHelper.ApplyFix(document, actions.Single(n => n.EquivalenceKey == equivalenceKey)); } else { document = CodeAnalysisHelper.ApplyFix(document, actions[0]); } var newSource = CodeAnalysisHelper.GetStringFromDocument(document); return newSource; }
internal static List<CodeAction> GetRefactoringActions(string language, CodeRefactoringProvider codeRefactoringProvider, string source, TextSpan span) { var document = CodeAnalysisHelper.CreateDocument(source, language); var actions = new List<CodeAction>(); var context = new CodeRefactoringContext(document, span, (a) => actions.Add(a), CancellationToken.None); codeRefactoringProvider.ComputeRefactoringsAsync(context).Wait(); return actions; }
private async Task <CodeRefactoring?> GetRefactoringFromProviderAsync( Document document, TextSpan state, CodeRefactoringProvider provider, CodeChangeProviderMetadata?providerMetadata, IExtensionManager extensionManager, CodeActionOptionsProvider options, bool isBlocking, CancellationToken cancellationToken) { cancellationToken.ThrowIfCancellationRequested(); if (extensionManager.IsDisabled(provider)) { return(null); } try { using var _ = ArrayBuilder <(CodeAction action, TextSpan?applicableToSpan)> .GetInstance(out var actions); var context = new CodeRefactoringContext(document, state, // TODO: Can we share code between similar lambdas that we pass to this API in BatchFixAllProvider.cs, CodeFixService.cs and CodeRefactoringService.cs? (action, applicableToSpan) => { // Serialize access for thread safety - we don't know what thread the refactoring provider will call this delegate from. lock (actions) { // Add the Refactoring Provider Name to the parent CodeAction's CustomTags. // Always add a name even in cases of 3rd party refactorings that do not export // name metadata. action.AddCustomTagAndTelemetryInfo(providerMetadata, provider); actions.Add((action, applicableToSpan)); } }, options, isBlocking, cancellationToken); var task = provider.ComputeRefactoringsAsync(context) ?? Task.CompletedTask; await task.ConfigureAwait(false); if (actions.Count == 0) { return(null); } var fixAllProviderInfo = extensionManager.PerformFunction( provider, () => ImmutableInterlocked.GetOrAdd(ref _fixAllProviderMap, provider, FixAllProviderInfo.Create), defaultValue: null); return(new CodeRefactoring(provider, actions.ToImmutable(), fixAllProviderInfo, options)); } catch (OperationCanceledException) { // We don't want to catch operation canceled exceptions in the catch block // below. So catch is here and rethrow it. throw; } catch (Exception e) { extensionManager.HandleException(provider, e); } return(null); }