1using System.Collections.Immutable;
2using System.Composition;
4using System.Threading.Tasks;
10using System.Collections.Generic;
15 [ExportCodeFixProvider(LanguageNames.CSharp)]
20 private static readonly ImmutableDictionary<string, string> nameAttributeMap =
new Dictionary<string, string>
22 { CslaMemberConstants.Operations.DataPortalCreate, CslaMemberConstants.OperationAttributes.Create },
23 { CslaMemberConstants.Operations.DataPortalFetch, CslaMemberConstants.OperationAttributes.Fetch },
24 { CslaMemberConstants.Operations.DataPortalInsert, CslaMemberConstants.OperationAttributes.Insert },
25 { CslaMemberConstants.Operations.DataPortalUpdate, CslaMemberConstants.OperationAttributes.Update },
26 { CslaMemberConstants.Operations.DataPortalDelete, CslaMemberConstants.OperationAttributes.Delete },
27 { CslaMemberConstants.Operations.DataPortalDeleteSelf, CslaMemberConstants.OperationAttributes.DeleteSelf },
28 { CslaMemberConstants.Operations.DataPortalExecute, CslaMemberConstants.OperationAttributes.Execute },
29 { CslaMemberConstants.Operations.ChildCreate, CslaMemberConstants.OperationAttributes.CreateChild },
30 { CslaMemberConstants.Operations.ChildFetch, CslaMemberConstants.OperationAttributes.FetchChild },
31 { CslaMemberConstants.Operations.ChildInsert, CslaMemberConstants.OperationAttributes.InsertChild },
32 { CslaMemberConstants.Operations.ChildUpdate, CslaMemberConstants.OperationAttributes.UpdateChild },
33 { CslaMemberConstants.Operations.ChildDeleteSelf, CslaMemberConstants.OperationAttributes.DeleteSelfChild },
34 { CslaMemberConstants.Operations.ChildExecute, CslaMemberConstants.OperationAttributes.ExecuteChild }
35 }.ToImmutableDictionary();
37 public override ImmutableArray<string>
FixableDiagnosticIds => ImmutableArray.Create(Constants.AnalyzerIdentifiers.DoesOperationHaveAttribute);
39 public sealed
override FixAllProvider
GetFixAllProvider() => WellKnownFixAllProviders.BatchFixer;
43 var root = await context.Document.GetSyntaxRootAsync(context.CancellationToken).ConfigureAwait(
false);
45 context.CancellationToken.ThrowIfCancellationRequested();
47 var diagnostic = context.Diagnostics.First();
48 var methodNode = root.FindNode(diagnostic.Location.SourceSpan) as MethodDeclarationSyntax;
50 context.CancellationToken.ThrowIfCancellationRequested();
52 AddCodeFix(context, root, diagnostic, methodNode);
55 private static SyntaxNode AddAttribute(SyntaxNode root, MethodDeclarationSyntax methodNode,
string name)
57 var attribute = SyntaxFactory.Attribute(SyntaxFactory.ParseName(name));
58 var attributeList = SyntaxFactory.AttributeList(SyntaxFactory.SeparatedList<AttributeSyntax>().Add(attribute));
59 var newClassNode = methodNode.AddAttributeLists(attributeList);
60 return root.ReplaceNode(methodNode, newClassNode);
63 private static void AddCodeFix(CodeFixContext context, SyntaxNode root,
64 Diagnostic diagnostic, MethodDeclarationSyntax methodNode)
66 var newRoot = AddAttribute(root, methodNode, nameAttributeMap[methodNode.Identifier.ValueText]);
68 var description = DoesOperationHaveAttributeAnalyzerAddAttributeCodeFixConstants.AddAttributeDescription;
70 if (!root.HasUsing(DoesOperationHaveAttributeAnalyzerAddAttributeCodeFixConstants.CslaNamespace))
72 newRoot = (newRoot as CompilationUnitSyntax).AddUsings(
73 SyntaxFactory.UsingDirective(SyntaxFactory.ParseName(
74 DoesOperationHaveAttributeAnalyzerAddAttributeCodeFixConstants.CslaNamespace)));
75 description = DoesOperationHaveAttributeAnalyzerAddAttributeCodeFixConstants.AddAttributeAndUsingDescription;
78 context.RegisterCodeFix(
81 _ => Task.FromResult(context.Document.WithSyntaxRoot(newRoot)),
82 description), diagnostic);
override async Task RegisterCodeFixesAsync(CodeFixContext context)
override ImmutableArray< string > FixableDiagnosticIds
sealed override FixAllProvider GetFixAllProvider()