/// <summary> /// Creates a new <see cref="CodeFixExecutionContext{T}"/> from the specified <paramref name="data"/>. /// </summary> /// <param name="data"><see cref="CodeFixData{T}"/> to create the <see cref="CodeFixExecutionContext{T}"/> from.</param> /// <param name="cancellationToken"><see cref="System.Threading.CancellationToken"/> that specifies if the operation should be canceled.</param> /// <exception cref="InvalidOperationException">The <see cref="CodeFixData{T}.Success"/> property of <paramref name="data"/> returned <see langword="false"/>. -or- The <see cref="CodeFixData{T}.HasNode"/> property of <paramref name="data"/> returned <see langword="false"/>.</exception> public static async Task <CodeFixExecutionContext <T> > FromAsync(CodeFixData <T> data, CancellationToken cancellationToken) { if (!data.Success) { throw new InvalidOperationException($"The {nameof(CodeFixData<T>.Success)} property of '{nameof(data)}' returned false!"); } if (!data.HasNode) { throw new InvalidOperationException($"The {nameof(CodeFixData<T>.HasNode)} property of '{nameof(data)}' returned false!"); } if (data.HasSemanticModel) { return(new CodeFixExecutionContext <T>( data.Diagnostic, data.Document, data.Root, data.Node, (CSharpCompilation)data.SemanticModel.Compilation, cancellationToken)); } CSharpCompilation?compilation = (CSharpCompilation?)await data.Document.Project.GetCompilationAsync(cancellationToken).ConfigureAwait(false); return(new CodeFixExecutionContext <T>( data.Diagnostic, data.Document, data.Root, data.Node, compilation !, cancellationToken)); }
/// <summary> /// Returns a <see cref="CodeAction"/> to be executed. /// </summary> /// <param name="data">Represents data that is used when creating a <see cref="CodeAction"/> for the code fix.</param> protected virtual async Task <CodeAction?> GetCodeActionAsync(CodeFixData <T> data) { if (!data.Success || !data.HasNode) { return(null); } Document document = data.Document; T node = data.Node; CompilationUnitSyntax root = data.Root; Diagnostic diagnostic = data.Diagnostic; SemanticModel? semanticModel = data.SemanticModel ?? await document.GetSemanticModelAsync(data.CancellationToken).ConfigureAwait(false); if (semanticModel is null) { return(null); } return(CodeAction.Create(Title, cancellationToken => ExecuteAsync(CodeFixExecutionContext <T> .From( diagnostic, document, root, node, semanticModel, cancellationToken)), Id)); }
/// <summary> /// Computes one or more fixes for the specified Microsoft.CodeAnalysis.CodeFixes.CodeFixContext. /// </summary> /// <param name="context">A Microsoft.CodeAnalysis.CodeFixes.CodeFixContext containing context information about the diagnostics to fix. The context must only contain diagnostics with a <see cref="Diagnostic.Id"/> included in the <see cref="CodeFixProvider.FixableDiagnosticIds"/> for the current provider.</param> /// <param name="includeSemanticModel">Determines whether to include the <see cref="SemanticModel"/> when creating this <see cref="CodeFixData{T}"/>.</param> protected async Task RegisterCodeFixesAsync(CodeFixContext context, bool includeSemanticModel) { CodeFixData <T> data = await CodeFixData <T> .FromAsync(context, includeSemanticModel).ConfigureAwait(false); CodeAction?action = await GetCodeActionAsync(data).ConfigureAwait(false); if (action is null) { return; } context.RegisterCodeFix(action, data.Diagnostic !); }
/// <inheritdoc cref="FromAsync(CodeFixData{T}, CancellationToken)"/> public static Task <CodeFixExecutionContext <T> > FromAsync(CodeFixData <T> data) { return(FromAsync(data, data.CancellationToken)); }