Skip to content

How to test diagnostic suppressor that suppresses rule from NuGet package? #1212

Description

@salkriaf34

I've written a diagnostic suppressor that suppresses SA1615 from the StyleCop.Analyzers NuGet package.

I've also written a unit test for the suppressor, but I can't get the diagnostic to trigger in it. I get Mismatch between number of diagnostics returned, expected "1" actual "0".

If I copy the code to a new project with the NuGet package installed, the diagnostic is reported.

Suppressor code
namespace MyCustomDiagnosticSuppressions
{
	using System.Collections.Immutable;
	using Microsoft.CodeAnalysis;
	using Microsoft.CodeAnalysis.Diagnostics;

	[DiagnosticAnalyzer(LanguageNames.CSharp)]
	public sealed class SA1615Suppressor
		: DiagnosticSuppressor
	{
		public const string DiagnosticId = "SA1615Suppressor";

		internal static readonly SuppressionDescriptor SuppressionDescriptor = new(
			id: DiagnosticId,
			suppressedDiagnosticId: "SA1615",
			justification: "Custom justification goes here.");

		public override ImmutableArray<SuppressionDescriptor> SupportedSuppressions { get; } = [SuppressionDescriptor];

		public override void ReportSuppressions(SuppressionAnalysisContext context)
		{
			foreach (Diagnostic diagnostic in context.ReportedDiagnostics)
			{
				bool shouldSuppress = true; // Custom logic goes here.

				if (shouldSuppress)
					context.ReportSuppression(Suppression.Create(SuppressionDescriptor, diagnostic));
			}
		}
	}
}
Unit test code
namespace MyCustomDiagnosticSuppressions.Test
{
	using System.Threading.Tasks;
	using Microsoft.CodeAnalysis.CSharp.Testing;
	using Microsoft.CodeAnalysis.Testing;
	using Microsoft.VisualStudio.TestTools.UnitTesting;

	[TestClass]
	public sealed class SA1615SuppressorTests
	{
		[TestMethod]
		public async Task Should_Be_Suppressed()
		{
			string testSourceCode =
				$$"""
				namespace TestNamespace
				{
				    using System;
				    using System.Threading.Tasks;

				    /// <summary>
				    /// Some class.
				    /// </summary>
				    public class TestClass
				    {
				        /// <summary>
				        /// Some method.
				        /// </summary>
				        public async Task TestMethod() => throw new NotSupportedException("Test");
				    }
				}
				""";

			await new CSharpAnalyzerTest<SA1615Suppressor, DefaultVerifier>
			{
				TestState =
				{
					ReferenceAssemblies = ReferenceAssemblies.Net.Net90.AddPackages([new PackageIdentity("StyleCop.Analyzers", "1.2.0-beta.556")]),
					Sources = { testSourceCode },
					ExpectedDiagnostics = { DiagnosticResult.CompilerWarning("SA1615").WithIsSuppressed(true) },
				},
			}.RunAsync().ConfigureAwait(false);
		}
	}
}
Unit test output
Test method MyCustomDiagnosticSuppressions.Test.SA1615SuppressorTests.Should_Be_Suppressed threw exception: 
System.InvalidOperationException: Mismatch between number of diagnostics returned, expected "1" actual "0"

Diagnostics:
    NONE.


  Stack Trace: 
DefaultVerifier.Equal[T](T expected, T actual, String message)
AnalyzerTest`1.VerifyDiagnosticResults(IEnumerable`1 actualResults, ImmutableArray`1 analyzers, DiagnosticResult[] expectedResults, IVerifier verifier)
AnalyzerTest`1.VerifyDiagnosticsAsync(EvaluatedProjectState primaryProject, ImmutableArray`1 additionalProjects, DiagnosticResult[] expected, IVerifier verifier, CancellationToken cancellationToken)
AnalyzerTest`1.RunImplAsync(CancellationToken cancellationToken)
AnalyzerTest`1.RunAsync(CancellationToken cancellationToken)
SA1615SuppressorTests.Should_Be_Suppressed() line 34
Screenshot showing SA1615 for the test code

Image

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions