c# - Roslyn, can not get provider to update solution after codefix -


i have created analyzer detect if method not contain <createddate> tag in xml , provider inject tag. works fine , inserts tag still returns build error though rule has been fixed. think need use semantic models possibly?

this have: codefixprovider.cs

using system; using system.collections.immutable; using system.composition; using system.linq; using system.threading; using system.threading.tasks; using microsoft.codeanalysis; using microsoft.codeanalysis.codefixes; using microsoft.codeanalysis.codeactions; using microsoft.codeanalysis.csharp; using microsoft.codeanalysis.csharp.syntax; using microsoft.codeanalysis.formatting; using microsoft.codeanalysis.simplification; using microsoft.codeanalysis.rename;  namespace newanalyzer {     [exportcodefixprovider(languagenames.csharp, name = nameof(newanalyzercodefixprovider)), shared]     public class newanalyzercodefixprovider : codefixprovider     {         private const string title = "add createddate";          public sealed override immutablearray<string> fixablediagnosticids         {             { return immutablearray.create(newanalyzeranalyzer.diagnosticid); }         }          public sealed override fixallprovider getfixallprovider()         {             // see https://github.com/dotnet/roslyn/blob/master/docs/analyzers/fixallprovider.md more information on fix providers             return wellknownfixallproviders.batchfixer;         }          public sealed override task registercodefixesasync(codefixcontext context)         {             var diagnostic = context.diagnostics.first();             var diagnosticspan = diagnostic.location.sourcespan;             syntaxnode root;             context.document.trygetsyntaxroot(out root);              var syntax = root.findnode(diagnostic.location.sourcespan);              var methoddeclarationsyntax = syntax.firstancestororself<methoddeclarationsyntax>();              var description = "add created datetime api endpoint.";             var equivalencekey = "empty string";             context.registercodefix(codeaction.create(description, cancellationtoken => createchangeddocument(context, methoddeclarationsyntax, cancellationtoken), equivalencekey), diagnostic);             return task.fromresult(0);         }           /// <summary>         /// create new method contain changes required insert createddate tag comments.         /// </summary>         /// <param name="context">context</param>         /// <param name="methoddeclarationsyntax">method declaration syntax</param>         /// <param name="cancellationtoken">cancellation token</param>         /// <returns>new method contains createddate in comments</returns>         private static async task<document> createchangeddocument(codefixcontext context, methoddeclarationsyntax methoddeclarationsyntax, cancellationtoken cancellationtoken)         {             var originaltree = await context.document.getsyntaxtreeasync(cancellationtoken);             var newtree = await context.document.getsyntaxtreeasync(cancellationtoken);             var root = await newtree.getrootasync(cancellationtoken);              var documentationcomment = methoddeclarationsyntax.getleadingtrivia().select(i => i.getstructure()).oftype<documentationcommenttriviasyntax>().firstordefault();             var summaryelement = (xmlelementsyntax)documentationcomment.content.firstordefault(x => x xmlelementsyntax); // works               if (documentationcomment == null)                 return context.document;              var newlinetext = syntaxfactory.xmltextnewline(syntaxfactory.trivialist(), environment.newline, environment.newline, syntaxfactory.trivialist());              var createddatetext =             syntaxfactory.xmltext(syntaxfactory.tokenlist(                 syntaxfactory.xmltextliteral(                     syntaxfactory.trivialist(),                     datetime.utcnow.tostring("d"),                     datetime.utcnow.tostring("d"),                     syntaxfactory.trivialist())                     ));              var textlist = syntaxfactory.list<xmlnodesyntax>(new[] { createddatetext });             var createddatenode = new xmlnodesyntax[]             {                 syntaxfactory.xmltext().addtexttokens(syntaxfactory.xmltextnewline(syntaxfactory.trivialist(), environment.newline, environment.newline, syntaxfactory.trivialist())),                     syntaxfactory.xmlelement(syntaxfactory.xmlelementstarttag(syntaxfactory.xmlname("createddate")).withleadingtrivia(syntaxfactory.documentationcommentexterior("/// ")),                                     textlist,                                     syntaxfactory.xmlelementendtag(syntaxfactory.xmlname("createddate"))).withadditionalannotations(formatter.annotation, simplifier.annotation)             };              var list = syntaxfactory.list<xmlnodesyntax>(createddatenode);             syntaxnode tempnode = documentationcomment.insertnodesafter(summaryelement, list);              var newroot = root.replacenode(documentationcomment, tempnode);              var semanticmodel = await context.document.getsemanticmodelasync(cancellationtoken);              var typesymbol = semanticmodel.getdeclaredsymbol(methoddeclarationsyntax, cancellationtoken);              var semmodel = await context.document.getsemanticmodelasync();             var compilation = semmodel.compilation.replacesyntaxtree(originaltree, newtree);              var oldsemmodel = await context.document.getsemanticmodelasync();             oldsemmodel = semanticmodel;             return context.document;         }     } } 

and diagnosticanalyzer.cs

using system; using system.collections.generic; using system.collections.immutable; using system.linq; using system.threading; using microsoft.codeanalysis; using microsoft.codeanalysis.csharp; using microsoft.codeanalysis.csharp.syntax; using microsoft.codeanalysis.diagnostics;  namespace newanalyzer {     [diagnosticanalyzer(languagenames.csharp)]     public class newanalyzeranalyzer : diagnosticanalyzer     {         public const string diagnosticid = "na001";          // can change these strings in resources.resx file. if not want analyzer localize-able, can use regular strings title , messageformat.         // see https://github.com/dotnet/roslyn/blob/master/docs/analyzers/localizing%20analyzers.md more on localization         private static readonly localizablestring title = "title: createddate missing";         private static readonly localizablestring messageformat = "format: createddate missing";         private static readonly localizablestring description = "desc: createddate missing";         private const string category = "naming";          private static diagnosticdescriptor rule = new diagnosticdescriptor(diagnosticid, title, messageformat, category, diagnosticseverity.error, isenabledbydefault: true, description: description);          public override immutablearray<diagnosticdescriptor> supporteddiagnostics { { return immutablearray.create(rule); } }          public override void initialize(analysiscontext context)         {             // todo: consider registering other actions act on syntax instead of or in addition symbols             // see https://github.com/dotnet/roslyn/blob/master/docs/analyzers/analyzer%20actions%20semantics.md more information             //context.registersymbolaction(analyzesymbol, symbolkind.namedtype);             context.registersymbolaction(analyzemethod, symbolkind.method);         }          /// <summary>         /// analyze method see if it's rest endpoint method         /// </summary>         /// <param name="context">context</param>         private static void analyzemethod(symbolanalysiscontext context)         {             var methoddeclarationnode = context.symbol.getdocumentationcommentxml();              if (methoddeclarationnode != null)             {                 if (!methoddeclarationnode.contains("createddate"))                 {                     var diagnostic = diagnostic.create(rule, context.symbol.locations[0], methoddeclarationnode);                     context.reportdiagnostic(diagnostic);                 }             }         }     } } 

any ideas how let build pass when tag present in xml? seems not updating solution?

context.registersymbolaction(analyzemethod, symbolkind.method) execute callback property getters , setters too. codefix failing on properties, because can't find methoddeclarationsyntax reported location.

why did implement functionality symbol based analyzer? syntax node based one, , can subscribe methoddeclarations.

also, in codefix documentationcomment can null, , content of it, can fail too.

other these codefix adds current time.

these come when start debugging extension. maybe have @ exception settings window break on clr exceptions.


Comments

Popular posts from this blog

html - Styling progress bar with inline style -

java - Oracle Sql developer error: could not install some modules -

How to use autoclose brackets in Jupyter notebook? -