public sealed override async Task RegisterCodeFixesAsync(CodeFixContext context) { Diagnostic diagnostic = context.Diagnostics[0]; if (!Settings.IsEnabled(diagnostic.Id, CodeFixIdentifiers.ChangeAccessibility)) { return; } SyntaxNode root = await context.GetSyntaxRootAsync().ConfigureAwait(false); if (!TryFindFirstAncestorOrSelf( root, context.Span, out SyntaxNode node, predicate: CSharpOverriddenSymbolInfo.CanCreate)) { return; } SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false); OverriddenSymbolInfo overrideInfo = CSharpOverriddenSymbolInfo.Create(node, semanticModel, context.CancellationToken); if (!overrideInfo.Success) { return; } Accessibility newAccessibility = overrideInfo.OverriddenSymbol.DeclaredAccessibility; CodeAction codeAction = CodeAction.Create( $"Change accessibility to '{SyntaxFacts.GetText(newAccessibility)}'", cancellationToken => { if (node.Kind() == SyntaxKind.VariableDeclarator) { node = node.Parent.Parent; } SyntaxNode newNode; if (newAccessibility == Accessibility.Public && node is AccessorDeclarationSyntax) { newNode = SyntaxAccessibility.WithoutExplicitAccessibility(node); } else { newNode = SyntaxAccessibility.WithExplicitAccessibility(node, newAccessibility); } return(context.Document.ReplaceNodeAsync(node, newNode, cancellationToken)); }, GetEquivalenceKey(diagnostic)); context.RegisterCodeFix(codeAction, diagnostic); }
public static Task <Document> RefactorAsync( Document document, ConstructorDeclarationSyntax constructorDeclaration, CancellationToken cancellationToken) { ConstructorDeclarationSyntax newNode = SyntaxAccessibility.WithExplicitAccessibility(constructorDeclaration, Accessibility.Protected); return(document.ReplaceNodeAsync(constructorDeclaration, newNode, cancellationToken)); }
public sealed override async Task RegisterCodeFixesAsync(CodeFixContext context) { if (!Settings.IsCodeFixEnabled(CodeFixIdentifiers.ChangeAccessibility)) { return; } SyntaxNode root = await context.GetSyntaxRootAsync().ConfigureAwait(false); if (!TryFindFirstAncestorOrSelf( root, context.Span, out SyntaxNode node, predicate: f => OverriddenSymbolInfo.CanCreate(f))) { return; } foreach (Diagnostic diagnostic in context.Diagnostics) { switch (diagnostic.Id) { case CompilerDiagnosticIdentifiers.CannotChangeAccessModifiersWhenOverridingInheritedMember: { SemanticModel semanticModel = await context.GetSemanticModelAsync().ConfigureAwait(false); OverriddenSymbolInfo overrideInfo = OverriddenSymbolInfo.Create(node, semanticModel, context.CancellationToken); if (!overrideInfo.Success) { break; } Accessibility newAccessibility = overrideInfo.OverriddenSymbol.DeclaredAccessibility; CodeAction codeAction = CodeAction.Create( $"Change accessibility to '{SyntaxFacts.GetText(newAccessibility)}'", cancellationToken => { if (node.Kind() == SyntaxKind.VariableDeclarator) { node = node.Parent.Parent; } SyntaxNode newNode = SyntaxAccessibility.WithExplicitAccessibility(node, newAccessibility); return(context.Document.ReplaceNodeAsync(node, newNode, cancellationToken)); }, GetEquivalenceKey(diagnostic)); context.RegisterCodeFix(codeAction, diagnostic); break; } } } }
public static Task <Document> RefactorAsync( Document document, SyntaxNode node, Accessibility newAccessibility, CancellationToken cancellationToken) { SyntaxNode newNode = SyntaxAccessibility.WithExplicitAccessibility(node, newAccessibility); return(document.ReplaceNodeAsync(node, newNode, cancellationToken)); }
public static Task <Document> RefactorAsync( Document document, MemberDeclarationSyntax memberDeclaration, Accessibility accessibility, CancellationToken cancellationToken) { MemberDeclarationSyntax newNode = SyntaxAccessibility.WithExplicitAccessibility(memberDeclaration, accessibility); return(document.ReplaceNodeAsync(memberDeclaration, newNode, cancellationToken)); }
public static async Task <Solution> RefactorAsync( Solution solution, MemberDeclarationListSelection selectedMembers, Accessibility newAccessibility, SemanticModel semanticModel, CancellationToken cancellationToken) { var members = new HashSet <MemberDeclarationSyntax>(); foreach (MemberDeclarationSyntax member in selectedMembers) { ModifierFilter filter = SyntaxInfo.ModifierListInfo(member).GetFilter(); if (filter.HasAnyFlag(ModifierFilter.Partial)) { ISymbol symbol = semanticModel.GetDeclaredSymbol(member, cancellationToken); foreach (SyntaxReference reference in symbol.DeclaringSyntaxReferences) { members.Add((MemberDeclarationSyntax)reference.GetSyntax(cancellationToken)); } } else if (filter.HasAnyFlag(ModifierFilter.AbstractVirtualOverride)) { ISymbol symbol = GetBaseSymbolOrDefault(member, semanticModel, cancellationToken); if (symbol != null) { foreach (MemberDeclarationSyntax member2 in GetMemberDeclarations(symbol, cancellationToken)) { members.Add(member2); } foreach (MemberDeclarationSyntax member2 in await FindOverridingMemberDeclarationsAsync(symbol, solution, cancellationToken).ConfigureAwait(false)) { members.Add(member2); } } else { members.Add(member); } } else { members.Add(member); } } return(await solution.ReplaceNodesAsync( members, (node, _) => SyntaxAccessibility.WithExplicitAccessibility(node, newAccessibility), cancellationToken) .ConfigureAwait(false)); }
public static Task <Document> RefactorAsync( Document document, PropertyDeclarationSyntax propertyDeclaration, CancellationToken cancellationToken = default(CancellationToken)) { AccessorListSyntax accessorList = AccessorList(); if (propertyDeclaration.ExpressionBody != null) { accessorList = accessorList .AddAccessors(AutoGetAccessorDeclaration()); } else { AccessorDeclarationSyntax getter = propertyDeclaration.Getter(); if (getter != null) { if (SyntaxAccessibility.GetExplicitAccessibility(getter) == Accessibility.Private) { getter = SyntaxAccessibility.WithExplicitAccessibility(getter, Accessibility.Protected); } accessorList = accessorList.AddAccessors(getter .WithBody(null) .WithSemicolonToken(SemicolonToken())); } AccessorDeclarationSyntax setter = propertyDeclaration.Setter(); if (setter != null) { if (SyntaxAccessibility.GetExplicitAccessibility(setter) == Accessibility.Private) { setter = SyntaxAccessibility.WithExplicitAccessibility(setter, Accessibility.Protected); } accessorList = accessorList.AddAccessors(setter .WithBody(null) .WithSemicolonToken(SemicolonToken())); } } PropertyDeclarationSyntax newNode = propertyDeclaration .WithExpressionBody(null) .WithSemicolonToken(default(SyntaxToken)) .WithAccessorList(accessorList) .InsertModifier(SyntaxKind.AbstractKeyword) .RemoveModifier(SyntaxKind.VirtualKeyword) .WithTriviaFrom(propertyDeclaration) .WithFormatterAnnotation(); return(document.ReplaceNodeAsync(propertyDeclaration, newNode, cancellationToken)); }
public override async Task RegisterCodeFixesAsync(CodeFixContext context) { SyntaxNode root = await context.GetSyntaxRootAsync().ConfigureAwait(false); if (!TryFindFirstAncestorOrSelf(root, context.Span, out MemberDeclarationSyntax memberDeclaration)) { return; } foreach (Diagnostic diagnostic in context.Diagnostics) { switch (diagnostic.Id) { case DiagnosticIdentifiers.RemoveRedundantOverridingMember: { CodeAction codeAction = CodeActionFactory.RemoveMemberDeclaration(context.Document, memberDeclaration, equivalenceKey: GetEquivalenceKey(diagnostic)); context.RegisterCodeFix(codeAction, diagnostic); break; } case DiagnosticIdentifiers.AddAccessibilityModifiersOrViceVersa: { if (diagnostic.Properties.TryGetValue(nameof(Accessibility), out string accessibilityText)) { var accessibility = (Accessibility)Enum.Parse(typeof(Accessibility), accessibilityText); CodeAction codeAction = CodeAction.Create( "Add accessibility modifiers", ct => { MemberDeclarationSyntax newNode = SyntaxAccessibility.WithExplicitAccessibility(memberDeclaration, accessibility); return(context.Document.ReplaceNodeAsync(memberDeclaration, newNode, ct)); }, GetEquivalenceKey(diagnostic)); context.RegisterCodeFix(codeAction, diagnostic); } else { CodeAction codeAction = CodeAction.Create( "Remove accessibility modifiers", ct => { MemberDeclarationSyntax newNode = SyntaxAccessibility.WithoutExplicitAccessibility(memberDeclaration); return(context.Document.ReplaceNodeAsync(memberDeclaration, newNode, ct)); }, GetEquivalenceKey(diagnostic)); context.RegisterCodeFix(codeAction, diagnostic); } break; } case DiagnosticIdentifiers.RemoveRedundantSealedModifier: { ModifiersCodeFixRegistrator.RemoveModifier(context, diagnostic, memberDeclaration, SyntaxKind.SealedKeyword); break; } case DiagnosticIdentifiers.AvoidSemicolonAtEndOfDeclaration: { CodeAction codeAction = CodeAction.Create( "Remove unnecessary semicolon", cancellationToken => AvoidSemicolonAtEndOfDeclarationRefactoring.RefactorAsync(context.Document, memberDeclaration, cancellationToken), GetEquivalenceKey(diagnostic)); context.RegisterCodeFix(codeAction, diagnostic); break; } case DiagnosticIdentifiers.OrderModifiers: { CodeAction codeAction = CodeAction.Create( "Order modifiers", ct => OrderModifiersAsync(context.Document, memberDeclaration, ct), GetEquivalenceKey(diagnostic)); context.RegisterCodeFix(codeAction, diagnostic); break; } case DiagnosticIdentifiers.MakeFieldReadOnly: { var fieldDeclaration = (FieldDeclarationSyntax)memberDeclaration; SeparatedSyntaxList <VariableDeclaratorSyntax> declarators = fieldDeclaration.Declaration.Variables; string title = (declarators.Count == 1) ? $"Make '{declarators[0].Identifier.ValueText}' read-only" : "Make fields read-only"; ModifiersCodeFixRegistrator.AddModifier(context, diagnostic, fieldDeclaration, SyntaxKind.ReadOnlyKeyword, title: title); break; } case DiagnosticIdentifiers.UseConstantInsteadOfField: { CodeAction codeAction = CodeAction.Create( "Use constant instead of field", cancellationToken => UseConstantInsteadOfFieldRefactoring.RefactorAsync(context.Document, (FieldDeclarationSyntax)memberDeclaration, cancellationToken), GetEquivalenceKey(diagnostic)); context.RegisterCodeFix(codeAction, diagnostic); break; } case DiagnosticIdentifiers.UseReadOnlyAutoProperty: { CodeAction codeAction = CodeAction.Create( "Use read-only auto-property", cancellationToken => UseReadOnlyAutoPropertyAsync(context.Document, (PropertyDeclarationSyntax)memberDeclaration, cancellationToken), GetEquivalenceKey(diagnostic)); context.RegisterCodeFix(codeAction, diagnostic); break; } case DiagnosticIdentifiers.ConvertCommentToDocumentationComment: { CodeAction codeAction = CodeAction.Create( ConvertCommentToDocumentationCommentRefactoring.Title, cancellationToken => ConvertCommentToDocumentationCommentRefactoring.RefactorAsync(context.Document, memberDeclaration, context.Span, cancellationToken), GetEquivalenceKey(diagnostic)); context.RegisterCodeFix(codeAction, diagnostic); break; } case DiagnosticIdentifiers.MakeMethodExtensionMethod: { var methodDeclaration = (MethodDeclarationSyntax)memberDeclaration; CodeAction codeAction = CodeAction.Create( "Make method an extension method", cancellationToken => { ParameterSyntax parameter = methodDeclaration.ParameterList.Parameters[0]; ParameterSyntax newParameter = ModifierList.Insert(parameter, SyntaxKind.ThisKeyword); return(context.Document.ReplaceNodeAsync(parameter, newParameter, cancellationToken)); }, GetEquivalenceKey(diagnostic)); context.RegisterCodeFix(codeAction, diagnostic); break; } } } }
public static Task <Document> RefactorAsync( Document document, MemberDeclarationListSelection selectedMembers, Accessibility newAccessibility, CancellationToken cancellationToken) { SyntaxList <MemberDeclarationSyntax> newMembers = selectedMembers .UnderlyingList .ReplaceRange(selectedMembers.FirstIndex, selectedMembers.Count, selectedMembers.Select(f => SyntaxAccessibility.WithExplicitAccessibility(f, newAccessibility))); MemberDeclarationListInfo info = SyntaxInfo.MemberDeclarationListInfo(selectedMembers); return(document.ReplaceMembersAsync(info, newMembers, cancellationToken)); }