private async Task <Solution?> FixAllContextsAsync(
            FixAllContext originalFixAllContext,
            ImmutableArray <FixAllContext> fixAllContexts)
        {
            var cancellationToken = originalFixAllContext.CancellationToken;
            var progressTracker   = originalFixAllContext.GetProgressTracker();

            progressTracker.Description = originalFixAllContext.GetDefaultFixAllTitle();

            // We have 2*P + 1 pieces of work.  Computing diagnostics and fixes/changes per context, and then one pass
            // applying fixes.
            progressTracker.AddItems(fixAllContexts.Length * 2 + 1);

            // Mapping from document to the cumulative text changes created for that document.
            var docIdToTextMerger = new Dictionary <DocumentId, TextChangeMerger>();

            // Process each context one at a time, allowing us to dump most of the information we computed for each once
            // done with it.  The only information we need to preserve is the data we store in docIdToTextMerger
            foreach (var fixAllContext in fixAllContexts)
            {
                Contract.ThrowIfFalse(fixAllContext.Scope is FixAllScope.Document or
                                      FixAllScope.Project or FixAllScope.ContainingMember or FixAllScope.ContainingType);
                await FixSingleContextAsync(fixAllContext, progressTracker, docIdToTextMerger).ConfigureAwait(false);
            }

            // Finally, merge in all text changes into the solution.  We can't do this per-project as we have to have
            // process *all* diagnostics in the solution to find the changes made to all documents.
            using (progressTracker.ItemCompletedScope())
            {
                if (docIdToTextMerger.Count == 0)
                {
                    return(null);
                }

                var currentSolution = originalFixAllContext.Solution;
                foreach (var group in docIdToTextMerger.GroupBy(kvp => kvp.Key.ProjectId))
                {
                    currentSolution = await ApplyChangesAsync(currentSolution, group.SelectAsArray(kvp => (kvp.Key, kvp.Value)), cancellationToken).ConfigureAwait(false);
                }

                return(currentSolution);
            }
        }
 public override Task <CodeAction?> GetFixAsync(FixAllContext fixAllContext)
 => DefaultFixAllProviderHelpers.GetFixAsync(
     fixAllContext.GetDefaultFixAllTitle(), fixAllContext, FixAllContextsAsync);
Exemple #3
0
 /// <summary>
 /// Produce a suitable title for the fix-all <see cref="CodeAction"/> this type creates in <see
 /// cref="GetFixAsync(FixAllContext)"/>.  Override this if customizing that title is desired.
 /// </summary>
 protected virtual string GetFixAllTitle(FixAllContext fixAllContext)
 => fixAllContext.GetDefaultFixAllTitle();