예제 #1
0
        private static Task <Document> RefactorAsync(
            Document document,
            StatementListInfo statementsInfo,
            StatementSyntax statement,
            InitializerExpressionSyntax initializer,
            ExpressionSyntax initializedExpression,
            CancellationToken cancellationToken)
        {
            ExpressionStatementSyntax[] expressions = CreateExpressionStatements(initializer, initializedExpression).ToArray();

            expressions[expressions.Length - 1] = expressions[expressions.Length - 1]
                                                  .WithTrailingTrivia(statement.GetTrailingTrivia());

            var objectCreationExpression = (ObjectCreationExpressionSyntax)initializer.Parent;

            ObjectCreationExpressionSyntax newObjectCreationExpression = objectCreationExpression.WithInitializer(null);

            if (newObjectCreationExpression.ArgumentList == null)
            {
                TypeSyntax type = newObjectCreationExpression.Type;

                newObjectCreationExpression = newObjectCreationExpression
                                              .WithArgumentList(ArgumentList().WithTrailingTrivia(type.GetTrailingTrivia()))
                                              .WithType(type.WithoutTrailingTrivia());
            }

            SyntaxList <StatementSyntax> statements = statementsInfo.Statements;

            int index = statements.IndexOf(statement);

            StatementSyntax newStatement = statement.ReplaceNode(objectCreationExpression, newObjectCreationExpression);

            SyntaxKind statementKind = statement.Kind();

            if (statementKind == SyntaxKind.ExpressionStatement)
            {
                var expressionStatement = (ExpressionStatementSyntax)newStatement;

                newStatement = expressionStatement
                               .WithExpression(expressionStatement.Expression.WithoutTrailingTrivia());
            }
            else if (statementKind == SyntaxKind.LocalDeclarationStatement)
            {
                var localDeclaration = (LocalDeclarationStatementSyntax)newStatement;

                newStatement = localDeclaration
                               .WithDeclaration(localDeclaration.Declaration.WithoutTrailingTrivia());
            }

            SyntaxList <StatementSyntax> newStatements = statements.Replace(statement, newStatement);

            SyntaxNode newNode = statementsInfo
                                 .WithStatements(newStatements.InsertRange(index + 1, expressions))
                                 .Parent
                                 .WithFormatterAnnotation();

            return(document.ReplaceNodeAsync(statementsInfo.Parent, newNode, cancellationToken));
        }
예제 #2
0
        public static Task <Document> RefactorAsync(
            Document document,
            ObjectCreationExpressionSyntax objectCreationExpression,
            CancellationToken cancellationToken)
        {
            ArgumentListSyntax          argumentList = objectCreationExpression.ArgumentList;
            InitializerExpressionSyntax initializer  = objectCreationExpression.Initializer;

            ObjectCreationExpressionSyntax newNode = objectCreationExpression.WithInitializer(null);

            if (argumentList == null)
            {
                TypeSyntax type = objectCreationExpression.Type;

                SyntaxTriviaList trailingTrivia = type.GetTrailingTrivia();

                ArgumentListSyntax newArgumentList = SyntaxFactory.ArgumentList();

                IEnumerable <SyntaxTrivia> trivia = objectCreationExpression.DescendantTrivia(TextSpan.FromBounds(type.Span.End, initializer.Span.End));

                if (trivia.Any(f => !f.IsWhitespaceOrEndOfLineTrivia()))
                {
                    newArgumentList = newArgumentList.WithTrailingTrivia(trivia);
                }

                newNode = newNode
                          .WithType(type.WithoutTrailingTrivia())
                          .WithArgumentList(newArgumentList);
            }
            else
            {
                IEnumerable <SyntaxTrivia> trivia = objectCreationExpression.DescendantTrivia(TextSpan.FromBounds(argumentList.Span.End, initializer.Span.End));

                if (trivia.Any(f => !f.IsWhitespaceOrEndOfLineTrivia()))
                {
                    newNode = newNode.WithTrailingTrivia(trivia);
                }
                else
                {
                    newNode = newNode.WithoutTrailingTrivia();
                }
            }

            newNode = newNode
                      .AppendToTrailingTrivia(initializer.GetTrailingTrivia())
                      .WithFormatterAnnotation();

            return(document.ReplaceNodeAsync(objectCreationExpression, newNode, cancellationToken));
        }
예제 #3
0
 private PropertyDeclarationSyntax WrapProperty()
 {
     return(PropertyDeclaration(type, variable.Identifier)
            .WithTrailingTrivia(CarriageReturnLineFeed)
            .WithModifiers(TokenList(Token(SyntaxKind.PublicKeyword).WithTrailingTrivia(Whitespace(" "))))
            .AddAccessorListAccessors(
                AccessorDeclaration(SyntaxKind.GetAccessorDeclaration)
                .WithLeadingTrivia(CarriageReturnLineFeed, Tab)
                .WithBody(Block(ReturnStatement(CastExpression(type.WithoutTrailingTrivia(), InvocationExpression(Program.GetValue, ArgumentList(SingletonSeparatedList(Argument(dpName)))))
                                                .WithLeadingTrivia(Whitespace(" ")))
                                .WithLeadingTrivia(Whitespace(" "))
                                .WithTrailingTrivia(Whitespace(" ")))),
                AccessorDeclaration(SyntaxKind.SetAccessorDeclaration)
                .WithModifiers(dpKey != null ? TokenList(Token(SyntaxKind.PrivateKeyword).WithTrailingTrivia(Whitespace(" "))) : TokenList())
                .WithLeadingTrivia(CarriageReturnLineFeed, Tab)
                .WithBody(Block(ExpressionStatement(InvocationExpression(Program.SetValue, ArgumentList(SeparatedList(new ArgumentSyntax[] { Argument(dpKey ?? dpName), Argument(IdentifierName("value")).WithLeadingTrivia(Whitespace(" ")) }))))
                                .WithLeadingTrivia(Whitespace(" "))
                                .WithTrailingTrivia(Whitespace(" "))))
                .WithTrailingTrivia(CarriageReturnLineFeed)));
 }
        public sealed override async Task RegisterCodeFixesAsync(CodeFixContext context)
        {
            Diagnostic diagnostic = context.Diagnostics[0];

            if (!Settings.IsEnabled(diagnostic.Id, CodeFixIdentifiers.MoveInitializerExpressionsToConstructor))
            {
                return;
            }

            SyntaxNode root = await context.GetSyntaxRootAsync().ConfigureAwait(false);

            ObjectCreationExpressionSyntax objectCreationExpression = root
                                                                      .FindNode(context.Span, getInnermostNodeForTie: true)?
                                                                      .FirstAncestorOrSelf <ObjectCreationExpressionSyntax>();

            if (objectCreationExpression == null)
            {
                return;
            }

            switch (diagnostic.Id)
            {
            case CompilerDiagnosticIdentifiers.ThereIsNoArgumentGivenThatCorrespondsToRequiredFormalParameter:
            {
                if (!Settings.IsEnabled(diagnostic.Id, CodeFixIdentifiers.MoveInitializerExpressionsToConstructor))
                {
                    break;
                }

                if (!objectCreationExpression.Type.Span.Contains(diagnostic.Location.SourceSpan))
                {
                    return;
                }

                ArgumentListSyntax argumentList = objectCreationExpression.ArgumentList;

                if (argumentList?.Arguments.Any() == true)
                {
                    return;
                }

                InitializerExpressionSyntax initializer = objectCreationExpression.Initializer;

                if (initializer == null)
                {
                    return;
                }

                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                List <ExpressionSyntax> expressions = null;

                foreach (ExpressionSyntax expression in initializer.Expressions)
                {
                    if (expression is AssignmentExpressionSyntax assignment &&
                        semanticModel.GetDiagnostic(
                            CompilerDiagnosticIdentifiers.PropertyOrIndexerCannotBeUsedInThisContextBecauseSetAccessorIsAccessible,
                            assignment.Left.Span,
                            context.CancellationToken) != null)
                    {
                        (expressions ??= new List <ExpressionSyntax>()).Add(expression);
                    }
                }

                if (expressions == null)
                {
                    return;
                }

                TypeSyntax type = objectCreationExpression.Type;

                if (argumentList == null)
                {
                    argumentList = ArgumentList().WithTrailingTrivia(type.GetTrailingTrivia());
                    type         = type.WithoutTrailingTrivia();
                }

                SeparatedSyntaxList <ArgumentSyntax> arguments = expressions
                                                                 .Select(f => Argument(((AssignmentExpressionSyntax)f).Right))
                                                                 .ToSeparatedSyntaxList();

                argumentList = argumentList.WithArguments(arguments);

                ObjectCreationExpressionSyntax newObjectCreationExpression = objectCreationExpression.Update(
                    objectCreationExpression.NewKeyword,
                    type,
                    argumentList,
                    initializer);

                SymbolInfo symbolInfo = semanticModel.GetSpeculativeSymbolInfo(
                    objectCreationExpression.SpanStart,
                    newObjectCreationExpression,
                    SpeculativeBindingOption.BindAsExpression);

                if (symbolInfo.Symbol is IMethodSymbol methodSymbol &&
                    methodSymbol.MethodKind == MethodKind.Constructor)
                {
                    CodeAction codeAction = CodeAction.Create(
                        "Move initializer expressions to constructor",
                        ct =>
                        {
                            InitializerExpressionSyntax newInitializer = initializer.RemoveNodes(expressions, SyntaxRefactorings.DefaultRemoveOptions);

                            if (newInitializer.Expressions.Count == 0 &&
                                newInitializer
                                .DescendantTrivia(TextSpan.FromBounds(newInitializer.OpenBraceToken.SpanStart, newInitializer.CloseBraceToken.SpanStart))
                                .All(f => f.IsWhitespaceOrEndOfLineTrivia()))
                            {
                                newInitializer = null;

                                ArgumentListSyntax newArgumentList = newObjectCreationExpression
                                                                     .ArgumentList
                                                                     .TrimTrailingTrivia()
                                                                     .AppendToTrailingTrivia(initializer.GetTrailingTrivia());

                                newObjectCreationExpression = newObjectCreationExpression
                                                              .WithArgumentList(newArgumentList);
                            }

                            newObjectCreationExpression = newObjectCreationExpression
                                                          .WithInitializer(newInitializer)
                                                          .WithFormatterAnnotation();

                            return(context.Document.ReplaceNodeAsync(objectCreationExpression, newObjectCreationExpression, ct));
                        },
                        GetEquivalenceKey(diagnostic));

                    context.RegisterCodeFix(codeAction, diagnostic);
                }

                break;
            }
            }
        }