“带有代码修复的分析器”项目模板已损坏

Ren*_*ogt 10 c# unit-testing roslyn-code-analysis visual-studio-2019

简短问题:如何在 Visual Studio 2019 v16.6.2 中使用工作单元测试项目设置 roslyn 代码分析器项目?

几个月前(以及一些 Visual Studio 更新),我尝试使用“Analyzer with Code Fix (.NET Standard)”项目模板设置代码分析器项目。它运行良好,并且正如所有可用的操作方法中所记录的那样。

今天(VS2019 v16.6.2)我想开始一个真正的分析器项目,但不幸的是更新的模板似乎已损坏或发布,还有很多未完成的工作正在进行中。(一个小问题是包管理器突然似乎无法恢复包,因为它不喜欢使用与分析器项目相同的程序集名称的 vsix 项目。)

该模板包含一个单元测试项目。在我试验的早期版本中,这个测试项目包含大量代码,这些代码充当测试基础设施,使开发人员可以轻松地针对真实代码测试分析器。

所有这些代码现在似乎都集成在许多特定于语言的 nuget 包中。但是这些包

这些是显然需要的包引用(省略测试框架包):

  • Microsoft.CodeAnalysis.CSharp.Analyzer.Testing.MSTest v1.0.1-beta1.20384.1
  • Microsoft.CodeAnalysis.CSharp.CodeFix.Testing.MSTest v1.0.1-beta1.20384.1
  • Microsoft.CodeAnalysis.CSharp.CodeRefactoring.Testing.MSTest v1.0.1-beta1.20384.1

这是示例单元测试代码:

using System.Threading.Tasks;
using Microsoft.VisualStudio.TestTools.UnitTesting;

using Verify = Microsoft.CodeAnalysis.CSharp.CodeFix.Testing.MSTest.CodeFixVerifier<
    Analyzer1.Analyzer1Analyzer,
    Analyzer1.Analyzer1CodeFixProvider>;

namespace Analyzer1.Test
{
    [TestClass]
    public class UnitTest
    {
        //No diagnostics expected to show up
        [TestMethod]
        public async Task TestMethod1()
        {
            var test = @"";

            await Verify.VerifyCSharpDiagnosticAsync(test);
        }

        //...
Run Code Online (Sandbox Code Playgroud)

我设法通过添加正确的源 url 来安装软件包,并将所有引用的软件包更新到最新(预发布)版本。但是无论我怎么尝试,这个模板代码都无法编译,因为命名空间

Microsoft.CodeAnalysis.CSharp.CodeFix

(在 的别名声明中使用Verify找不到。谷歌搜索那个命名空间只会让我回到 myget.org 站点以获取Microsoft.CodeAnalysis.CSharp.CodeFix.Testing.*软件包。


那么,我该怎么做才能为我的代码分析器项目设置一个工作单元测试(最好是 mstest)项目?我也可以使用直接在项目中包含所有帮助程序代码的“旧”版本,而不是使用明显未完成的 nuget 包。


更新:在实施AndrewSilvers 的回答后,模板中的第二个测试失败:

    [TestMethod]
    public async Task TestMethod2()
    {
        var test = @"
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Diagnostics;

namespace ConsoleApplication1
{
    class TypeName
    {   
    }
}";

        var fixtest = @"
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Diagnostics;

namespace ConsoleApplication1
{
    class TYPENAME
    {   
    }
}";

        var expected = Verify.Diagnostic("Analyzer1").WithLocation(11, 15).WithArguments("TypeName");
        await Verify.VerifyCodeFixAsync(test, expected, fixtest);
    }
}
Run Code Online (Sandbox Code Playgroud)

声明发现了一个诊断,但没有预期(这显然是错误的,该测试显然需要一个诊断)。

所以问题仍然存在:如何修复这个测试项目?

Vik*_*ing 7

我找到了几个带有工作单元测试的存储库:

他们似乎都在使用“手动”方法,其中包含项目中的帮助程序代码。虽然它们没有说明捆绑到“测试版”nuget 中的项目模板和帮助程序代码发生了什么,但至少它们提供了一个工作起点。

更新:微软已更新其文档;“构建你的第一个分析器和代码修复”教程现在在先决条件部分有一个注释,说明模板中存在一个应该在 Visual Studio v16.7 中修复的错误。该说明还提供了在此之前修复生成的项目的步骤。

更新 2:按照说明中的步骤进行操作。事实上,对于测试源,它们与 AndrewSilver 在他的回答中提供的相同。得到相同的结果,第二次测试失败。哦,好吧,回到第一个。

更新 3:好的,我想我明白了。简短版本:将以下行添加到分析器的Initialize方法中:

context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
Run Code Online (Sandbox Code Playgroud)

长版

花了一些时间调试库。罪魁祸首似乎是这一行,该行将声明您的预期诊断消息排除在外,并将其从预期结果列表中丢弃,从而由于实际(1)和预期(现在为 0)诊断之间的不匹配而导致测试失败。正要提出问题,但决定检查是否已经存在类似的问题。,的确,它指向另一个漫长的线程这个解决方案

顺便说一下,项目的README 文件提供了更多的使用示例。


And*_*ver 5

我最近遇到了同样的问题。感谢您提及更改的 nuget URL。在 VS 设置中更改它后,我已经能够通过删除.CodeFix此处的部分来编译项目

using Verify = Microsoft.CodeAnalysis.CSharp.CodeFix.Testing.MSTest.CodeFixVerifier<
    Analyzer1.Analyzer1Analyzer,
    Analyzer1.Analyzer1CodeFixProvider>;
Run Code Online (Sandbox Code Playgroud)

和之后通过更换VerifyCSharpDiagnosticAsyncVerifyAnalyzerAsync在第一单元测试和VerifyCSharpFixAsyncVerifyCodeFixAsync在第二个。

不幸的是,其中一个单元测试还没有工作。我将不胜感激对此问题的任何帮助。