Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.

using System.Reflection;
using Microsoft.CodeAnalysis.CSharp;
using Microsoft.CodeAnalysis.CSharp.Testing;
using Microsoft.CodeAnalysis.Text;
using Microsoft.VisualStudio.Composition.Analyzers;

public static partial class CSharpMultiAnalyzerVerifier
{
/// <summary>
/// Test class that configures all VSMEF analyzers for simultaneous testing.
/// </summary>
public class Test : CSharpCodeFixTest<VSMEF001PropertyMustHaveSetter, EmptyCodeFixProvider, DefaultVerifier>
{
/// <summary>
/// Initializes a new instance of the <see cref="Test"/> class.
/// </summary>
public Test()
{
this.ReferenceAssemblies = ReferencesHelper.DefaultReferences;
this.TestBehaviors |= TestBehaviors.SkipGeneratedCodeCheck;

this.SolutionTransforms.Add((solution, projectId) =>
{
var parseOptions = (CSharpParseOptions)solution.GetProject(projectId)!.ParseOptions!;
solution = solution.WithProjectParseOptions(projectId, parseOptions.WithLanguageVersion(LanguageVersion.CSharp12));
return solution;
});

this.TestState.AdditionalFilesFactories.Add(() =>
{
const string additionalFilePrefix = "AdditionalFiles.";
return from resourceName in Assembly.GetExecutingAssembly().GetManifestResourceNames()
where resourceName.StartsWith(additionalFilePrefix, StringComparison.Ordinal)
let content = ReadManifestResource(Assembly.GetExecutingAssembly(), resourceName)
select (filename: resourceName.Substring(additionalFilePrefix.Length), SourceText.From(content));
});
}

/// <inheritdoc/>
protected override IEnumerable<DiagnosticAnalyzer> GetDiagnosticAnalyzers()
{
return
[
new VSMEF001PropertyMustHaveSetter(),
new VSMEF002AvoidMixingAttributeVarietiesAnalyzer(),
new VSMEF003ExportTypeMismatchAnalyzer(),
new VSMEF004ExportWithoutImportingConstructorAnalyzer(),
new VSMEF005MultipleImportingConstructorsAnalyzer(),
new VSMEF006ImportNullabilityAnalyzer(),
new VSMEF007DuplicateImportAnalyzer(),
new VSMEF008ImportContractTypeMismatchAnalyzer(),
new VSMEF009ImportManyMemberCollectionTypeAnalyzer(),
new VSMEF010ImportManyParameterCollectionTypeAnalyzer(),
new VSMEF011BothImportAndImportManyAnalyzer(),
new VSMEF012DisallowMefAttributeVersionAnalyzer(),
];
}

private static string ReadManifestResource(Assembly assembly, string resourceName)
{
using (var reader = new StreamReader(assembly.GetManifestResourceStream(resourceName) ?? throw new ArgumentException("No such resource stream", nameof(resourceName))))
{
return reader.ReadToEnd();
}
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.

using Microsoft.CodeAnalysis.Text;

/// <summary>
/// A verifier that tests source code against all VSMEF analyzers simultaneously.
/// Used for tests that verify code produces no diagnostics from any analyzer.
/// </summary>
public static partial class CSharpMultiAnalyzerVerifier
{
/// <summary>
/// Verifies that the given source code produces no diagnostics from any VSMEF analyzer.
/// </summary>
/// <param name="source">The source code to analyze.</param>
/// <returns>A task representing the asynchronous operation.</returns>
public static Task VerifyAnalyzerAsync(string source)
{
var test = new Test { TestCode = source };
return test.RunAsync();
}

/// <summary>
/// Verifies that the given source code produces no diagnostics from any VSMEF analyzer,
/// with optional editor configuration.
/// </summary>
/// <param name="source">The source code to analyze.</param>
/// <param name="editorConfig">Optional editor configuration content.</param>
/// <returns>A task representing the asynchronous operation.</returns>
public static Task VerifyAnalyzerAsync(string source, string? editorConfig)
{
var test = new Test { TestCode = source };
if (editorConfig is not null)
{
test.TestState.AnalyzerConfigFiles.Add(("/.editorconfig", SourceText.From(editorConfig)));
}

return test.RunAsync();
}
}
Loading