简体   繁体   中英

Static code analysis on Roslyn in-memory code

The Roslyn documentation gives the example below as a way of compiling some code and displaying any compilation errors.

I was wondering if anyone knows of a way to perform some static code analysis on the code contained in the variable sourceCode in the example below. I've added StyleCop.Analyzers to my test project but I cannot see at this stage how that could be used to perform a style analysis (for example readability).

Is it feasible to do this with StyleCop.Analyzers or is there an alternative approach? Any suggestion gratefully received.

Thanks.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.CSharp;
using Microsoft.CodeAnalysis.CSharp.Syntax;

namespace SemanticsCS
{
    class Program
    {
        static void Main(string[] args)
        {
            var sourceCode = @"using System;
                using System.Collections.Generic;
                using System.Text;

                namespace HelloWorld
                {
                    class Program
                    {
                        static void Main(string[] args)
                        {
                            Console.WriteLine(""Hello, World!"");
                        }
                    }
                }";
            SyntaxTree tree = CSharpSyntaxTree.ParseText(sourceCode);

            var root = (CompilationUnitSyntax)tree.GetRoot();
            var compilation = CSharpCompilation.Create("HelloWorld")
                                               .AddReferences(
                                                    MetadataReference.CreateFromFile(
                                                        typeof(object).Assembly.Location))
                                               .AddSyntaxTrees(tree);

            using (var ms = new MemoryStream())
            {
                EmitResult result = compilation.Emit(ms);
                if (!result.Success)
                {
                    IEnumerable<Diagnostic> failures = result.Diagnostics.Where(diagnostic =>
                        diagnostic.IsWarningAsError ||
                        diagnostic.Severity == DiagnosticSeverity.Error);

                    foreach (Diagnostic diagnostic in failures)
                    {
                        Console.WriteLine(diagnostic.ToString());
                        Console.Error.WriteLine("{0}({1})", diagnostic.GetMessage(), diagnostic.Id);
                    }
                }
            }
         }
    }
}

Actually, this is absolutely possible.

You need to add an analyzer reference to your Roslyn Compilation , using the WithAnalyzers method .

To make this work, you'll need to add a normal reference to StyleCop.Analy‌zers to your project, then create instances of the various DiagnosticAnalyzer s in it. Since they're internal , you'll need Reflection.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM