Пример #1
0
        private static async Task <Document> GetTransformedDocumentAsync(Document document, Diagnostic diagnostic, CancellationToken cancellationToken)
        {
            var syntaxRoot = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false);

            var violatingAttribute = (AttributeSyntax)syntaxRoot.FindNode(diagnostic.Location.SourceSpan).Parent;
            var attributeList      = (AttributeListSyntax)violatingAttribute.Parent;
            var newAttributeLists  = new List <AttributeListSyntax>();

            var indentationOptions = IndentationOptions.FromDocument(document);
            var indentationSteps   = IndentationHelper.GetIndentationSteps(indentationOptions, attributeList);
            var indentationTrivia  = IndentationHelper.GenerateWhitespaceTrivia(indentationOptions, indentationSteps);

            for (var i = 0; i < attributeList.Attributes.Count; i++)
            {
                var newAttributes    = SyntaxFactory.SingletonSeparatedList(attributeList.Attributes[i]);
                var newAttributeList = SyntaxFactory.AttributeList(attributeList.Target, newAttributes);

                newAttributeList = (i == 0)
                    ? newAttributeList.WithLeadingTrivia(attributeList.GetLeadingTrivia())
                    : newAttributeList.WithLeadingTrivia(indentationTrivia);

                newAttributeList = (i == (attributeList.Attributes.Count - 1))
                    ? newAttributeList.WithTrailingTrivia(attributeList.GetTrailingTrivia())
                    : newAttributeList.WithTrailingTrivia(SyntaxFactory.CarriageReturnLineFeed);

                newAttributeLists.Add(newAttributeList);
            }

            var newSyntaxRoot = syntaxRoot.ReplaceNode(attributeList, newAttributeLists);
            var newDocument   = document.WithSyntaxRoot(newSyntaxRoot.WithoutFormatting());

            return(newDocument);
        }
            protected override async Task <SyntaxNode> FixAllInDocumentAsync(FixAllContext fixAllContext, Document document, ImmutableArray <Diagnostic> diagnostics)
            {
                if (diagnostics.IsEmpty)
                {
                    return(null);
                }

                var syntaxRoot = await document.GetSyntaxRootAsync(fixAllContext.CancellationToken).ConfigureAwait(false);

                var settings = SettingsHelper.GetStyleCopSettings(document.Project.AnalyzerOptions, syntaxRoot.SyntaxTree, fixAllContext.CancellationToken);

                // 🐉 Need to eagerly evaluate this with ToList() to ensure nodes are not garbage collected between the
                // call to TrackNodes and subsequent enumeration.
                var nodes = diagnostics.Select(diagnostic => syntaxRoot.FindNode(diagnostic.Location.SourceSpan, getInnermostNodeForTie: true).FirstAncestorOrSelf <AttributeListSyntax>()).ToList();

                var newRoot = syntaxRoot.TrackNodes(nodes);

                foreach (var attributeList in nodes)
                {
                    var indentationSteps  = IndentationHelper.GetIndentationSteps(settings.Indentation, attributeList);
                    var indentationTrivia = IndentationHelper.GenerateWhitespaceTrivia(settings.Indentation, indentationSteps);
                    newRoot = newRoot.ReplaceNode(newRoot.GetCurrentNode(attributeList), GetNewAttributeList(attributeList, indentationTrivia));
                }

                return(newRoot);
            }
        private static void ReformatStatement(IndentationSettings indentationSettings, StatementSyntax statement, Dictionary <SyntaxToken, SyntaxToken> tokenReplaceMap)
        {
            var indentationLevel = DetermineIndentationLevel(indentationSettings, tokenReplaceMap, statement);

            // use one additional step of indentation for lambdas / anonymous methods
            switch (statement.Parent.Kind())
            {
            case SyntaxKind.AnonymousMethodExpression:
            case SyntaxKind.SimpleLambdaExpression:
            case SyntaxKind.ParenthesizedLambdaExpression:
                indentationLevel++;
                break;
            }

            var statementIndentationTrivia = IndentationHelper.GenerateWhitespaceTrivia(indentationSettings, indentationLevel + 1);

            var newFirstTokenLeadingTrivia = statement.GetFirstToken().LeadingTrivia
                                             .WithoutTrailingWhitespace()
                                             .Add(statementIndentationTrivia);

            var newLastTokenTrailingTrivia = statement.GetLastToken().TrailingTrivia
                                             .WithoutTrailingWhitespace()
                                             .Add(SyntaxFactory.CarriageReturnLineFeed);

            AddToReplaceMap(tokenReplaceMap, statement.GetFirstToken(), statement.GetFirstToken().WithLeadingTrivia(newFirstTokenLeadingTrivia));
            AddToReplaceMap(tokenReplaceMap, statement.GetLastToken(), statement.GetLastToken().WithTrailingTrivia(newLastTokenTrailingTrivia));
        }
        /// <summary>
        /// Gets a whitespace trivia containing the proper amount of indentation for new lines in the given query.
        /// </summary>
        /// <param name="indentationOptions">The indentation options to use.</param>
        /// <param name="queryExpression">The query expression to determine indentation from.</param>
        /// <returns>A whitespace trivia containing the proper amount of indentation.</returns>
        internal static SyntaxTrivia GetQueryIndentationTrivia(IndentationOptions indentationOptions, QueryExpressionSyntax queryExpression)
        {
            var firstTokenOnTextLine = IndentationHelper.GetFirstTokenOnTextLine(queryExpression.FromClause.FromKeyword);
            var indentationSteps     = IndentationHelper.GetIndentationSteps(indentationOptions, firstTokenOnTextLine);

            // add an extra indentation step when the first from clause is not properly indented yet
            if (!firstTokenOnTextLine.IsKind(SyntaxKind.OpenParenToken) && (firstTokenOnTextLine != queryExpression.FromClause.FromKeyword))
            {
                indentationSteps++;
            }

            return(IndentationHelper.GenerateWhitespaceTrivia(indentationOptions, indentationSteps));
        }
        private static SyntaxNode ReformatAccessorAsMultipleLines(IndentationSettings indentationSettings, AccessorDeclarationSyntax accessor)
        {
            var accessorList          = (AccessorListSyntax)accessor.Parent;
            var indentationSteps      = IndentationHelper.GetIndentationSteps(indentationSettings, accessorList.OpenBraceToken) + 1;
            var indentation           = IndentationHelper.GenerateWhitespaceTrivia(indentationSettings, indentationSteps);
            var indentationStatements = IndentationHelper.GenerateWhitespaceTrivia(indentationSettings, indentationSteps + 1);

            var newAccessor = accessor
                              .WithModifiers(ReformatModifiersAsMultipleLines(accessor.Modifiers, indentation))
                              .WithKeyword(ReformatKeywordAsMultipleLines(accessor.Keyword, indentation, accessor.Modifiers.Count == 0))
                              .WithBody(ReformatBodyAsMultipleLines(accessor.Body, indentation, indentationStatements));

            return(newAccessor);
        }
        private static SyntaxNode ReformatAccessorAsSingleLine(IndentationSettings indentationSettings, AccessorDeclarationSyntax accessor)
        {
            var newAccessor = accessor
                              .WithModifiers(ReformatModifiersAsSingleLine(accessor.Modifiers))
                              .WithKeyword(ReformatKeywordAsSingleLine(accessor.Keyword))
                              .WithBody(ReformatBodyAsSingleLine(accessor.Body));

            var accessorList = (AccessorListSyntax)accessor.Parent;

            var indentationSteps = IndentationHelper.GetIndentationSteps(indentationSettings, accessorList.OpenBraceToken);
            var indentation      = IndentationHelper.GenerateWhitespaceTrivia(indentationSettings, indentationSteps + 1);

            newAccessor = newAccessor.WithLeadingTrivia(newAccessor.GetLeadingTrivia().Insert(0, indentation));
            return(newAccessor);
        }
        private static void ReformatStatementAndSurroundings(StatementSyntax statement, IndentationSettings indentationSettings, Dictionary <SyntaxToken, SyntaxToken> tokenReplaceMap)
        {
            var block = statement as BlockSyntax;

            var previousToken        = statement.GetFirstToken().GetPreviousToken();
            var previousTokenEndLine = previousToken.GetEndLine();
            var statementStartLine   = statement.GetFirstToken().GetLine();

            if (previousTokenEndLine == statementStartLine)
            {
                var newTrailingTrivia = previousToken.TrailingTrivia
                                        .WithoutTrailingWhitespace()
                                        .Add(SyntaxFactory.CarriageReturnLineFeed);

                AddToReplaceMap(tokenReplaceMap, previousToken, previousToken.WithTrailingTrivia(newTrailingTrivia));
            }

            if (block != null)
            {
                ReformatBlock(indentationSettings, block, tokenReplaceMap);
            }
            else
            {
                ReformatStatement(indentationSettings, statement, tokenReplaceMap);
            }

            var nextToken = statement.GetLastToken().GetNextToken();

            if ((block != null) && nextToken.IsKind(SyntaxKind.SemicolonToken))
            {
                // skip trailing semicolon tokens for blocks
                nextToken = nextToken.GetNextToken();
            }

            var nextTokenStartLine = nextToken.GetLine();
            var statementEndLine   = statement.GetLastToken().GetEndLine();

            if (nextTokenStartLine == statementEndLine)
            {
                var indentationLevel  = DetermineIndentationLevel(indentationSettings, tokenReplaceMap, statement);
                var indentationTrivia = IndentationHelper.GenerateWhitespaceTrivia(indentationSettings, indentationLevel);

                AddToReplaceMap(tokenReplaceMap, nextToken, nextToken.WithLeadingTrivia(indentationTrivia));
            }
        }
Пример #8
0
        private static async Task <Document> GetTransformedDocumentAsync(Document document, Diagnostic diagnostic, CancellationToken cancellationToken)
        {
            var syntaxRoot = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false);

            var nodeInSourceSpan = syntaxRoot.FindNode(diagnostic.Location.SourceSpan, getInnermostNodeForTie: true);
            AttributeListSyntax attributeList = nodeInSourceSpan.FirstAncestorOrSelf <AttributeListSyntax>();

            var settings          = SettingsHelper.GetStyleCopSettings(document.Project.AnalyzerOptions, cancellationToken);
            var indentationSteps  = IndentationHelper.GetIndentationSteps(settings.Indentation, attributeList);
            var indentationTrivia = IndentationHelper.GenerateWhitespaceTrivia(settings.Indentation, indentationSteps);

            List <AttributeListSyntax> newAttributeLists = GetNewAttributeList(attributeList, indentationTrivia);

            var newSyntaxRoot = syntaxRoot.ReplaceNode(attributeList, newAttributeLists);
            var newDocument   = document.WithSyntaxRoot(newSyntaxRoot.WithoutFormatting());

            return(newDocument);
        }
        private static async Task <Document> GetTransformedDocumentAsync(Document document, Diagnostic diagnostic, CancellationToken cancellationToken)
        {
            var syntaxRoot = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false);

            var settings = SettingsHelper.GetStyleCopSettings(document.Project.AnalyzerOptions, syntaxRoot.SyntaxTree, cancellationToken);

            var attributeListSyntax = (AttributeListSyntax)syntaxRoot.FindNode(diagnostic.Location.SourceSpan);

            // use the containing type to determine the indentation level, anything else is less reliable.
            var containingType    = attributeListSyntax.Parent?.Parent;
            var indentationSteps  = (containingType != null) ? IndentationHelper.GetIndentationSteps(settings.Indentation, containingType) + 1 : 0;
            var indentationTrivia = IndentationHelper.GenerateWhitespaceTrivia(settings.Indentation, indentationSteps);

            var tokensToReplace = new Dictionary <SyntaxToken, SyntaxToken>();

            if (diagnostic.Properties.ContainsKey(SA1134AttributesMustNotShareLine.FixWithNewLineBeforeKey))
            {
                var token     = attributeListSyntax.OpenBracketToken;
                var prevToken = token.GetPreviousToken();

                tokensToReplace[prevToken] = prevToken.WithTrailingTrivia(prevToken.TrailingTrivia.WithoutTrailingWhitespace().Add(SyntaxFactory.CarriageReturnLineFeed));

                var newLeadingTrivia = token.LeadingTrivia.Insert(0, indentationTrivia);
                tokensToReplace[token] = token.WithLeadingTrivia(newLeadingTrivia);
            }

            if (diagnostic.Properties.ContainsKey(SA1134AttributesMustNotShareLine.FixWithNewLineAfterKey))
            {
                var token     = attributeListSyntax.CloseBracketToken;
                var nextToken = token.GetNextToken();

                tokensToReplace[token] = token.WithTrailingTrivia(token.TrailingTrivia.WithoutTrailingWhitespace().Add(SyntaxFactory.CarriageReturnLineFeed));

                var newLeadingTrivia = nextToken.LeadingTrivia.Insert(0, indentationTrivia);
                tokensToReplace[nextToken] = nextToken.WithLeadingTrivia(newLeadingTrivia);
            }

            var newSyntaxRoot = syntaxRoot.ReplaceTokens(tokensToReplace.Keys, (original, rewritten) => tokensToReplace[original]);
            var newDocument   = document.WithSyntaxRoot(newSyntaxRoot.WithoutFormatting());

            return(newDocument);
        }
            protected override async Task <SyntaxNode> FixAllInDocumentAsync(FixAllContext fixAllContext, Document document, ImmutableArray <Diagnostic> diagnostics)
            {
                if (diagnostics.IsEmpty)
                {
                    return(null);
                }

                var indentationOptions = IndentationOptions.FromDocument(document);
                var syntaxRoot         = await document.GetSyntaxRootAsync(fixAllContext.CancellationToken).ConfigureAwait(false);

                var nodes = diagnostics.Select(diagnostic => syntaxRoot.FindNode(diagnostic.Location.SourceSpan, getInnermostNodeForTie: true).FirstAncestorOrSelf <AttributeListSyntax>());

                var newRoot = syntaxRoot.TrackNodes(nodes);

                foreach (var attributeList in nodes)
                {
                    var indentationSteps  = IndentationHelper.GetIndentationSteps(indentationOptions, attributeList);
                    var indentationTrivia = IndentationHelper.GenerateWhitespaceTrivia(indentationOptions, indentationSteps);
                    newRoot = newRoot.ReplaceNode(newRoot.GetCurrentNode(attributeList), GetNewAttributeList(attributeList, indentationTrivia));
                }

                return(newRoot);
            }
Пример #11
0
        private static ConstructorDeclarationSyntax ReformatConstructorDeclaration(ConstructorDeclarationSyntax constructorDeclaration, IndentationSettings indentationSettings, SyntaxTrivia newLine)
        {
            var constructorInitializer = constructorDeclaration.Initializer;

            var newParameterList = constructorDeclaration.ParameterList
                                   .WithTrailingTrivia(constructorDeclaration.ParameterList.GetTrailingTrivia().WithoutTrailingWhitespace().Add(newLine));

            var indentationSteps = IndentationHelper.GetIndentationSteps(indentationSettings, constructorDeclaration);
            var indentation      = IndentationHelper.GenerateWhitespaceTrivia(indentationSettings, indentationSteps + 1);

            var newColonTrailingTrivia = constructorInitializer.ColonToken.TrailingTrivia.WithoutTrailingWhitespace();

            var newColonToken = constructorInitializer.ColonToken
                                .WithLeadingTrivia(indentation)
                                .WithTrailingTrivia(newColonTrailingTrivia);

            var newInitializer = constructorInitializer
                                 .WithColonToken(newColonToken)
                                 .WithThisOrBaseKeyword(constructorInitializer.ThisOrBaseKeyword.WithLeadingTrivia(SyntaxFactory.Space));

            return(constructorDeclaration
                   .WithParameterList(newParameterList)
                   .WithInitializer(newInitializer));
        }
        private static async Task <Document> GetTransformedDocumentAsync(Document document, Diagnostic diagnostic, CancellationToken cancellationToken)
        {
            var syntaxRoot = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false);

            var settings = SettingsHelper.GetStyleCopSettings(document.Project.AnalyzerOptions, syntaxRoot.SyntaxTree, cancellationToken);

            var enumMemberDeclaration = (EnumMemberDeclarationSyntax)syntaxRoot.FindNode(diagnostic.Location.SourceSpan);
            var enumDeclaration       = (EnumDeclarationSyntax)enumMemberDeclaration.Parent;

            var memberIndex             = enumDeclaration.Members.IndexOf(enumMemberDeclaration);
            var precedingSeparatorToken = enumDeclaration.Members.GetSeparator(memberIndex - 1);

            // determine the indentation for enum members (which is parent + 1 step)
            var parentIndentationSteps = IndentationHelper.GetIndentationSteps(settings.Indentation, enumDeclaration);
            var indentation            = IndentationHelper.GenerateWhitespaceTrivia(settings.Indentation, parentIndentationSteps + 1);

            // combine all trivia between the separator and the enum member and place them after the separator, followed by a new line.
            var enumMemberDeclarationFirstToken = enumMemberDeclaration.GetFirstToken();
            var sharedTrivia = TriviaHelper.MergeTriviaLists(precedingSeparatorToken.TrailingTrivia, enumMemberDeclarationFirstToken.LeadingTrivia);

            var newTrailingTrivia = SyntaxFactory.TriviaList(sharedTrivia)
                                    .WithoutTrailingWhitespace()
                                    .Add(SyntaxFactory.CarriageReturnLineFeed);

            // replace the trivia for the tokens
            var replacements = new Dictionary <SyntaxToken, SyntaxToken>
            {
                [precedingSeparatorToken]         = precedingSeparatorToken.WithTrailingTrivia(newTrailingTrivia),
                [enumMemberDeclarationFirstToken] = enumMemberDeclarationFirstToken.WithLeadingTrivia(indentation),
            };

            var newSyntaxRoot = syntaxRoot.ReplaceTokens(replacements.Keys, (original, rewritten) => replacements[original]);
            var newDocument   = document.WithSyntaxRoot(newSyntaxRoot.WithoutFormatting());

            return(newDocument);
        }
Пример #13
0
        private static Dictionary <SyntaxToken, SyntaxToken> GenerateBraceFixes(IndentationSettings indentationSettings, ImmutableArray <SyntaxToken> braceTokens)
        {
            var tokenReplacements = new Dictionary <SyntaxToken, SyntaxToken>();

            foreach (var braceToken in braceTokens)
            {
                var braceLine             = LocationHelpers.GetLineSpan(braceToken).StartLinePosition.Line;
                var braceReplacementToken = braceToken;

                var indentationSteps = DetermineIndentationSteps(indentationSettings, braceToken);

                var previousToken = braceToken.GetPreviousToken();

                if (IsAccessorWithSingleLineBlock(previousToken, braceToken))
                {
                    var newTrailingTrivia = previousToken.TrailingTrivia
                                            .WithoutTrailingWhitespace()
                                            .Add(SyntaxFactory.Space);

                    AddReplacement(tokenReplacements, previousToken, previousToken.WithTrailingTrivia(newTrailingTrivia));

                    braceReplacementToken = braceReplacementToken.WithLeadingTrivia(braceToken.LeadingTrivia.WithoutLeadingWhitespace());
                }
                else
                {
                    // Check if we need to apply a fix before the brace
                    if (LocationHelpers.GetLineSpan(previousToken).StartLinePosition.Line == braceLine)
                    {
                        if (!braceTokens.Contains(previousToken))
                        {
                            var sharedTrivia = braceReplacementToken.LeadingTrivia.WithoutTrailingWhitespace();
                            var previousTokenNewTrailingTrivia = previousToken.TrailingTrivia
                                                                 .WithoutTrailingWhitespace()
                                                                 .AddRange(sharedTrivia)
                                                                 .Add(SyntaxFactory.CarriageReturnLineFeed);

                            AddReplacement(tokenReplacements, previousToken, previousToken.WithTrailingTrivia(previousTokenNewTrailingTrivia));
                        }

                        braceReplacementToken = braceReplacementToken.WithLeadingTrivia(IndentationHelper.GenerateWhitespaceTrivia(indentationSettings, indentationSteps));
                    }

                    // Check if we need to apply a fix after the brace. No fix is needed when:
                    // - The closing brace is followed by a semi-colon or closing paren
                    // - The closing brace is the last token in the file
                    var nextToken     = braceToken.GetNextToken();
                    var nextTokenLine = nextToken.IsKind(SyntaxKind.None) ? -1 : LocationHelpers.GetLineSpan(nextToken).StartLinePosition.Line;
                    var isMultiDimensionArrayInitializer = braceToken.IsKind(SyntaxKind.OpenBraceToken) && braceToken.Parent.IsKind(SyntaxKind.ArrayInitializerExpression) && braceToken.Parent.Parent.IsKind(SyntaxKind.ArrayInitializerExpression);

                    if ((nextTokenLine == braceLine) &&
                        (!braceToken.IsKind(SyntaxKind.CloseBraceToken) || !IsValidFollowingToken(nextToken)) &&
                        !isMultiDimensionArrayInitializer)
                    {
                        var sharedTrivia      = nextToken.LeadingTrivia.WithoutTrailingWhitespace();
                        var newTrailingTrivia = braceReplacementToken.TrailingTrivia
                                                .WithoutTrailingWhitespace()
                                                .AddRange(sharedTrivia)
                                                .Add(SyntaxFactory.CarriageReturnLineFeed);

                        if (!braceTokens.Contains(nextToken))
                        {
                            int newIndentationSteps = indentationSteps;
                            if (braceToken.IsKind(SyntaxKind.OpenBraceToken))
                            {
                                newIndentationSteps++;
                            }

                            if (nextToken.IsKind(SyntaxKind.CloseBraceToken))
                            {
                                newIndentationSteps = Math.Max(0, newIndentationSteps - 1);
                            }

                            AddReplacement(tokenReplacements, nextToken, nextToken.WithLeadingTrivia(IndentationHelper.GenerateWhitespaceTrivia(indentationSettings, newIndentationSteps)));
                        }

                        braceReplacementToken = braceReplacementToken.WithTrailingTrivia(newTrailingTrivia);
                    }
                }

                AddReplacement(tokenReplacements, braceToken, braceReplacementToken);
            }

            return(tokenReplacements);
        }
        private static Dictionary <SyntaxToken, SyntaxToken> GenerateBraceFixes(Document document, ImmutableArray <SyntaxToken> braceTokens)
        {
            var tokenReplacements = new Dictionary <SyntaxToken, SyntaxToken>();

            foreach (var braceToken in braceTokens)
            {
                var braceLine             = LocationHelpers.GetLineSpan(braceToken).StartLinePosition.Line;
                var braceReplacementToken = braceToken;

                var indentationOptions = IndentationOptions.FromDocument(document);
                var indentationSteps   = DetermineIndentationSteps(indentationOptions, braceToken);

                var previousToken = braceToken.GetPreviousToken();
                var nextToken     = braceToken.GetNextToken();

                if (IsAccessorWithSingleLineBlock(previousToken, braceToken))
                {
                    var newTrailingTrivia = previousToken.TrailingTrivia
                                            .WithoutTrailingWhitespace()
                                            .Add(SyntaxFactory.Space);

                    AddReplacement(tokenReplacements, previousToken, previousToken.WithTrailingTrivia(newTrailingTrivia));

                    braceReplacementToken = braceReplacementToken.WithLeadingTrivia(braceToken.LeadingTrivia.WithoutLeadingWhitespace());
                }
                else
                {
                    // Check if we need to apply a fix before the brace
                    if (LocationHelpers.GetLineSpan(previousToken).StartLinePosition.Line == braceLine)
                    {
                        if (!braceTokens.Contains(previousToken))
                        {
                            var sharedTrivia = braceReplacementToken.LeadingTrivia.WithoutTrailingWhitespace();
                            var previousTokenNewTrailingTrivia = previousToken.TrailingTrivia
                                                                 .WithoutTrailingWhitespace()
                                                                 .AddRange(sharedTrivia)
                                                                 .Add(SyntaxFactory.CarriageReturnLineFeed);

                            AddReplacement(tokenReplacements, previousToken, previousToken.WithTrailingTrivia(previousTokenNewTrailingTrivia));
                        }

                        braceReplacementToken = braceReplacementToken.WithLeadingTrivia(IndentationHelper.GenerateWhitespaceTrivia(indentationOptions, indentationSteps));
                    }

                    // Check if we need to apply a fix after the brace
                    // if a closing brace is followed by a semi-colon or closing paren, no fix is needed.
                    if ((LocationHelpers.GetLineSpan(nextToken).StartLinePosition.Line == braceLine) &&
                        (!braceToken.IsKind(SyntaxKind.CloseBraceToken) || !IsValidFollowingToken(nextToken)))
                    {
                        var sharedTrivia      = nextToken.LeadingTrivia.WithoutTrailingWhitespace();
                        var newTrailingTrivia = braceReplacementToken.TrailingTrivia
                                                .WithoutTrailingWhitespace()
                                                .AddRange(sharedTrivia)
                                                .Add(SyntaxFactory.CarriageReturnLineFeed);

                        if (!braceTokens.Contains(nextToken))
                        {
                            int newIndentationSteps;
                            if (braceToken.IsKind(SyntaxKind.OpenBraceToken))
                            {
                                newIndentationSteps = indentationSteps + 1;
                            }
                            else if (nextToken.IsKind(SyntaxKind.CloseBraceToken))
                            {
                                newIndentationSteps = Math.Max(0, indentationSteps - 1);
                            }
                            else
                            {
                                newIndentationSteps = indentationSteps;
                            }

                            AddReplacement(tokenReplacements, nextToken, nextToken.WithLeadingTrivia(IndentationHelper.GenerateWhitespaceTrivia(indentationOptions, newIndentationSteps)));
                        }

                        braceReplacementToken = braceReplacementToken.WithTrailingTrivia(newTrailingTrivia);
                    }
                }

                AddReplacement(tokenReplacements, braceToken, braceReplacementToken);
            }

            return(tokenReplacements);
        }
Пример #15
0
        private static async Task <Document> GetTransformedDocumentAsync(Document document, Diagnostic diagnostic, CancellationToken cancellationToken)
        {
            var syntaxRoot = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false);

            var curlyBracketToken            = syntaxRoot.FindToken(diagnostic.Location.SourceSpan.Start);
            var curlyBracketLine             = curlyBracketToken.GetLocation().GetLineSpan().StartLinePosition.Line;
            var curlyBracketReplacementToken = curlyBracketToken;

            var indentationOptions = IndentationOptions.FromDocument(document);
            var indentationSteps   = DetermineIndentationSteps(indentationOptions, curlyBracketToken);

            var previousToken = curlyBracketToken.GetPreviousToken();
            var nextToken     = curlyBracketToken.GetNextToken();

            var rewriter = new Rewriter();

            if (IsAccessorWithSingleLineBlock(previousToken, curlyBracketToken))
            {
                var newTrailingTrivia = previousToken.TrailingTrivia
                                        .WithoutTrailingWhitespace()
                                        .Add(SyntaxFactory.Space);

                rewriter.AddReplacement(previousToken, previousToken.WithTrailingTrivia(newTrailingTrivia));

                curlyBracketReplacementToken = curlyBracketReplacementToken.WithLeadingTrivia(curlyBracketToken.LeadingTrivia.WithoutLeadingWhitespace());
            }
            else
            {
                // Check if we need to apply a fix before the curly bracket
                if (previousToken.GetLocation().GetLineSpan().StartLinePosition.Line == curlyBracketLine)
                {
                    var sharedTrivia = curlyBracketReplacementToken.LeadingTrivia.WithoutTrailingWhitespace();
                    var previousTokenNewTrailingTrivia = previousToken.TrailingTrivia
                                                         .WithoutTrailingWhitespace()
                                                         .AddRange(sharedTrivia)
                                                         .Add(SyntaxFactory.CarriageReturnLineFeed);

                    rewriter.AddReplacement(previousToken, previousToken.WithTrailingTrivia(previousTokenNewTrailingTrivia));

                    curlyBracketReplacementToken = curlyBracketReplacementToken.WithLeadingTrivia(IndentationHelper.GenerateWhitespaceTrivia(indentationOptions, indentationSteps));
                }

                // Check if we need to apply a fix after the curly bracket
                // if a closing curly bracket is followed by a semi-colon or closing paren, no fix is needed.
                if ((nextToken.GetLocation().GetLineSpan().StartLinePosition.Line == curlyBracketLine) &&
                    (!curlyBracketToken.IsKind(SyntaxKind.CloseBraceToken) || !IsValidFollowingToken(nextToken)))
                {
                    var sharedTrivia      = nextToken.LeadingTrivia.WithoutTrailingWhitespace();
                    var newTrailingTrivia = curlyBracketReplacementToken.TrailingTrivia
                                            .WithoutTrailingWhitespace()
                                            .AddRange(sharedTrivia)
                                            .Add(SyntaxFactory.CarriageReturnLineFeed);

                    int newIndentationSteps;
                    if (curlyBracketToken.IsKind(SyntaxKind.OpenBraceToken))
                    {
                        newIndentationSteps = indentationSteps + 1;
                    }
                    else if (nextToken.IsKind(SyntaxKind.CloseBraceToken))
                    {
                        newIndentationSteps = Math.Max(0, indentationSteps - 1);
                    }
                    else
                    {
                        newIndentationSteps = indentationSteps;
                    }

                    rewriter.AddReplacement(nextToken, nextToken.WithLeadingTrivia(IndentationHelper.GenerateWhitespaceTrivia(indentationOptions, newIndentationSteps)));

                    curlyBracketReplacementToken = curlyBracketReplacementToken.WithTrailingTrivia(newTrailingTrivia);
                }
            }

            rewriter.AddReplacement(curlyBracketToken, curlyBracketReplacementToken);

            var newSyntaxRoot = rewriter.Visit(syntaxRoot).WithoutFormatting();

            return(document.WithSyntaxRoot(newSyntaxRoot));
        }