public static async Task ComputeRefactoringAsync(RefactoringContext context, InvocationExpressionSyntax invocationExpression)
        {
            SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

            var methodSymbol = semanticModel.GetSymbolInfo(invocationExpression, context.CancellationToken).Symbol as IMethodSymbol;

            if (methodSymbol == null)
            {
                return;
            }

            INamedTypeSymbol enumerable = semanticModel.Compilation.GetTypeByMetadataName("System.Linq.Enumerable");

            if (enumerable == null)
            {
                return;
            }

            int argumentIndex = (methodSymbol.ReducedFrom != null) ? 0 : 1;

            methodSymbol = methodSymbol.ReducedFrom ?? methodSymbol.ConstructedFrom;

            if (methodSymbol.Equals(GetMethod(enumerable, "Any")))
            {
                ExpressionSyntax expression = GetExpression(invocationExpression, argumentIndex);

                if (expression != null)
                {
                    context.RegisterRefactoring(
                        "Replace 'Any' with 'All'",
                        cancellationToken =>
                    {
                        return(RefactorAsync(
                                   context.Document,
                                   invocationExpression,
                                   "All",
                                   expression,
                                   cancellationToken));
                    });
                }
            }
            else if (methodSymbol.Equals(GetMethod(enumerable, "All")))
            {
                ExpressionSyntax expression = GetExpression(invocationExpression, argumentIndex);

                if (expression != null)
                {
                    context.RegisterRefactoring(
                        "Replace 'All' with 'Any'",
                        cancellationToken =>
                    {
                        return(RefactorAsync(
                                   context.Document,
                                   invocationExpression,
                                   "Any",
                                   expression,
                                   cancellationToken));
                    });
                }
            }
        }
Exemplo n.º 2
0
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, InitializerExpressionSyntax initializer)
        {
            if (initializer.IsKind(SyntaxKind.ComplexElementInitializerExpression) &&
                initializer.IsParentKind(SyntaxKind.CollectionInitializerExpression))
            {
                initializer = (InitializerExpressionSyntax)initializer.Parent;
            }

            if (context.Span.IsEmptyAndContainedInSpanOrBetweenSpans(initializer) ||
                context.Span.IsEmptyAndContainedInSpanOrBetweenSpans(initializer.Expressions))
            {
                SeparatedSyntaxList <ExpressionSyntax> expressions = initializer.Expressions;

                if (context.IsRefactoringEnabled(RefactoringDescriptors.WrapInitializerExpressions) &&
                    expressions.Any() &&
                    !initializer.IsKind(SyntaxKind.ComplexElementInitializerExpression) &&
                    initializer.IsParentKind(
                        SyntaxKind.ArrayCreationExpression,
                        SyntaxKind.ImplicitArrayCreationExpression,
                        SyntaxKind.ObjectCreationExpression,
                        SyntaxKind.CollectionInitializerExpression,
                        SyntaxKind.WithExpression))
                {
                    if (initializer.IsSingleLine(includeExteriorTrivia: false))
                    {
                        context.RegisterRefactoring(
                            "Wrap initializer expression",
                            ct => SyntaxFormatter.ToMultiLineAsync(context.Document, initializer, ct),
                            RefactoringDescriptors.WrapInitializerExpressions);
                    }
                    else if (expressions.All(expression => expression.IsSingleLine()) &&
                             initializer.DescendantTrivia(initializer.Span).All(f => f.IsWhitespaceOrEndOfLineTrivia()))
                    {
                        context.RegisterRefactoring(
                            "Unwrap initializer expressions",
                            ct => SyntaxFormatter.ToSingleLineAsync(
                                context.Document,
                                initializer.Parent,
                                TextSpan.FromBounds(initializer.OpenBraceToken.GetPreviousToken().Span.End, initializer.CloseBraceToken.Span.End),
                                ct),
                            RefactoringDescriptors.WrapInitializerExpressions);
                    }
                }

                if (context.IsRefactoringEnabled(RefactoringDescriptors.AddAllPropertiesToInitializer) &&
                    initializer.IsKind(SyntaxKind.ObjectInitializerExpression, SyntaxKind.WithInitializerExpression) &&
                    AddAllPropertiesToInitializerRefactoring.IsApplicableSpan(initializer, context.Span))
                {
                    SemanticModel semanticModdel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                    AddAllPropertiesToInitializerRefactoring.ComputeRefactorings(context, initializer, semanticModdel);
                }

                await ExpandInitializerRefactoring.ComputeRefactoringsAsync(context, initializer).ConfigureAwait(false);

                if (context.IsRefactoringEnabled(RefactoringDescriptors.UseIndexInitializer) &&
                    context.SupportsCSharp6)
                {
                    await UseIndexInitializerRefactoring.ComputeRefactoringAsync(context, initializer).ConfigureAwait(false);
                }
            }
        }
Exemplo n.º 3
0
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, BinaryExpressionSyntax binaryExpression)
        {
            if (context.IsRefactoringEnabled(RefactoringIdentifiers.NegateOperator))
            {
                SyntaxToken operatorToken = binaryExpression.OperatorToken;

                if (operatorToken.Span.Contains(context.Span) &&
                    NegateOperatorRefactoring.CanBeNegated(operatorToken))
                {
                    context.RegisterRefactoring(
                        "Negate operator",
                        cancellationToken => NegateOperatorRefactoring.RefactorAsync(context.Document, operatorToken, cancellationToken));
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.FormatBinaryExpression))
            {
                FormatBinaryExpressionRefactoring.ComputeRefactorings(context, binaryExpression);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.NegateBinaryExpression))
            {
                NegateBinaryExpressionRefactoring.ComputeRefactoring(context, binaryExpression);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ExpandCoalesceExpression) &&
                binaryExpression.OperatorToken.Span.Contains(context.Span))
            {
                ExpandCoalesceExpressionRefactoring.ComputeRefactoring(context, binaryExpression);
            }

            if (context.IsAnyRefactoringEnabled(
                    RefactoringIdentifiers.JoinStringExpressions,
                    RefactoringIdentifiers.UseStringBuilderInsteadOfConcatenation) &&
                context.Span.IsBetweenSpans(binaryExpression) &&
                binaryExpression.IsKind(SyntaxKind.AddExpression))
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                StringConcatenationExpression concatenation;
                if (StringConcatenationExpression.TryCreate(binaryExpression, semanticModel, out concatenation, context.CancellationToken))
                {
                    if (context.IsRefactoringEnabled(RefactoringIdentifiers.JoinStringExpressions))
                    {
                        JoinStringExpressionsRefactoring.ComputeRefactoring(context, concatenation);
                    }

                    if (context.IsRefactoringEnabled(RefactoringIdentifiers.UseStringBuilderInsteadOfConcatenation))
                    {
                        UseStringBuilderInsteadOfConcatenationRefactoring.ComputeRefactoring(context, concatenation);
                    }
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.SwapExpressionsInBinaryExpression) &&
                context.Span.IsBetweenSpans(binaryExpression))
            {
                SwapExpressionsInBinaryExpressionRefactoring.ComputeRefactoring(context, binaryExpression);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ReplaceAsWithCast) &&
                context.Span.IsEmptyAndContainedInSpanOrBetweenSpans(binaryExpression))
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                if (ReplaceAsWithCastRefactoring.CanRefactor(binaryExpression, semanticModel, context.CancellationToken))
                {
                    context.RegisterRefactoring(
                        "Replace as with cast",
                        cancellationToken => ReplaceAsWithCastRefactoring.RefactorAsync(context.Document, binaryExpression, context.CancellationToken));
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.NegateIsExpression))
            {
                NegateIsExpressionRefactoring.ComputeRefactoring(context, binaryExpression);
            }

            if (context.Span.IsContainedInSpanOrBetweenSpans(binaryExpression.OperatorToken))
            {
                if (context.IsRefactoringEnabled(RefactoringIdentifiers.ReplaceEqualsExpressionWithStringEquals))
                {
                    await ReplaceEqualsExpressionWithStringEqualsRefactoring.ComputeRefactoringAsync(context, binaryExpression).ConfigureAwait(false);
                }

                if (context.IsAnyRefactoringEnabled(
                        RefactoringIdentifiers.ReplaceEqualsExpressionWithStringIsNullOrEmpty,
                        RefactoringIdentifiers.ReplaceEqualsExpressionWithStringIsNullOrWhiteSpace))
                {
                    await ReplaceEqualsExpressionRefactoring.ComputeRefactoringsAsync(context, binaryExpression).ConfigureAwait(false);
                }
            }

            if (!context.Span.IsBetweenSpans(binaryExpression) &&
                context.IsAnyRefactoringEnabled(
                    RefactoringIdentifiers.ExtractExpressionFromCondition,
                    RefactoringIdentifiers.JoinStringExpressions))
            {
                BinaryExpressionSelection binaryExpressionSelection = BinaryExpressionSelection.Create(binaryExpression, context.Span);

                if (binaryExpressionSelection.Expressions.Length > 1)
                {
                    if (context.IsRefactoringEnabled(RefactoringIdentifiers.ExtractExpressionFromCondition))
                    {
                        ExtractConditionRefactoring.ComputeRefactoring(context, binaryExpressionSelection);
                    }

                    if (context.IsRefactoringEnabled(RefactoringIdentifiers.JoinStringExpressions) &&
                        binaryExpression.IsKind(SyntaxKind.AddExpression))
                    {
                        SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                        StringConcatenationExpression concatenation;
                        if (StringConcatenationExpression.TryCreate(binaryExpressionSelection, semanticModel, out concatenation, context.CancellationToken))
                        {
                            JoinStringExpressionsRefactoring.ComputeRefactoring(context, concatenation);
                        }
                    }
                }
            }
        }
        public static async Task <bool> CanRefactorAsync(RefactoringContext context, ForStatementSyntax forStatement)
        {
            VariableDeclaratorSyntax variableDeclarator = forStatement
                                                          .Declaration?
                                                          .Variables
                                                          .SingleOrDefault(shouldThrow: false);

            if (variableDeclarator == null)
            {
                return(false);
            }

            if (variableDeclarator.Initializer?.Value?.IsNumericLiteralExpression("0") != true)
            {
                return(false);
            }

            ExpressionSyntax condition = forStatement.Condition;

            if (condition?.IsKind(SyntaxKind.LessThanExpression) != true)
            {
                return(false);
            }

            ExpressionSyntax right = ((BinaryExpressionSyntax)condition).Right;

            if (right?.IsKind(SyntaxKind.SimpleMemberAccessExpression) != true)
            {
                return(false);
            }

            var memberAccessExpression = (MemberAccessExpressionSyntax)right;

            string memberName = memberAccessExpression.Name?.Identifier.ValueText;

            if (memberName != "Count" && memberName != "Length")
            {
                return(false);
            }

            ExpressionSyntax expression = memberAccessExpression.Expression;

            if (expression == null)
            {
                return(false);
            }

            if (forStatement.Incrementors.SingleOrDefault(shouldThrow: false)?.IsKind(SyntaxKind.PostIncrementExpression) != true)
            {
                return(false);
            }

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

            ISymbol symbol = semanticModel.GetSymbol(expression, context.CancellationToken);

            if (symbol == null)
            {
                return(false);
            }

            ISymbol variableSymbol = semanticModel.GetDeclaredSymbol(variableDeclarator, context.CancellationToken);

            ImmutableArray <SyntaxNode> nodes = await SyntaxFinder.FindReferencesAsync(variableSymbol, context.Document, cancellationToken : context.CancellationToken).ConfigureAwait(false);

            TextSpan span = forStatement.Statement.Span;

            foreach (SyntaxNode node in nodes)
            {
                if (span.Contains(node.Span) &&
                    !IsElementAccess(node, symbol, semanticModel, context.CancellationToken))
                {
                    return(false);
                }
            }

            return(true);
        }
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, SyntaxToken modifier)
        {
            SyntaxNode node = modifier.Parent;

            if (node.IsKind(SyntaxKind.DestructorDeclaration))
            {
                return;
            }

            ModifierListInfo modifiersInfo = SyntaxInfo.ModifierListInfo(node);

            if (node.IsKind(
                    SyntaxKind.ClassDeclaration,
                    SyntaxKind.InterfaceDeclaration,
                    SyntaxKind.StructDeclaration,
                    SyntaxKind.RecordStructDeclaration))
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                var symbol = (INamedTypeSymbol)semanticModel.GetDeclaredSymbol(node, context.CancellationToken);

                ImmutableArray <SyntaxReference> syntaxReferences = symbol.DeclaringSyntaxReferences;

                if (syntaxReferences.Length > 1)
                {
                    ImmutableArray <MemberDeclarationSyntax> memberDeclarations = ImmutableArray.CreateRange(
                        syntaxReferences,
                        f => (MemberDeclarationSyntax)f.GetSyntax(context.CancellationToken));

                    foreach (Accessibility accessibility in AvailableAccessibilities)
                    {
                        if (accessibility != modifiersInfo.ExplicitAccessibility &&
                            SyntaxAccessibility.IsValidAccessibility(node, accessibility))
                        {
                            context.RegisterRefactoring(
                                GetTitle(accessibility),
                                ct => RefactorAsync(context.Solution, memberDeclarations, accessibility, ct),
                                RefactoringDescriptors.ChangeAccessibility,
                                accessibility.ToString());
                        }
                    }

                    return;
                }
            }

            foreach (Accessibility accessibility in AvailableAccessibilities)
            {
                if (accessibility == modifiersInfo.ExplicitAccessibility)
                {
                    continue;
                }

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

                ISymbol symbol = GetBaseSymbolOrDefault(semanticModel, context.CancellationToken);

                if (symbol != null)
                {
                    if (SyntaxAccessibility.IsValidAccessibility(node, accessibility, ignoreOverride: true))
                    {
                        context.RegisterRefactoring(
                            GetTitle(accessibility),
                            ct => RefactorAsync(context.Solution, symbol, accessibility, ct),
                            RefactoringDescriptors.ChangeAccessibility,
                            accessibility.ToString());
                    }
                }
                else if (SyntaxAccessibility.IsValidAccessibility(node, accessibility))
                {
                    context.RegisterRefactoring(
                        GetTitle(accessibility),
                        ct => RefactorAsync(context.Document, node, accessibility, ct),
                        RefactoringDescriptors.ChangeAccessibility,
                        accessibility.ToString());
                }
            }

            ISymbol GetBaseSymbolOrDefault(SemanticModel semanticModel, CancellationToken cancellationToken)
            {
                if (modifiersInfo.GetFilter().HasAnyFlag(ModifierFilter.AbstractVirtualOverride))
                {
                    return(ChangeAccessibilityRefactoring.GetBaseSymbolOrDefault(node, semanticModel, cancellationToken));
                }

                return(null);
            }
        }
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, ForEachStatementSyntax forEachStatement)
        {
            if (context.SupportsSemanticModel)
            {
                if (context.IsRefactoringEnabled(RefactoringIdentifiers.ChangeTypeAccordingToExpression))
                {
                    await ChangeTypeAccordingToExpressionAsync(context, forEachStatement).ConfigureAwait(false);
                }

                if (context.IsAnyRefactoringEnabled(
                        RefactoringIdentifiers.ChangeExplicitTypeToVar,
                        RefactoringIdentifiers.ChangeVarToExplicitType))
                {
                    await ChangeTypeAsync(context, forEachStatement).ConfigureAwait(false);
                }

                if (context.IsRefactoringEnabled(RefactoringIdentifiers.RenameIdentifierAccordingToTypeName))
                {
                    await RenameIdentifierAccordingToTypeNameAsync(context, forEachStatement).ConfigureAwait(false);
                }

                if (context.IsRefactoringEnabled(RefactoringIdentifiers.ReplaceForEachWithFor) &&
                    context.Span.IsEmpty &&
                    ReplaceForEachWithForRefactoring.CanRefactor(forEachStatement, await context.GetSemanticModelAsync().ConfigureAwait(false), context.CancellationToken))
                {
                    context.RegisterRefactoring(
                        "Replace foreach with for",
                        cancellationToken => ReplaceForEachWithForRefactoring.RefactorAsync(context.Document, forEachStatement, cancellationToken));
                }
            }
        }
Exemplo n.º 7
0
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, MethodDeclarationSyntax methodDeclaration)
        {
            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ChangeMethodReturnTypeToVoid) &&
                context.Span.IsEmptyAndContainedInSpan(methodDeclaration))
            {
                await ChangeMethodReturnTypeToVoidRefactoring.ComputeRefactoringAsync(context, methodDeclaration).ConfigureAwait(false);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.AddTypeParameter))
            {
                AddTypeParameterRefactoring.ComputeRefactoring(context, methodDeclaration);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ReplaceMethodWithProperty) &&
                methodDeclaration.HeaderSpan().Contains(context.Span) &&
                ReplaceMethodWithPropertyRefactoring.CanRefactor(methodDeclaration))
            {
                context.RegisterRefactoring(
                    $"Replace '{methodDeclaration.Identifier.ValueText}' with property",
                    cancellationToken => ReplaceMethodWithPropertyRefactoring.RefactorAsync(context.Document, methodDeclaration, cancellationToken),
                    RefactoringIdentifiers.ReplaceMethodWithProperty);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ConvertBlockBodyToExpressionBody) &&
                context.SupportsCSharp6 &&
                ConvertBlockBodyToExpressionBodyRefactoring.CanRefactor(methodDeclaration, context.Span))
            {
                context.RegisterRefactoring(
                    ConvertBlockBodyToExpressionBodyRefactoring.Title,
                    cancellationToken => ConvertBlockBodyToExpressionBodyRefactoring.RefactorAsync(context.Document, methodDeclaration, cancellationToken),
                    RefactoringIdentifiers.ConvertBlockBodyToExpressionBody);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.MakeMemberAbstract) &&
                context.Span.IsEmptyAndContainedInSpan(methodDeclaration.Identifier))
            {
                MakeMethodAbstractRefactoring.ComputeRefactoring(context, methodDeclaration);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.MakeMemberVirtual) &&
                methodDeclaration.HeaderSpan().Contains(context.Span))
            {
                MakeMethodVirtualRefactoring.ComputeRefactoring(context, methodDeclaration);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.CopyDocumentationCommentFromBaseMember) &&
                methodDeclaration.HeaderSpan().Contains(context.Span) &&
                !methodDeclaration.HasDocumentationComment())
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                CopyDocumentationCommentFromBaseMemberRefactoring.ComputeRefactoring(context, methodDeclaration, semanticModel);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.RenameMethodAccordingToTypeName))
            {
                await RenameMethodAccordingToTypeNameAsync(context, methodDeclaration).ConfigureAwait(false);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.AddParameterToInterfaceMember) &&
                context.Span.IsEmptyAndContainedInSpanOrBetweenSpans(methodDeclaration.Identifier))
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                foreach (CodeAction codeAction in AddParameterToInterfaceMemberRefactoring.ComputeRefactoringForImplicitImplementation(
                             new CommonFixContext(context.Document, RefactoringIdentifiers.AddParameterToInterfaceMember, semanticModel, context.CancellationToken),
                             methodDeclaration))
                {
                    context.RegisterRefactoring(codeAction);
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.AddMemberToInterface) &&
                context.Span.IsEmptyAndContainedInSpanOrBetweenSpans(methodDeclaration.Identifier))
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                AddMemberToInterfaceRefactoring.ComputeRefactoring(context, methodDeclaration, semanticModel);
            }
        }
Exemplo n.º 8
0
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, IfStatementSyntax ifStatement)
        {
            if (ifStatement.IsTopmostIf() &&
                (context.Span.IsEmptyAndContainedInSpan(ifStatement.IfKeyword) || context.Span.IsBetweenSpans(ifStatement)))
            {
                if (context.IsAnyRefactoringEnabled(
                        RefactoringIdentifiers.UseCoalesceExpressionInsteadOfIf,
                        RefactoringIdentifiers.UseConditionalExpressionInsteadOfIf,
                        RefactoringIdentifiers.SimplifyIf))
                {
                    SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                    var options = new IfAnalysisOptions(
                        useCoalesceExpression: context.IsRefactoringEnabled(RefactoringIdentifiers.UseCoalesceExpressionInsteadOfIf),
                        useConditionalExpression: context.IsRefactoringEnabled(RefactoringIdentifiers.UseConditionalExpressionInsteadOfIf),
                        useBooleanExpression: context.IsRefactoringEnabled(RefactoringIdentifiers.SimplifyIf),
                        useExpression: false);

                    foreach (IfRefactoring refactoring in IfRefactoring.Analyze(ifStatement, options, semanticModel, context.CancellationToken))
                    {
                        context.RegisterRefactoring(
                            refactoring.Title,
                            cancellationToken => refactoring.RefactorAsync(context.Document, cancellationToken));
                    }
                }

                if (context.IsRefactoringEnabled(RefactoringIdentifiers.SwapStatementsInIfElse))
                {
                    SwapStatementInIfElseRefactoring.ComputeRefactoring(context, ifStatement);
                }

                if (context.IsRefactoringEnabled(RefactoringIdentifiers.ReplaceIfWithSwitch))
                {
                    await ReplaceIfWithSwitchRefactoring.ComputeRefactoringAsync(context, ifStatement).ConfigureAwait(false);
                }

                if (context.IsRefactoringEnabled(RefactoringIdentifiers.SplitIfStatement))
                {
                    SplitIfStatementRefactoring.ComputeRefactoring(context, ifStatement);
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ReduceIfNesting) &&
                context.Span.IsEmptyAndContainedInSpanOrBetweenSpans(ifStatement.IfKeyword))
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                ReduceIfNestingAnalysis analysis = ReduceIfNestingRefactoring.Analyze(
                    ifStatement,
                    semanticModel,
                    options: ReduceIfNestingOptions.AllowNestedFix
                    | ReduceIfNestingOptions.AllowIfInsideIfElse
                    | ReduceIfNestingOptions.AllowLoop
                    | ReduceIfNestingOptions.AllowSwitchSection,
                    taskSymbol: semanticModel.GetTypeByMetadataName(MetadataNames.System_Threading_Tasks_Task),
                    cancellationToken: context.CancellationToken);

                if (analysis.Success)
                {
                    context.RegisterRefactoring(
                        "Reduce if nesting",
                        cancellationToken => ReduceIfNestingRefactoring.RefactorAsync(context.Document, ifStatement, analysis.JumpKind, false, cancellationToken));

                    if (ReduceIfNestingRefactoring.IsFixableRecursively(ifStatement, analysis.JumpKind))
                    {
                        context.RegisterRefactoring(
                            "Reduce if nesting (recursively)",
                            cancellationToken => ReduceIfNestingRefactoring.RefactorAsync(context.Document, ifStatement, analysis.JumpKind, true, cancellationToken));
                    }
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ReplaceIfElseWithIfReturn) &&
                context.Span.IsEmptyAndContainedInSpanOrBetweenSpans(ifStatement.IfKeyword))
            {
                ReplaceIfElseWithIfReturnRefactoring.ComputeRefactoring(context, ifStatement);
            }
        }
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, SyntaxToken token)
        {
            SyntaxNode parent = token.Parent;

            switch (parent.Kind())
            {
            case SyntaxKind.MethodDeclaration:
            {
                var methodDeclaration = (MethodDeclarationSyntax)parent;

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

                RemoveAsyncAwaitResult result = RemoveAsyncAwaitAnalysis.Analyze(methodDeclaration, semanticModel, context.CancellationToken);

                ComputeRefactoring(context, token, result);

                return;
            }

            case SyntaxKind.LocalFunctionStatement:
            {
                var localFunction = (LocalFunctionStatementSyntax)parent;

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

                RemoveAsyncAwaitResult result = RemoveAsyncAwaitAnalysis.Analyze(localFunction, semanticModel, context.CancellationToken);

                ComputeRefactoring(context, token, result);

                return;
            }

            case SyntaxKind.ParenthesizedLambdaExpression:
            {
                var parenthesizedLambda = (ParenthesizedLambdaExpressionSyntax)parent;

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

                RemoveAsyncAwaitResult result = RemoveAsyncAwaitAnalysis.Analyze(parenthesizedLambda, semanticModel, context.CancellationToken);

                ComputeRefactoring(context, token, result);

                return;
            }

            case SyntaxKind.SimpleLambdaExpression:
            {
                var simpleLambda = (SimpleLambdaExpressionSyntax)parent;

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

                RemoveAsyncAwaitResult result = RemoveAsyncAwaitAnalysis.Analyze(simpleLambda, semanticModel, context.CancellationToken);

                ComputeRefactoring(context, token, result);

                return;
            }

            case SyntaxKind.AnonymousMethodExpression:
            {
                var anonymousMethod = (AnonymousMethodExpressionSyntax)parent;

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

                RemoveAsyncAwaitResult result = RemoveAsyncAwaitAnalysis.Analyze(anonymousMethod, semanticModel, context.CancellationToken);

                ComputeRefactoring(context, token, result);

                return;
            }
            }
        }
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, InterpolatedStringTextSyntax interpolatedStringText)
        {
            if (context.IsRefactoringEnabled(RefactoringIdentifiers.InsertStringInterpolation) &&
                interpolatedStringText.IsParentKind(SyntaxKind.InterpolatedStringExpression))
            {
                TextSpan span = context.Span;
                var      interpolatedString = (InterpolatedStringExpressionSyntax)interpolatedStringText.Parent;
                string   text       = interpolatedStringText.TextToken.Text;
                bool     isVerbatim = interpolatedString.IsVerbatim();

                if (StringLiteralParser.CanExtractSpan(
                        text,
                        span.Offset(-interpolatedStringText.SpanStart),
                        isVerbatim,
                        isInterpolatedText: true))
                {
                    context.RegisterRefactoring(
                        "Insert interpolation",
                        cancellationToken =>
                    {
                        return(InsertInterpolationRefactoring.RefactorAsync(
                                   context.Document,
                                   interpolatedString,
                                   span,
                                   addNameOf: false,
                                   cancellationToken: cancellationToken));
                    });

                    if (!span.IsEmpty)
                    {
                        SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                        string name = StringLiteralParser.Parse(
                            text,
                            span.Start - interpolatedStringText.SpanStart,
                            span.Length,
                            isVerbatim: isVerbatim,
                            isInterpolatedText: true);

                        foreach (ISymbol symbol in semanticModel.LookupSymbols(interpolatedStringText.SpanStart))
                        {
                            if (string.Equals(name, symbol.MetadataName, StringComparison.Ordinal))
                            {
                                context.RegisterRefactoring(
                                    "Insert interpolation with nameof",
                                    cancellationToken =>
                                {
                                    return(InsertInterpolationRefactoring.RefactorAsync(
                                               context.Document,
                                               interpolatedString,
                                               span,
                                               addNameOf: true,
                                               cancellationToken: cancellationToken));
                                });

                                break;
                            }
                        }
                    }
                }
            }
        }
Exemplo n.º 11
0
        public static async Task ComputeRefactoringAsync(RefactoringContext context, StatementContainerSelection selectedStatements)
        {
            if (selectedStatements.Count > 1)
            {
                StatementSyntax lastStatement = selectedStatements.Last();

                if (lastStatement.IsKind(SyntaxKind.WhileStatement))
                {
                    IEnumerable <StatementSyntax> statements = selectedStatements
                                                               .Take(selectedStatements.EndIndex - selectedStatements.StartIndex);

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

                    List <LocalDeclarationStatementSyntax> localDeclarations = null;
                    List <ExpressionSyntax> expressions = null;

                    foreach (StatementSyntax statement in statements)
                    {
                        SyntaxKind kind = statement.Kind();

                        if (kind == SyntaxKind.LocalDeclarationStatement)
                        {
                            var localDeclaration = (LocalDeclarationStatementSyntax)statement;

                            if (!IsAnySymbolReferenced(localDeclaration, selectedStatements.ToImmutableArray(), selectedStatements.EndIndex + 1, semanticModel, context.CancellationToken))
                            {
                                (localDeclarations ?? (localDeclarations = new List <LocalDeclarationStatementSyntax>())).Add(localDeclaration);
                            }
                            else
                            {
                                return;
                            }
                        }
                        else if (kind == SyntaxKind.ExpressionStatement)
                        {
                            var expressionStatement = (ExpressionStatementSyntax)statement;

                            ExpressionSyntax expression = expressionStatement.Expression;

                            if (expression != null)
                            {
                                if (CanBeInitializer(expression))
                                {
                                    (expressions ?? (expressions = new List <ExpressionSyntax>())).Add(expression);
                                }
                                else
                                {
                                    return;
                                }
                            }
                        }
                        else
                        {
                            return;
                        }
                    }

                    if (localDeclarations == null ||
                        expressions == null)
                    {
                        if (localDeclarations == null ||
                            localDeclarations
                            .Select(f => f.Declaration)
                            .Where(f => f != null)
                            .Select(f => semanticModel.GetTypeSymbol(f.Type, context.CancellationToken))
                            .Distinct()
                            .Count() == 1)
                        {
                            context.RegisterRefactoring(
                                Title,
                                cancellationToken => RefactorAsync(context.Document, localDeclarations, expressions, (WhileStatementSyntax)lastStatement, cancellationToken));
                        }
                    }
                }
            }
        }
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, ExpressionSyntax expression)
        {
            if (expression != null &&
                context.SupportsSemanticModel)
            {
                MemberDeclarationSyntax declaration = GetContainingMethodOrPropertyOrIndexer(expression);

                if (declaration != null)
                {
                    TypeSyntax memberType = GetMemberType(declaration);

                    if (memberType != null)
                    {
                        SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                        ITypeSymbol memberTypeSymbol = semanticModel
                                                       .GetTypeInfo(memberType, context.CancellationToken)
                                                       .Type;

                        if (memberTypeSymbol != null)
                        {
                            ITypeSymbol expressionSymbol = semanticModel
                                                           .GetTypeInfo(expression, context.CancellationToken)
                                                           .Type;

                            if (expressionSymbol?.IsErrorType() == false)
                            {
                                if (context.IsRefactoringEnabled(RefactoringIdentifiers.AddBooleanComparison) &&
                                    memberTypeSymbol.IsBoolean() &&
                                    expressionSymbol.IsNamedType())
                                {
                                    var namedTypeSymbol = (INamedTypeSymbol)expressionSymbol;

                                    if (namedTypeSymbol?.IsNullableOf(SpecialType.System_Boolean) == true)
                                    {
                                        AddBooleanComparisonRefactoring.RegisterRefactoring(context, expression);
                                    }
                                }

                                ISymbol memberSymbol = semanticModel.GetDeclaredSymbol(declaration, context.CancellationToken);

                                if (context.IsRefactoringEnabled(RefactoringIdentifiers.ChangeMemberTypeAccordingToReturnExpression))
                                {
                                    ITypeSymbol newType = GetMemberNewType(memberSymbol, memberTypeSymbol, expression, expressionSymbol, semanticModel, context.CancellationToken);

                                    if (newType?.IsErrorType() == false &&
                                        !memberTypeSymbol.Equals(newType))
                                    {
                                        if (newType.IsNamedType() && memberTypeSymbol.IsNamedType())
                                        {
                                            var newNamedType = (INamedTypeSymbol)newType;

                                            INamedTypeSymbol orderedEnumerableSymbol = semanticModel.Compilation.GetTypeByMetadataName("System.Linq.IOrderedEnumerable`1");

                                            if (newNamedType.ConstructedFrom == orderedEnumerableSymbol)
                                            {
                                                INamedTypeSymbol enumerableSymbol = semanticModel.Compilation.GetTypeByMetadataName("System.Collections.Generic.IEnumerable`1");

                                                if (enumerableSymbol != null &&
                                                    ((INamedTypeSymbol)memberTypeSymbol).ConstructedFrom != enumerableSymbol)
                                                {
                                                    RegisterChangeType(context, declaration, memberType, enumerableSymbol.Construct(newNamedType.TypeArguments.ToArray()));
                                                }
                                            }
                                        }

                                        RegisterChangeType(context, declaration, memberType, newType);
                                    }
                                }

                                if (context.IsAnyRefactoringEnabled(RefactoringIdentifiers.AddCastExpression, RefactoringIdentifiers.CallToMethod) &&
                                    !memberTypeSymbol.IsErrorType())
                                {
                                    ITypeSymbol castTypeSymbol = GetCastTypeSymbol(memberSymbol, memberTypeSymbol, expressionSymbol, semanticModel);

                                    if (castTypeSymbol != null)
                                    {
                                        ModifyExpressionRefactoring.ComputeRefactoring(
                                            context,
                                            expression,
                                            castTypeSymbol,
                                            semanticModel);
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
Exemplo n.º 13
0
        private static async Task ComputeRefactoringAsync(RefactoringContext context, ExpressionSyntax expression)
        {
            if (expression == null)
            {
                return;
            }

            if (!expression.IsKind(SyntaxKind.IdentifierName, SyntaxKind.SimpleMemberAccessExpression))
            {
                return;
            }

            if (!context.Span.IsContainedInSpanOrBetweenSpans(expression))
            {
                return;
            }

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

            var methodSymbol = semanticModel.GetSymbol(expression, context.CancellationToken) as IMethodSymbol;

            if (methodSymbol == null)
            {
                return;
            }

            if (methodSymbol.IsImplicitlyDeclared)
            {
                return;
            }

            if (methodSymbol.PartialDefinitionPart != null)
            {
                return;
            }

            Debug.Assert(methodSymbol.DeclaringSyntaxReferences.Any());

            SyntaxNode node = methodSymbol.GetSyntaxOrDefault(context.CancellationToken);

            switch (node)
            {
            case MethodDeclarationSyntax methodDeclaration:
            {
                if (methodDeclaration.ContainsYield())
                {
                    break;
                }

                context.RegisterRefactoring(
                    Title,
                    cancellationToken => RefactorAsync(
                        context.Document,
                        expression,
                        methodDeclaration.Modifiers,
                        methodDeclaration.ParameterList,
                        methodDeclaration.BodyOrExpressionBody(),
                        cancellationToken));

                break;
            }

            case LocalFunctionStatementSyntax localFunction:
            {
                if (localFunction.ContainsYield())
                {
                    break;
                }

                context.RegisterRefactoring(
                    Title,
                    cancellationToken => RefactorAsync(
                        context.Document,
                        expression,
                        localFunction.Modifiers,
                        localFunction.ParameterList,
                        localFunction.BodyOrExpressionBody(),
                        cancellationToken));

                break;
            }

            default:
            {
                Debug.Assert(node == null, node.Kind().ToString());
                break;
            }
            }
        }
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, SyntaxToken token)
        {
            switch (token.Parent)
            {
            case MethodDeclarationSyntax methodDeclaration:
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                RemoveAsyncAwaitAnalysis analysis = RemoveAsyncAwaitAnalysis.Create(methodDeclaration, semanticModel, context.CancellationToken);

                if (analysis.Success)
                {
                    RegisterRefactoring(context, token, analysis);
                }

                return;
            }

            case LocalFunctionStatementSyntax localFunction:
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                RemoveAsyncAwaitAnalysis analysis = RemoveAsyncAwaitAnalysis.Create(localFunction, semanticModel, context.CancellationToken);

                if (analysis.Success)
                {
                    RegisterRefactoring(context, token, analysis);
                }

                return;
            }

            case ParenthesizedLambdaExpressionSyntax parenthesizedLambda:
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                RemoveAsyncAwaitAnalysis analysis = RemoveAsyncAwaitAnalysis.Create(parenthesizedLambda, semanticModel, context.CancellationToken);

                if (analysis.Success)
                {
                    RegisterRefactoring(context, token, analysis);
                }

                return;
            }

            case SimpleLambdaExpressionSyntax simpleLambda:
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                RemoveAsyncAwaitAnalysis analysis = RemoveAsyncAwaitAnalysis.Create(simpleLambda, semanticModel, context.CancellationToken);

                if (analysis.Success)
                {
                    RegisterRefactoring(context, token, analysis);
                }

                return;
            }

            case AnonymousMethodExpressionSyntax anonymousMethod:
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                RemoveAsyncAwaitAnalysis analysis = RemoveAsyncAwaitAnalysis.Create(anonymousMethod, semanticModel, context.CancellationToken);

                if (analysis.Success)
                {
                    RegisterRefactoring(context, token, analysis);
                }

                return;
            }
            }
        }
Exemplo n.º 15
0
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, InvocationExpressionSyntax invocation)
        {
            if (invocation.IsParentKind(SyntaxKind.ExpressionStatement))
            {
                return;
            }

            SimpleMemberInvocationExpressionInfo invocationInfo = SyntaxInfo.SimpleMemberInvocationExpressionInfo(invocation);

            if (!invocationInfo.Success)
            {
                return;
            }

            switch (invocationInfo.NameText)
            {
            case "First":
            {
                if (invocationInfo.Arguments.Any())
                {
                    break;
                }

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

                if (!UseElementAccessAnalysis.IsFixableFirst(invocationInfo, semanticModel, context.CancellationToken))
                {
                    break;
                }

                context.RegisterRefactoring(
                    "Use [] instead of calling 'First'",
                    ct => UseElementAccessInsteadOfEnumerableMethodRefactoring.UseElementAccessInsteadOfFirstAsync(context.Document, invocation, ct),
                    RefactoringDescriptors.UseElementAccessInsteadOfLinqMethod);

                break;
            }

            case "Last":
            {
                if (invocationInfo.Arguments.Any())
                {
                    break;
                }

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

                if (!UseElementAccessAnalysis.IsFixableLast(invocationInfo, semanticModel, context.CancellationToken))
                {
                    break;
                }

                string propertyName = CSharpUtility.GetCountOrLengthPropertyName(invocationInfo.Expression, semanticModel, context.CancellationToken);

                if (propertyName == null)
                {
                    break;
                }

                context.RegisterRefactoring(
                    "Use [] instead of calling 'Last'",
                    ct => UseElementAccessInsteadOfEnumerableMethodRefactoring.UseElementAccessInsteadOfLastAsync(context.Document, invocation, propertyName, ct),
                    RefactoringDescriptors.UseElementAccessInsteadOfLinqMethod);

                break;
            }

            case "ElementAt":
            {
                if (invocationInfo.Arguments.SingleOrDefault(shouldThrow: false)?.Expression?.IsMissing != false)
                {
                    break;
                }

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

                if (!UseElementAccessAnalysis.IsFixableElementAt(invocationInfo, semanticModel, context.CancellationToken))
                {
                    break;
                }

                context.RegisterRefactoring(
                    "Use [] instead of calling 'ElementAt'",
                    ct => UseElementAccessInsteadOfEnumerableMethodRefactoring.UseElementAccessInsteadOfElementAtAsync(context.Document, invocation, ct),
                    RefactoringDescriptors.UseElementAccessInsteadOfLinqMethod);

                break;
            }
            }
        }
        private static async Task SyncPropertyNameAndBackingFieldNameAsync(
            RefactoringContext context,
            IdentifierNameSyntax identifierName)
        {
            if (IsQualified(identifierName) &&
                !IsQualifiedWithThis(identifierName))
            {
                return;
            }

            PropertyDeclarationSyntax propertyDeclaration = identifierName.FirstAncestor <PropertyDeclarationSyntax>();

            if (propertyDeclaration == null)
            {
                return;
            }

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

            var fieldSymbol = semanticModel.GetSymbol(identifierName, context.CancellationToken) as IFieldSymbol;

            if (fieldSymbol?.DeclaredAccessibility != Accessibility.Private)
            {
                return;
            }

            IPropertySymbol propertySymbol = semanticModel.GetDeclaredSymbol(propertyDeclaration, context.CancellationToken);

            if (propertySymbol == null)
            {
                return;
            }

            if (fieldSymbol.IsStatic != propertySymbol.IsStatic)
            {
                return;
            }

            if (!SymbolEqualityComparer.Default.Equals(fieldSymbol.ContainingType, propertySymbol.ContainingType))
            {
                return;
            }

            string newName = StringUtility.ToCamelCase(propertySymbol.Name, context.PrefixFieldIdentifierWithUnderscore);

            if (string.Equals(fieldSymbol.Name, newName, StringComparison.Ordinal))
            {
                return;
            }

            if (!await MemberNameGenerator.IsUniqueMemberNameAsync(
                    newName,
                    fieldSymbol,
                    context.Solution,
                    cancellationToken: context.CancellationToken)
                .ConfigureAwait(false))
            {
                return;
            }

            context.RegisterRefactoring(
                $"Rename '{fieldSymbol.Name}' to '{newName}'",
                ct => Renamer.RenameSymbolAsync(context.Solution, fieldSymbol, newName, default(OptionSet), ct),
                RefactoringDescriptors.SyncPropertyNameAndBackingFieldName);
        }
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, StatementsSelection selectedStatements)
        {
            if (selectedStatements.Count > 1)
            {
                StatementSyntax firstStatement = selectedStatements.First();

                SemanticModel semanticModel = null;
                ISymbol       symbol        = null;
                ObjectCreationExpressionSyntax objectCreation = null;

                SyntaxKind kind = firstStatement.Kind();

                if (kind == SyntaxKind.LocalDeclarationStatement)
                {
                    var localDeclaration = (LocalDeclarationStatementSyntax)firstStatement;

                    VariableDeclaratorSyntax variable = localDeclaration
                                                        .Declaration?
                                                        .Variables
                                                        .SingleOrDefault(shouldthrow: false);

                    objectCreation = variable?.Initializer?.Value as ObjectCreationExpressionSyntax;

                    if (objectCreation != null)
                    {
                        semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                        symbol = semanticModel.GetDeclaredSymbol(variable, context.CancellationToken);
                    }
                }
                else if (kind == SyntaxKind.ExpressionStatement)
                {
                    var expressionStatement = (ExpressionStatementSyntax)firstStatement;

                    if (expressionStatement.Expression is AssignmentExpressionSyntax assignment)
                    {
                        objectCreation = assignment.Right as ObjectCreationExpressionSyntax;

                        if (objectCreation != null)
                        {
                            semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                            symbol = semanticModel.GetSymbol(assignment.Left, context.CancellationToken);
                        }
                    }
                }

                if (objectCreation != null &&
                    symbol?.IsErrorType() == false &&
                    selectedStatements
                    .Skip(1)
                    .All(f => IsValidAssignmentStatement(f, symbol, semanticModel, context.CancellationToken)))
                {
                    context.RegisterRefactoring(
                        "Collapse to initializer",
                        cancellationToken =>
                    {
                        return(RefactorAsync(
                                   context.Document,
                                   objectCreation,
                                   selectedStatements,
                                   cancellationToken));
                    });
                }
            }
        }
Exemplo n.º 18
0
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, VariableDeclarationSyntax variableDeclaration)
        {
            TypeSyntax type = variableDeclaration.Type;

            if (type?.Span.Contains(context.Span) == true &&
                context.IsAnyRefactoringEnabled(
                    RefactoringIdentifiers.ChangeExplicitTypeToVar,
                    RefactoringIdentifiers.ChangeVarToExplicitType,
                    RefactoringIdentifiers.ChangeTypeAccordingToExpression))
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                TypeAnalysis analysis = CSharpTypeAnalysis.AnalyzeType(variableDeclaration, semanticModel, context.CancellationToken);

                if (analysis.IsExplicit)
                {
                    if (analysis.SupportsImplicit &&
                        context.IsRefactoringEnabled(RefactoringIdentifiers.ChangeExplicitTypeToVar))
                    {
                        context.RegisterRefactoring(CodeActionFactory.ChangeTypeToVar(context.Document, type, equivalenceKey: RefactoringIdentifiers.ChangeExplicitTypeToVar));
                    }

                    if (!variableDeclaration.ContainsDiagnostics &&
                        context.IsRefactoringEnabled(RefactoringIdentifiers.ChangeTypeAccordingToExpression))
                    {
                        ChangeTypeAccordingToExpression(context, variableDeclaration, analysis.Symbol, semanticModel);
                    }
                }
                else if (analysis.SupportsExplicit &&
                         context.IsRefactoringEnabled(RefactoringIdentifiers.ChangeVarToExplicitType))
                {
                    ITypeSymbol typeSymbol = analysis.Symbol;

                    VariableDeclaratorSyntax variableDeclarator = variableDeclaration.Variables.SingleOrDefault(shouldThrow: false);

                    if (variableDeclarator?.Initializer?.Value != null)
                    {
                        if (typeSymbol.OriginalDefinition.EqualsOrInheritsFromTaskOfT())
                        {
                            Func <CancellationToken, Task <Document> > createChangedDocument = DocumentRefactoringFactory.ChangeTypeAndAddAwait(
                                context.Document,
                                variableDeclaration,
                                variableDeclarator,
                                typeSymbol,
                                semanticModel,
                                context.CancellationToken);

                            if (createChangedDocument != null)
                            {
                                ITypeSymbol typeArgument = ((INamedTypeSymbol)typeSymbol).TypeArguments[0];

                                context.RegisterRefactoring(
                                    $"Change type to '{SymbolDisplay.ToMinimalDisplayString(typeArgument, semanticModel, type.SpanStart)}' and add 'await'",
                                    createChangedDocument,
                                    EquivalenceKey.Join(RefactoringIdentifiers.ChangeVarToExplicitType, "AddAwait"));
                            }
                        }

                        typeSymbol = semanticModel.GetTypeSymbol(variableDeclarator.Initializer.Value, context.CancellationToken);

                        if (typeSymbol != null)
                        {
                            context.RegisterRefactoring(CodeActionFactory.ChangeType(context.Document, type, typeSymbol, semanticModel, equivalenceKey: RefactoringIdentifiers.ChangeVarToExplicitType));
                        }
                    }
                }
            }
        }
Exemplo n.º 19
0
        private static async Task RenameMethodAccordingToTypeNameAsync(
            RefactoringContext context,
            MethodDeclarationSyntax methodDeclaration)
        {
            TypeSyntax returnType = methodDeclaration.ReturnType;

            if (returnType?.IsVoid() != false)
            {
                return;
            }

            SyntaxToken identifier = methodDeclaration.Identifier;

            if (!context.Span.IsEmptyAndContainedInSpanOrBetweenSpans(identifier))
            {
                return;
            }

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

            IMethodSymbol methodSymbol = semanticModel.GetDeclaredSymbol(methodDeclaration, context.CancellationToken);

            ITypeSymbol typeSymbol = GetType(returnType, semanticModel, context.CancellationToken);

            if (typeSymbol == null)
            {
                return;
            }

            string newName = NameGenerator.CreateName(typeSymbol);

            if (string.IsNullOrEmpty(newName))
            {
                return;
            }

            newName = "Get" + newName;

            if (methodSymbol.IsAsync)
            {
                newName += "Async";
            }

            string oldName = identifier.ValueText;

            if (string.Equals(oldName, newName, StringComparison.Ordinal))
            {
                return;
            }

            if (!await MemberNameGenerator.IsUniqueMemberNameAsync(
                    newName,
                    methodSymbol,
                    context.Solution,
                    cancellationToken: context.CancellationToken)
                .ConfigureAwait(false))
            {
                return;
            }

            context.RegisterRefactoring(
                $"Rename '{oldName}' to '{newName}'",
                cancellationToken => Renamer.RenameSymbolAsync(context.Solution, methodSymbol, newName, default(OptionSet), cancellationToken),
                RefactoringIdentifiers.RenameMethodAccordingToTypeName);
        }
Exemplo n.º 20
0
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, InitializerExpressionSyntax initializer)
        {
            if (initializer.IsKind(
                    SyntaxKind.ObjectInitializerExpression,
                    SyntaxKind.CollectionInitializerExpression) &&
                initializer.Expressions.Any())
            {
                SyntaxNode parent = initializer.Parent;

                if (parent?.IsKind(SyntaxKind.ObjectCreationExpression) == true)
                {
                    SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                    if (CanExpand(initializer, semanticModel, context.CancellationToken))
                    {
                        parent = parent.Parent;

                        switch (parent?.Kind())
                        {
                        case SyntaxKind.SimpleAssignmentExpression:
                        {
                            var assignmentExpression = (AssignmentExpressionSyntax)parent;

                            ExpressionSyntax left = assignmentExpression.Left;

                            if (left != null)
                            {
                                parent = assignmentExpression.Parent;

                                if (parent?.IsKind(SyntaxKind.ExpressionStatement) == true)
                                {
                                    RegisterRefactoring(context, (StatementSyntax)parent, initializer, left);
                                }
                            }

                            break;
                        }

                        case SyntaxKind.EqualsValueClause:
                        {
                            var equalsValueClause = (EqualsValueClauseSyntax)parent;

                            parent = equalsValueClause.Parent;

                            if (parent?.IsKind(SyntaxKind.VariableDeclarator) == true)
                            {
                                parent = parent.Parent;

                                if (parent?.IsKind(SyntaxKind.VariableDeclaration) == true)
                                {
                                    parent = parent.Parent;

                                    if (parent?.IsKind(SyntaxKind.LocalDeclarationStatement) == true)
                                    {
                                        var variableDeclarator = (VariableDeclaratorSyntax)equalsValueClause.Parent;

                                        RegisterRefactoring(
                                            context,
                                            (StatementSyntax)parent,
                                            initializer,
                                            IdentifierName(variableDeclarator.Identifier.ValueText));
                                    }
                                }
                            }

                            break;
                        }
                        }
                    }
                }
            }
        }
Exemplo n.º 21
0
        public static async Task ComputeRefactoringAsync(RefactoringContext context, MemberDeclarationListSelection selectedMembers)
        {
            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ChangeAccessibility) &&
                !selectedMembers.Parent.IsKind(SyntaxKind.InterfaceDeclaration))
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                AccessibilityFilter validAccessibilities = ChangeAccessibilityAnalysis.GetValidAccessibilityFilter(selectedMembers, semanticModel, context.CancellationToken);

                if (validAccessibilities != AccessibilityFilter.None)
                {
                    bool canHaveMultipleDeclarations = CanHaveMultipleDeclarations();

                    TryRegisterRefactoring(validAccessibilities, Accessibility.Public, canHaveMultipleDeclarations);
                    TryRegisterRefactoring(validAccessibilities, Accessibility.Internal, canHaveMultipleDeclarations);
                    TryRegisterRefactoring(validAccessibilities, Accessibility.Protected, canHaveMultipleDeclarations);
                    TryRegisterRefactoring(validAccessibilities, Accessibility.Private, canHaveMultipleDeclarations);
                }
            }

            if (context.IsAnyRefactoringEnabled(
                    RefactoringIdentifiers.ConvertBlockBodyToExpressionBody,
                    RefactoringIdentifiers.ConvertExpressionBodyToBlockBody))
            {
                ConvertBodyAndExpressionBodyRefactoring.ComputeRefactoring(context, selectedMembers);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.InitializeFieldFromConstructor) &&
                !selectedMembers.Parent.IsKind(SyntaxKind.InterfaceDeclaration))
            {
                InitializeFieldFromConstructorRefactoring.ComputeRefactoring(context, selectedMembers);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.AddEmptyLineBetweenDeclarations))
            {
                AddEmptyLineBetweenDeclarationsRefactoring.ComputeRefactoring(context, selectedMembers);
            }

            void TryRegisterRefactoring(AccessibilityFilter accessibilities, Accessibility accessibility, bool canHaveMultipleDeclarations)
            {
                if ((accessibilities & accessibility.GetAccessibilityFilter()) != 0)
                {
                    if (canHaveMultipleDeclarations)
                    {
                        context.RegisterRefactoring(
                            ChangeAccessibilityRefactoring.GetTitle(accessibility),
                            async cancellationToken =>
                        {
                            SemanticModel semanticModel = await context.Document.GetSemanticModelAsync(cancellationToken).ConfigureAwait(false);
                            return(await ChangeAccessibilityRefactoring.RefactorAsync(context.Document.Solution(), selectedMembers, accessibility, semanticModel, cancellationToken).ConfigureAwait(false));
                        },
                            _accessiblityIdentifierMap[accessibility]);
                    }
                    else
                    {
                        context.RegisterRefactoring(
                            ChangeAccessibilityRefactoring.GetTitle(accessibility),
                            cancellationToken => ChangeAccessibilityRefactoring.RefactorAsync(context.Document, selectedMembers, accessibility, cancellationToken),
                            EquivalenceKey.Join(RefactoringIdentifiers.ChangeAccessibility, accessibility.ToString()));
                    }
                }
            }

            bool CanHaveMultipleDeclarations()
            {
                foreach (MemberDeclarationSyntax member in selectedMembers)
                {
                    switch (member.Kind())
                    {
                    case SyntaxKind.ClassDeclaration:
                    {
                        if (((ClassDeclarationSyntax)member).Modifiers.Contains(SyntaxKind.PartialKeyword))
                        {
                            return(true);
                        }

                        break;
                    }

                    case SyntaxKind.InterfaceDeclaration:
                    {
                        if (((InterfaceDeclarationSyntax)member).Modifiers.Contains(SyntaxKind.PartialKeyword))
                        {
                            return(true);
                        }

                        break;
                    }

                    case SyntaxKind.RecordDeclaration:
                    {
                        if (((RecordDeclarationSyntax)member).Modifiers.Contains(SyntaxKind.PartialKeyword))
                        {
                            return(true);
                        }

                        break;
                    }

                    case SyntaxKind.StructDeclaration:
                    {
                        if (((StructDeclarationSyntax)member).Modifiers.Contains(SyntaxKind.PartialKeyword))
                        {
                            return(true);
                        }

                        break;
                    }

                    case SyntaxKind.MethodDeclaration:
                    {
                        if (((MethodDeclarationSyntax)member).Modifiers.ContainsAny(SyntaxKind.PartialKeyword, SyntaxKind.AbstractKeyword, SyntaxKind.VirtualKeyword, SyntaxKind.OverrideKeyword))
                        {
                            return(true);
                        }

                        break;
                    }

                    case SyntaxKind.PropertyDeclaration:
                    {
                        if (((PropertyDeclarationSyntax)member).Modifiers.ContainsAny(SyntaxKind.AbstractKeyword, SyntaxKind.VirtualKeyword, SyntaxKind.OverrideKeyword))
                        {
                            return(true);
                        }

                        break;
                    }

                    case SyntaxKind.IndexerDeclaration:
                    {
                        if (((IndexerDeclarationSyntax)member).Modifiers.ContainsAny(SyntaxKind.AbstractKeyword, SyntaxKind.VirtualKeyword, SyntaxKind.OverrideKeyword))
                        {
                            return(true);
                        }

                        break;
                    }

                    case SyntaxKind.EventDeclaration:
                    {
                        if (((EventDeclarationSyntax)member).Modifiers.ContainsAny(SyntaxKind.AbstractKeyword, SyntaxKind.VirtualKeyword, SyntaxKind.OverrideKeyword))
                        {
                            return(true);
                        }

                        break;
                    }

                    case SyntaxKind.EventFieldDeclaration:
                    {
                        if (((EventFieldDeclarationSyntax)member).Modifiers.ContainsAny(SyntaxKind.AbstractKeyword, SyntaxKind.VirtualKeyword, SyntaxKind.OverrideKeyword))
                        {
                            return(true);
                        }

                        break;
                    }
                    }
                }

                return(false);
            }
        }
        public static async Task ComputeRefactoringAsync(RefactoringContext context, StructDeclarationSyntax structDeclaration)
        {
            SyntaxToken identifier = structDeclaration.Identifier;

            if (identifier.IsMissing)
            {
                return;
            }

            TextSpan span = identifier.Span;

            BaseListSyntax baseList = structDeclaration.BaseList;

            if (baseList != null)
            {
                span = TextSpan.FromBounds(span.Start, baseList.Span.End);
            }

            TypeParameterListSyntax typeParameterList = structDeclaration.TypeParameterList;

            if (typeParameterList != null)
            {
                span = TextSpan.FromBounds(span.Start, typeParameterList.Span.End);
            }

            if (!span.Contains(context.Span))
            {
                return;
            }

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

            INamedTypeSymbol typeSymbol = semanticModel.GetDeclaredSymbol(structDeclaration, context.CancellationToken);

            if (typeSymbol?.IsErrorType() != false)
            {
                return;
            }

            foreach (INamedTypeSymbol interfaceSymbol in typeSymbol.AllInterfaces)
            {
                if (interfaceSymbol.HasMetadataName(MetadataNames.System_IEquatable_T) &&
                    interfaceSymbol.TypeArguments.Single().Equals(typeSymbol))
                {
                    return;
                }
            }

            INamedTypeSymbol equatableSymbol = semanticModel.GetTypeByMetadataName("System.IEquatable`1");

            if (equatableSymbol == null)
            {
                return;
            }

            equatableSymbol = equatableSymbol.Construct(typeSymbol);

            context.RegisterRefactoring(
                GetTitle(equatableSymbol, semanticModel, structDeclaration.SpanStart),
                ct => RefactorAsync(context.Document, structDeclaration, typeSymbol, equatableSymbol, semanticModel, ct),
                RefactoringIdentifiers.ImplementIEquatableOfT);
        }
        public static async Task ComputeRefactoringAsync(RefactoringContext context, StatementListSelection selectedStatements)
        {
            if (context.IsRefactoringEnabled(RefactoringIdentifiers.WrapInUsingStatement))
            {
                var refactoring = new WrapStatements.WrapInUsingStatementRefactoring();
                await refactoring.ComputeRefactoringAsync(context, selectedStatements).ConfigureAwait(false);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.CollapseToInitializer))
            {
                await CollapseToInitializerRefactoring.ComputeRefactoringsAsync(context, selectedStatements).ConfigureAwait(false);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.MergeIfStatements))
            {
                MergeIfStatementsRefactoring.ComputeRefactorings(context, selectedStatements);
            }

            if (context.IsAnyRefactoringEnabled(
                    RefactoringIdentifiers.UseCoalesceExpressionInsteadOfIf,
                    RefactoringIdentifiers.UseConditionalExpressionInsteadOfIf,
                    RefactoringIdentifiers.SimplifyIf))
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                var options = new IfAnalysisOptions(
                    useCoalesceExpression: context.IsRefactoringEnabled(RefactoringIdentifiers.UseCoalesceExpressionInsteadOfIf),
                    useConditionalExpression: context.IsRefactoringEnabled(RefactoringIdentifiers.UseConditionalExpressionInsteadOfIf),
                    useBooleanExpression: context.IsRefactoringEnabled(RefactoringIdentifiers.SimplifyIf),
                    useExpression: false);

                foreach (IfAnalysis analysis in IfAnalysis.Analyze(selectedStatements, options, semanticModel, context.CancellationToken))
                {
                    context.RegisterRefactoring(
                        analysis.Title,
                        cancellationToken => IfRefactoring.RefactorAsync(context.Document, analysis, cancellationToken));
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.MergeLocalDeclarations))
            {
                await MergeLocalDeclarationsRefactoring.ComputeRefactoringsAsync(context, selectedStatements).ConfigureAwait(false);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.MergeAssignmentExpressionWithReturnStatement))
            {
                MergeAssignmentExpressionWithReturnStatementRefactoring.ComputeRefactorings(context, selectedStatements);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.CheckExpressionForNull))
            {
                await CheckExpressionForNullRefactoring.ComputeRefactoringAsync(context, selectedStatements).ConfigureAwait(false);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ReplaceWhileWithFor))
            {
                await ReplaceWhileWithForRefactoring.ComputeRefactoringAsync(context, selectedStatements).ConfigureAwait(false);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.WrapInElseClause))
            {
                WrapInElseClauseRefactoring.ComputeRefactoring(context, selectedStatements);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.WrapInCondition))
            {
                context.RegisterRefactoring(
                    WrapInIfStatementRefactoring.Title,
                    ct => WrapInIfStatementRefactoring.Instance.RefactorAsync(context.Document, selectedStatements, ct));
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.WrapInTryCatch))
            {
                context.RegisterRefactoring(
                    WrapInTryCatchRefactoring.Title,
                    ct => WrapInTryCatchRefactoring.Instance.RefactorAsync(context.Document, selectedStatements, ct));
            }
        }
Exemplo n.º 24
0
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, InvocationExpressionSyntax invocation)
        {
            MemberInvocationExpressionInfo invocationInfo = SyntaxInfo.MemberInvocationExpressionInfo(invocation);

            if (!invocationInfo.Success)
            {
                return;
            }

            switch (invocationInfo.NameText)
            {
            case "First":
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                if (invocationInfo.Arguments.Any())
                {
                    break;
                }

                if (!UseElementAccessInsteadOfFirstRefactoring.CanRefactor(invocationInfo, semanticModel, context.CancellationToken))
                {
                    break;
                }

                context.RegisterRefactoring(
                    "Use [] instead of calling 'First'",
                    cancellationToken => UseElementAccessInsteadOfFirstRefactoring.RefactorAsync(context.Document, invocation, cancellationToken));

                break;
            }

            case "Last":
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                if (invocationInfo.Arguments.Any())
                {
                    break;
                }

                if (!UseElementAccessInsteadOfLastRefactoring.CanRefactor(invocationInfo, semanticModel, context.CancellationToken))
                {
                    break;
                }

                string propertyName = CSharpUtility.GetCountOrLengthPropertyName(invocationInfo.Expression, semanticModel, context.CancellationToken);

                if (propertyName == null)
                {
                    break;
                }

                context.RegisterRefactoring(
                    "Use [] instead of calling 'Last'",
                    cancellationToken => UseElementAccessInsteadOfLastRefactoring.RefactorAsync(context.Document, invocation, propertyName, cancellationToken));

                break;
            }

            case "ElementAt":
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                if (invocationInfo.Arguments.Count != 1)
                {
                    break;
                }

                if (!UseElementAccessInsteadOfElementAtRefactoring.CanRefactor(invocationInfo, semanticModel, context.CancellationToken))
                {
                    break;
                }

                context.RegisterRefactoring(
                    "Use [] instead of calling 'ElementAt'",
                    cancellationToken => UseElementAccessInsteadOfElementAtRefactoring.RefactorAsync(context.Document, invocation, cancellationToken));

                break;
            }
            }
        }
        public static async Task ComputeRefactoringAsync(RefactoringContext context, EventFieldDeclarationSyntax eventFieldDeclaration)
        {
            if (eventFieldDeclaration.IsParentKind(SyntaxKind.InterfaceDeclaration))
            {
                return;
            }

            VariableDeclarationSyntax variableDeclaration = eventFieldDeclaration.Declaration;

            if (variableDeclaration == null)
            {
                return;
            }

            SemanticModel semanticModel = null;

            foreach (VariableDeclaratorSyntax variableDeclarator in variableDeclaration.Variables)
            {
                if (!context.Span.IsContainedInSpanOrBetweenSpans(variableDeclarator.Identifier))
                {
                    continue;
                }

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

                var eventSymbol = semanticModel.GetDeclaredSymbol(variableDeclarator, context.CancellationToken) as IEventSymbol;

                if (eventSymbol?.IsStatic != false)
                {
                    continue;
                }

                INamedTypeSymbol containingType = eventSymbol.ContainingType;

                if (containingType == null)
                {
                    return;
                }

                if (!(eventSymbol.Type is INamedTypeSymbol eventHandlerType))
                {
                    continue;
                }

                ITypeSymbol eventArgsSymbol = GetEventArgsSymbol(eventHandlerType, semanticModel);

                if (eventArgsSymbol == null)
                {
                    continue;
                }

                string methodName = "On" + eventSymbol.Name;

                if (containingType.ContainsMember <IMethodSymbol>(
                        $"On{eventSymbol.Name}",
                        methodSymbol => eventArgsSymbol.Equals(methodSymbol.Parameters.SingleOrDefault(shouldThrow: false)?.Type)))
                {
                    continue;
                }

                methodName = NameGenerator.Default.EnsureUniqueMemberName(methodName, containingType);

                context.RegisterRefactoring(
                    $"Generate '{methodName}' method",
                    cancellationToken =>
                {
                    return(RefactorAsync(
                               context.Document,
                               eventFieldDeclaration,
                               eventSymbol,
                               eventArgsSymbol,
                               context.SupportsCSharp6,
                               cancellationToken));
                });
            }
        }
Exemplo n.º 26
0
        public static async Task ComputeRefactoringAsync(
            RefactoringContext context,
            PropertyDeclarationSyntax property)
        {
            AccessorDeclarationSyntax setter = property.Setter();

            if (setter == null)
            {
                return;
            }

            ExpressionSyntax expression = GetExpression();

            if (expression == null)
            {
                return;
            }

            SimpleAssignmentExpressionInfo simpleAssignment = SyntaxInfo.SimpleAssignmentExpressionInfo(expression);

            if (!simpleAssignment.Success)
            {
                return;
            }

            if (!simpleAssignment.Left.IsKind(SyntaxKind.IdentifierName))
            {
                return;
            }

            if (!(simpleAssignment.Right is IdentifierNameSyntax identifierName))
            {
                return;
            }

            if (identifierName.Identifier.ValueText != "value")
            {
                return;
            }

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

            INamedTypeSymbol containingType = semanticModel
                                              .GetDeclaredSymbol(property, context.CancellationToken)?
                                              .ContainingType;

            if (containingType == null)
            {
                return;
            }

            if (!containingType.Implements(MetadataNames.System_ComponentModel_INotifyPropertyChanged, allInterfaces: true))
            {
                return;
            }

            IMethodSymbol methodSymbol = SymbolUtility.FindMethodThatRaisePropertyChanged(containingType, expression.SpanStart, semanticModel);

            if (methodSymbol == null)
            {
                return;
            }

            Document document = context.Document;

            context.RegisterRefactoring(
                "Notify when property change",
                ct => RefactorAsync(document, property, methodSymbol.Name, ct),
                RefactoringIdentifiers.NotifyWhenPropertyChange);

            ExpressionSyntax GetExpression()
            {
                BlockSyntax body = setter.Body;

                if (body != null)
                {
                    if (body.Statements.SingleOrDefault(shouldThrow: false) is ExpressionStatementSyntax expressionStatement)
                    {
                        return(expressionStatement.Expression);
                    }
                }
                else
                {
                    return(setter.ExpressionBody?.Expression);
                }

                return(null);
            }
        }
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, PropertyDeclarationSyntax propertyDeclaration)
        {
            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ReplacePropertyWithMethod) &&
                propertyDeclaration.HeaderSpan().Contains(context.Span))
            {
                ReplacePropertyWithMethodRefactoring.ComputeRefactoring(context, propertyDeclaration);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.RemovePropertyInitializer) &&
                RemovePropertyInitializerRefactoring.CanRefactor(context, propertyDeclaration))
            {
                context.RegisterRefactoring(
                    "Remove property initializer",
                    cancellationToken => RemovePropertyInitializerRefactoring.RefactorAsync(context.Document, propertyDeclaration, cancellationToken));
            }

            if (context.IsAnyRefactoringEnabled(
                    RefactoringIdentifiers.ExpandProperty,
                    RefactoringIdentifiers.ExpandPropertyAndAddBackingField) &&
                propertyDeclaration.Span.Contains(context.Span) &&
                ExpandPropertyRefactoring.CanRefactor(propertyDeclaration))
            {
                if (context.IsRefactoringEnabled(RefactoringIdentifiers.ExpandProperty))
                {
                    context.RegisterRefactoring(
                        "Expand property",
                        cancellationToken => ExpandPropertyRefactoring.RefactorAsync(context.Document, propertyDeclaration, cancellationToken));
                }

                if (context.IsRefactoringEnabled(RefactoringIdentifiers.ExpandPropertyAndAddBackingField))
                {
                    context.RegisterRefactoring(
                        "Expand property and add backing field",
                        cancellationToken => ExpandPropertyAndAddBackingFieldRefactoring.RefactorAsync(context.Document, propertyDeclaration, context.Settings.PrefixFieldIdentifierWithUnderscore, cancellationToken));
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.NotifyPropertyChanged) &&
                await NotifyPropertyChangedRefactoring.CanRefactorAsync(context, propertyDeclaration).ConfigureAwait(false))
            {
                context.RegisterRefactoring(
                    "Notify property changed",
                    cancellationToken =>
                {
                    return(NotifyPropertyChangedRefactoring.RefactorAsync(
                               context.Document,
                               propertyDeclaration,
                               context.SupportsCSharp6,
                               cancellationToken));
                });
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.MakeMemberAbstract) &&
                propertyDeclaration.HeaderSpan().Contains(context.Span))
            {
                MakePropertyAbstractRefactoring.ComputeRefactoring(context, propertyDeclaration);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.MakeMemberVirtual) &&
                propertyDeclaration.HeaderSpan().Contains(context.Span))
            {
                MakePropertyVirtualRefactoring.ComputeRefactoring(context, propertyDeclaration);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.CopyDocumentationCommentFromBaseMember) &&
                propertyDeclaration.HeaderSpan().Contains(context.Span))
            {
                await CopyDocumentationCommentFromBaseMemberRefactoring.ComputeRefactoringAsync(context, propertyDeclaration).ConfigureAwait(false);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.RenamePropertyAccordingToTypeName))
            {
                TypeSyntax type = propertyDeclaration.Type;

                if (type != null)
                {
                    SyntaxToken identifier = propertyDeclaration.Identifier;

                    if (context.Span.IsEmptyAndContainedInSpanOrBetweenSpans(identifier))
                    {
                        SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                        ITypeSymbol typeSymbol = semanticModel.GetTypeSymbol(type, context.CancellationToken);

                        if (typeSymbol?.IsErrorType() == false)
                        {
                            string newName = NameGenerator.CreateName(typeSymbol);

                            if (!string.IsNullOrEmpty(newName))
                            {
                                string oldName = identifier.ValueText;

                                newName = StringUtility.FirstCharToUpper(newName);

                                if (!string.Equals(oldName, newName, StringComparison.Ordinal))
                                {
                                    ISymbol symbol = semanticModel.GetDeclaredSymbol(propertyDeclaration, context.CancellationToken);

                                    if (await NameGenerator.IsUniqueMemberNameAsync(
                                            newName,
                                            symbol,
                                            context.Solution,
                                            cancellationToken: context.CancellationToken).ConfigureAwait(false))
                                    {
                                        context.RegisterRefactoring(
                                            $"Rename '{oldName}' to '{newName}'",
                                            cancellationToken => Renamer.RenameSymbolAsync(context.Solution, symbol, newName, default(OptionSet), cancellationToken));
                                    }
                                }
                            }
                        }
                    }
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.AddMemberToInterface) &&
                context.Span.IsEmptyAndContainedInSpanOrBetweenSpans(propertyDeclaration.Identifier))
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                AddMemberToInterfaceRefactoring.ComputeRefactoring(context, propertyDeclaration, semanticModel);
            }
        }
Exemplo n.º 28
0
        public static async Task ComputeRefactoringAsync(RefactoringContext context, ConditionalExpressionSyntax conditionalExpression)
        {
            ExpressionSyntax expression = conditionalExpression.WalkUpParentheses();

            SyntaxNode parent = expression.Parent;

            if (parent.IsKind(SyntaxKind.ReturnStatement, SyntaxKind.YieldReturnStatement))
            {
                var statement = (StatementSyntax)parent;

                RegisterRefactoring(context, conditionalExpression, statement);

                if (IsRecursive())
                {
                    RegisterRefactoring(context, conditionalExpression, statement, recursive: true);
                }
            }
            else if (parent is AssignmentExpressionSyntax assignment)
            {
                if (assignment.Parent is ExpressionStatementSyntax expressionStatement)
                {
                    RegisterRefactoring(context, conditionalExpression, expressionStatement);

                    if (IsRecursive())
                    {
                        RegisterRefactoring(context, conditionalExpression, expressionStatement, recursive: true);
                    }
                }
            }
            else
            {
                SingleLocalDeclarationStatementInfo localDeclarationInfo = SyntaxInfo.SingleLocalDeclarationStatementInfo(expression);

                if (localDeclarationInfo.Success)
                {
                    TypeSyntax type = localDeclarationInfo.Type;

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

                    if (!type.IsVar ||
                        semanticModel.GetTypeSymbol(type, context.CancellationToken)?.SupportsExplicitDeclaration() == true)
                    {
                        LocalDeclarationStatementSyntax statement = localDeclarationInfo.Statement;

                        RegisterRefactoring(context, conditionalExpression, statement, semanticModel);

                        if (IsRecursive())
                        {
                            RegisterRefactoring(context, conditionalExpression, statement, semanticModel, recursive: true);
                        }
                    }
                }
            }

            bool IsRecursive()
            {
                return(conditionalExpression
                       .WhenFalse
                       .WalkDownParentheses()
                       .IsKind(SyntaxKind.ConditionalExpression));
            }
        }
Exemplo n.º 29
0
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, BinaryExpressionSyntax binaryExpression)
        {
            SyntaxToken operatorToken = binaryExpression.OperatorToken;

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.InvertOperator) &&
                context.Span.IsEmptyAndContainedInSpanOrBetweenSpans(operatorToken) &&
                InvertOperatorRefactoring.CanBeInverted(operatorToken))
            {
                context.RegisterRefactoring(
                    "Invert operator",
                    cancellationToken => InvertOperatorRefactoring.RefactorAsync(context.Document, operatorToken, cancellationToken),
                    RefactoringIdentifiers.InvertOperator);
            }

            if (context.Span.IsEmptyAndContainedInSpan(operatorToken))
            {
                if (context.IsRefactoringEnabled(RefactoringIdentifiers.InvertBinaryExpression))
                {
                    InvertBinaryExpressionRefactoring.ComputeRefactoring(context, binaryExpression);
                }

                if (context.IsRefactoringEnabled(RefactoringIdentifiers.SwapBinaryOperands))
                {
                    SwapBinaryOperandsRefactoring.ComputeRefactoring(context, binaryExpression);
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.FormatBinaryExpression))
            {
                FormatBinaryExpressionRefactoring.ComputeRefactorings(context, binaryExpression);
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ExpandCoalesceExpression) &&
                operatorToken.Span.Contains(context.Span))
            {
                ExpandCoalesceExpressionRefactoring.ComputeRefactoring(context, binaryExpression);
            }

            if (context.IsAnyRefactoringEnabled(
                    RefactoringIdentifiers.ExtractExpressionFromCondition,
                    RefactoringIdentifiers.JoinStringExpressions,
                    RefactoringIdentifiers.UseStringBuilderInsteadOfConcatenation) &&
                !context.Span.IsEmpty &&
                binaryExpression.IsKind(SyntaxKind.AddExpression, SyntaxKind.LogicalAndExpression, SyntaxKind.LogicalOrExpression))
            {
                ExpressionChain chain = binaryExpression.AsChain(context.Span);

                ExpressionChain.Enumerator en = chain.GetEnumerator();

                if (en.MoveNext() &&
                    en.MoveNext())
                {
                    if (context.IsRefactoringEnabled(RefactoringIdentifiers.ExtractExpressionFromCondition))
                    {
                        ExtractConditionRefactoring.ComputeRefactoring(context, chain);
                    }

                    if (binaryExpression.IsKind(SyntaxKind.AddExpression))
                    {
                        SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                        StringConcatenationExpressionInfo concatenationInfo = SyntaxInfo.StringConcatenationExpressionInfo(chain, semanticModel, context.CancellationToken);
                        if (concatenationInfo.Success)
                        {
                            if (context.IsRefactoringEnabled(RefactoringIdentifiers.JoinStringExpressions))
                            {
                                JoinStringExpressionsRefactoring.ComputeRefactoring(context, concatenationInfo);
                            }

                            if (context.IsRefactoringEnabled(RefactoringIdentifiers.UseStringBuilderInsteadOfConcatenation))
                            {
                                UseStringBuilderInsteadOfConcatenationRefactoring.ComputeRefactoring(context, concatenationInfo);
                            }
                        }
                    }
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ReplaceAsWithCast) &&
                context.Span.IsEmptyAndContainedInSpanOrBetweenSpans(binaryExpression))
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                if (ReplaceAsWithCastAnalysis.IsFixable(binaryExpression, semanticModel, context.CancellationToken))
                {
                    context.RegisterRefactoring(
                        ReplaceAsWithCastRefactoring.Title,
                        cancellationToken => ReplaceAsWithCastRefactoring.RefactorAsync(context.Document, binaryExpression, cancellationToken),
                        RefactoringIdentifiers.ReplaceAsWithCast);
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.InvertIsExpression))
            {
                InvertIsExpressionRefactoring.ComputeRefactoring(context, binaryExpression);
            }

            if (context.Span.IsContainedInSpanOrBetweenSpans(operatorToken))
            {
                if (context.IsRefactoringEnabled(RefactoringIdentifiers.ReplaceEqualsExpressionWithStringEquals))
                {
                    await ReplaceEqualsExpressionWithStringEqualsRefactoring.ComputeRefactoringAsync(context, binaryExpression).ConfigureAwait(false);
                }

                if (context.IsAnyRefactoringEnabled(
                        RefactoringIdentifiers.ReplaceEqualsExpressionWithStringIsNullOrEmpty,
                        RefactoringIdentifiers.ReplaceEqualsExpressionWithStringIsNullOrWhiteSpace))
                {
                    await ReplaceEqualsExpressionRefactoring.ComputeRefactoringsAsync(context, binaryExpression).ConfigureAwait(false);
                }
            }
        }
Exemplo n.º 30
0
        public static async Task ComputeRefactoringsAsync(RefactoringContext context, IfStatementSyntax ifStatement)
        {
            SyntaxToken ifKeyword = ifStatement.IfKeyword;

            bool isTopmostIf = ifStatement.IsTopmostIf();

            if (context.Span.IsEmptyAndContainedInSpan(ifKeyword) ||
                context.Span.IsBetweenSpans(ifStatement))
            {
                if (isTopmostIf &&
                    context.IsAnyRefactoringEnabled(
                        RefactoringIdentifiers.UseCoalesceExpressionInsteadOfIf,
                        RefactoringIdentifiers.ConvertIfToConditionalOperator,
                        RefactoringIdentifiers.SimplifyIf))
                {
                    SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                    IfAnalysisOptions options = GetIfAnalysisOptions(context);

                    foreach (IfAnalysis analysis in IfAnalysis.Analyze(ifStatement, options, semanticModel, context.CancellationToken))
                    {
                        string refactoringId = GetRefactoringIdentifier(analysis);

                        if (context.IsRefactoringEnabled(refactoringId))
                        {
                            context.RegisterRefactoring(
                                analysis.Title,
                                ct => IfRefactoring.RefactorAsync(context.Document, analysis, ct),
                                refactoringId);
                        }
                    }
                }

                if (context.IsAnyRefactoringEnabled(RefactoringIdentifiers.InvertIf, RefactoringIdentifiers.InvertIfElse) &&
                    context.Span.IsEmptyAndContainedInSpan(ifKeyword))
                {
                    InvertIfRefactoring.ComputeRefactoring(context, ifStatement);
                }

                if (context.IsRefactoringEnabled(RefactoringIdentifiers.ConvertIfToSwitch) &&
                    isTopmostIf)
                {
                    SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                    ConvertIfToSwitchRefactoring.ComputeRefactoring(context, ifStatement, semanticModel);
                }

                if (context.IsRefactoringEnabled(RefactoringIdentifiers.SplitIfStatement))
                {
                    SplitIfStatementRefactoring.ComputeRefactoring(context, ifStatement);
                }

                if (context.IsRefactoringEnabled(RefactoringIdentifiers.MergeIfWithParentIf) &&
                    isTopmostIf &&
                    context.Span.IsEmptyAndContainedInSpan(ifKeyword))
                {
                    MergeIfWithParentIfRefactoring.ComputeRefactoring(context, ifStatement);
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.InvertIf) &&
                context.Span.IsEmptyAndContainedInSpan(ifKeyword))
            {
                SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false);

                ReduceIfNestingAnalysisResult analysis = ReduceIfNestingAnalysis.Analyze(
                    ifStatement,
                    semanticModel,
                    options: ReduceIfNestingOptions.AllowNestedFix
                    | ReduceIfNestingOptions.AllowIfInsideIfElse
                    | ReduceIfNestingOptions.AllowLoop
                    | ReduceIfNestingOptions.AllowSwitchSection,
                    cancellationToken: context.CancellationToken);

                if (analysis.Success)
                {
                    context.RegisterRefactoring(
                        "Invert if",
                        ct => ReduceIfNestingRefactoring.RefactorAsync(context.Document, ifStatement, analysis.JumpKind, false, ct),
                        RefactoringIdentifiers.InvertIf);

                    if (ReduceIfNestingAnalysis.IsFixableRecursively(ifStatement, analysis.JumpKind))
                    {
                        context.RegisterRefactoring(
                            "Invert if (recursively)",
                            ct => ReduceIfNestingRefactoring.RefactorAsync(context.Document, ifStatement, analysis.JumpKind, true, ct),
                            EquivalenceKey.Join(RefactoringIdentifiers.InvertIf, "Recursive"));
                    }
                }
            }

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.SplitIfElse) &&
                context.Span.IsEmptyAndContainedInSpan(ifKeyword))
            {
                SplitIfElseRefactoring.ComputeRefactoring(context, ifStatement);
            }
        }