Exemplo n.º 1
0
        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))
            {
                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),
                                cancellationToken => RefactorAsync(context.Solution, memberDeclarations, accessibility, cancellationToken),
                                EquivalenceKey.Join(RefactoringIdentifiers.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),
                            cancellationToken => RefactorAsync(context.Solution, symbol, accessibility, cancellationToken),
                            EquivalenceKey.Join(RefactoringIdentifiers.ChangeAccessibility, accessibility.ToString()));
                    }
                }
                else if (SyntaxAccessibility.IsValidAccessibility(node, accessibility))
                {
                    context.RegisterRefactoring(
                        GetTitle(accessibility),
                        cancellationToken => RefactorAsync(context.Document, node, accessibility, cancellationToken),
                        EquivalenceKey.Join(RefactoringIdentifiers.ChangeAccessibility, accessibility.ToString()));
                }
            }

            ISymbol GetBaseSymbolOrDefault(SemanticModel semanticModel, CancellationToken cancellationToken)
            {
                if (modifiersInfo.GetKinds().Any(ModifierKinds.AbstractVirtualOverride))
                {
                    return(ChangeAccessibilityRefactoring.GetBaseSymbolOrDefault(node, semanticModel, cancellationToken));
                }

                return(null);
            }
        }
        public static void ComputeRefactoring(RefactoringContext context, MemberDeclarationSelection selectedMembers)
        {
            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ChangeAccessibility))
            {
                AccessibilityFlags accessibilityFlags = ChangeAccessibilityRefactoring.GetAccessibilityFlags(selectedMembers);

                if (accessibilityFlags != AccessibilityFlags.None)
                {
                    bool isAnyPartial = IsAnyPartial();

                    TryRegisterRefactoring(accessibilityFlags, Accessibility.Public, isAnyPartial);
                    TryRegisterRefactoring(accessibilityFlags, Accessibility.Internal, isAnyPartial);
                    TryRegisterRefactoring(accessibilityFlags, Accessibility.Protected, isAnyPartial);
                    TryRegisterRefactoring(accessibilityFlags, Accessibility.Private, isAnyPartial);
                }
            }

            void TryRegisterRefactoring(AccessibilityFlags accessibilityFlags, Accessibility accessibility, bool isAnyPartial)
            {
                if ((accessibilityFlags & accessibility.GetAccessibilityFlag()) != 0)
                {
                    if (isAnyPartial)
                    {
                        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));
                        });
                    }
                    else
                    {
                        context.RegisterRefactoring(
                            ChangeAccessibilityRefactoring.GetTitle(accessibility),
                            cancellationToken => ChangeAccessibilityRefactoring.RefactorAsync(context.Document, selectedMembers, accessibility, cancellationToken));
                    }
                }
            }

            bool IsAnyPartial()
            {
                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.StructDeclaration:
                    {
                        if (((StructDeclarationSyntax)member).Modifiers.Contains(SyntaxKind.PartialKeyword))
                        {
                            return(true);
                        }

                        break;
                    }

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

                        break;
                    }
                    }
                }

                return(false);
            }
        }
        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.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 void ComputeRefactoring(RefactoringContext context, MemberDeclarationSelection selectedMembers)
        {
            if (context.IsRefactoringEnabled(RefactoringIdentifiers.ChangeAccessibility))
            {
                AccessibilityFlags accessibilityFlags = ChangeAccessibilityRefactoring.GetAllowedAccessibilityFlags(selectedMembers, allowOverride: true);

                if (accessibilityFlags != AccessibilityFlags.None)
                {
                    bool canHaveMultipleDeclarations = CanHaveMultipleDeclarations();

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

            if (context.IsRefactoringEnabled(RefactoringIdentifiers.InitializeFieldFromConstructor))
            {
                InitializeFieldFromConstructorRefactoring.ComputeRefactoring(context, selectedMembers);
            }

            void TryRegisterRefactoring(AccessibilityFlags accessibilityFlags, Accessibility accessibility, bool canHaveMultipleDeclarations)
            {
                if ((accessibilityFlags & accessibility.GetAccessibilityFlag()) != 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));
                        });
                    }
                    else
                    {
                        context.RegisterRefactoring(
                            ChangeAccessibilityRefactoring.GetTitle(accessibility),
                            cancellationToken => ChangeAccessibilityRefactoring.RefactorAsync(context.Document, selectedMembers, accessibility, cancellationToken));
                    }
                }
            }

            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.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);
            }
        }