diff --git a/CHANGELOG.md b/CHANGELOG.md
index 31082aa6fb..ed4d1db3ee 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,6 +1,9 @@
# Changelog
All changes to the project will be documented in this file.
+## [1.34.16] - not yet released
+* Support for `` and `` (PR: [#1739](https://github.com/OmniSharp/omnisharp-roslyn/pull/1739))
+
## [1.34.15] - 2020-03-25
* Support for .NET Core 3.1 in csx files (PR: [#1731](https://github.com/OmniSharp/omnisharp-roslyn/pull/1731))
* Update the minimal MSBuild to better support .NET 5 Previews ([omnisharp-vscode#3653](https://github.com/OmniSharp/omnisharp-vscode/issues/3653), PR: [#1746](https://github.com/OmniSharp/omnisharp-roslyn/pull/1746))
diff --git a/build.json b/build.json
index 7301822d3e..8c09180fe8 100644
--- a/build.json
+++ b/build.json
@@ -38,6 +38,9 @@
"ProjectWithMultiTFMLib",
"ExternAlias",
"ProjectWithComplexAnalyzers",
+ "ProjectWithDisabledAnalyzers",
+ "ProjectWithDisabledAnalyzers2",
+ "ProjectWithAnalyzers",
"NetCore30Project",
"Net50Project"
],
@@ -50,4 +53,4 @@
"RestoreOnlyTestAssets": [
"ProjectWithMissingType"
]
-}
\ No newline at end of file
+}
diff --git a/src/OmniSharp.MSBuild/ProjectFile/ProjectFileInfo.ProjectData.cs b/src/OmniSharp.MSBuild/ProjectFile/ProjectFileInfo.ProjectData.cs
index 1e6aa214ee..6602d98f64 100644
--- a/src/OmniSharp.MSBuild/ProjectFile/ProjectFileInfo.ProjectData.cs
+++ b/src/OmniSharp.MSBuild/ProjectFile/ProjectFileInfo.ProjectData.cs
@@ -53,6 +53,8 @@ private class ProjectData
public ImmutableDictionary ReferenceAliases { get; }
public ImmutableDictionary ProjectReferenceAliases { get; }
public bool TreatWarningsAsErrors { get; }
+ public bool RunAnalyzers { get; }
+ public bool RunAnalyzersDuringLiveAnalysis { get; }
public string DefaultNamespace { get; }
private ProjectData()
@@ -91,6 +93,8 @@ private ProjectData(
string assemblyOriginatorKeyFile,
bool treatWarningsAsErrors,
string defaultNamespace,
+ bool runAnalyzers,
+ bool runAnalyzersDuringLiveAnalysis,
RuleSet ruleset)
: this()
{
@@ -122,6 +126,9 @@ private ProjectData(
TreatWarningsAsErrors = treatWarningsAsErrors;
RuleSet = ruleset;
DefaultNamespace = defaultNamespace;
+
+ RunAnalyzers = runAnalyzers;
+ RunAnalyzersDuringLiveAnalysis = runAnalyzersDuringLiveAnalysis;
}
private ProjectData(
@@ -149,12 +156,14 @@ private ProjectData(
ImmutableArray additionalFiles,
bool treatWarningsAsErrors,
string defaultNamespace,
+ bool runAnalyzers,
+ bool runAnalyzersDuringLiveAnalysis,
RuleSet ruleset,
ImmutableDictionary referenceAliases,
ImmutableDictionary projectReferenceAliases)
: this(guid, name, assemblyName, targetPath, outputPath, intermediateOutputPath, projectAssetsFile,
configuration, platform, targetFramework, targetFrameworks, outputKind, languageVersion, nullableContextOptions, allowUnsafeCode, checkForOverflowUnderflow,
- documentationFile, preprocessorSymbolNames, suppressedDiagnosticIds, signAssembly, assemblyOriginatorKeyFile, treatWarningsAsErrors, defaultNamespace, ruleset)
+ documentationFile, preprocessorSymbolNames, suppressedDiagnosticIds, signAssembly, assemblyOriginatorKeyFile, treatWarningsAsErrors, defaultNamespace, runAnalyzers, runAnalyzersDuringLiveAnalysis, ruleset)
{
SourceFiles = sourceFiles.EmptyIfDefault();
ProjectReferences = projectReferences.EmptyIfDefault();
@@ -200,11 +209,13 @@ public static ProjectData Create(MSB.Evaluation.Project project)
var signAssembly = PropertyConverter.ToBoolean(project.GetPropertyValue(PropertyNames.SignAssembly), defaultValue: false);
var assemblyOriginatorKeyFile = project.GetPropertyValue(PropertyNames.AssemblyOriginatorKeyFile);
var treatWarningsAsErrors = PropertyConverter.ToBoolean(project.GetPropertyValue(PropertyNames.TreatWarningsAsErrors), defaultValue: false);
+ var runAnalyzers = PropertyConverter.ToBoolean(project.GetPropertyValue(PropertyNames.RunAnalyzers), defaultValue: true);
+ var runAnalyzersDuringLiveAnalysis = PropertyConverter.ToBoolean(project.GetPropertyValue(PropertyNames.RunAnalyzersDuringLiveAnalysis), defaultValue: true);
return new ProjectData(
guid, name, assemblyName, targetPath, outputPath, intermediateOutputPath, projectAssetsFile,
configuration, platform, targetFramework, targetFrameworks, outputKind, languageVersion, nullableContextOptions, allowUnsafeCode, checkForOverflowUnderflow,
- documentationFile, preprocessorSymbolNames, suppressedDiagnosticIds, signAssembly, assemblyOriginatorKeyFile, treatWarningsAsErrors, defaultNamespace, ruleset: null);
+ documentationFile, preprocessorSymbolNames, suppressedDiagnosticIds, signAssembly, assemblyOriginatorKeyFile, treatWarningsAsErrors, defaultNamespace, runAnalyzers, runAnalyzersDuringLiveAnalysis, ruleset: null);
}
public static ProjectData Create(MSB.Execution.ProjectInstance projectInstance)
@@ -240,6 +251,8 @@ public static ProjectData Create(MSB.Execution.ProjectInstance projectInstance)
var suppressedDiagnosticIds = PropertyConverter.ToSuppressedDiagnosticIds(projectInstance.GetPropertyValue(PropertyNames.NoWarn));
var signAssembly = PropertyConverter.ToBoolean(projectInstance.GetPropertyValue(PropertyNames.SignAssembly), defaultValue: false);
var treatWarningsAsErrors = PropertyConverter.ToBoolean(projectInstance.GetPropertyValue(PropertyNames.TreatWarningsAsErrors), defaultValue: false);
+ var runAnalyzers = PropertyConverter.ToBoolean(projectInstance.GetPropertyValue(PropertyNames.RunAnalyzers), defaultValue: true);
+ var runAnalyzersDuringLiveAnalysis = PropertyConverter.ToBoolean(projectInstance.GetPropertyValue(PropertyNames.RunAnalyzersDuringLiveAnalysis), defaultValue: true);
var assemblyOriginatorKeyFile = projectInstance.GetPropertyValue(PropertyNames.AssemblyOriginatorKeyFile);
var ruleset = ResolveRulesetIfAny(projectInstance);
@@ -310,7 +323,7 @@ public static ProjectData Create(MSB.Execution.ProjectInstance projectInstance)
configuration, platform, targetFramework, targetFrameworks,
outputKind, languageVersion, nullableContextOptions, allowUnsafeCode, checkForOverflowUnderflow, documentationFile, preprocessorSymbolNames, suppressedDiagnosticIds,
signAssembly, assemblyOriginatorKeyFile,
- sourceFiles, projectReferences.ToImmutable(), references.ToImmutable(), packageReferences, analyzers, additionalFiles, treatWarningsAsErrors, defaultNamespace, ruleset,
+ sourceFiles, projectReferences.ToImmutable(), references.ToImmutable(), packageReferences, analyzers, additionalFiles, treatWarningsAsErrors, defaultNamespace, runAnalyzers, runAnalyzersDuringLiveAnalysis, ruleset,
referenceAliases.ToImmutableDictionary(), projectReferenceAliases.ToImmutable());
}
diff --git a/src/OmniSharp.MSBuild/ProjectFile/ProjectFileInfo.cs b/src/OmniSharp.MSBuild/ProjectFile/ProjectFileInfo.cs
index 1d7177847b..2d9651af76 100644
--- a/src/OmniSharp.MSBuild/ProjectFile/ProjectFileInfo.cs
+++ b/src/OmniSharp.MSBuild/ProjectFile/ProjectFileInfo.cs
@@ -55,6 +55,8 @@ internal partial class ProjectFileInfo
public ImmutableDictionary ReferenceAliases => _data.ReferenceAliases;
public ImmutableDictionary ProjectReferenceAliases => _data.ProjectReferenceAliases;
public bool TreatWarningsAsErrors => _data.TreatWarningsAsErrors;
+ public bool RunAnalyzers => _data.RunAnalyzers;
+ public bool RunAnalyzersDuringLiveAnalysis => _data.RunAnalyzersDuringLiveAnalysis;
public string DefaultNamespace => _data.DefaultNamespace;
public ProjectIdInfo ProjectIdInfo { get; }
diff --git a/src/OmniSharp.MSBuild/ProjectFile/ProjectFileInfoExtensions.cs b/src/OmniSharp.MSBuild/ProjectFile/ProjectFileInfoExtensions.cs
index ada58e331a..d983e7655e 100644
--- a/src/OmniSharp.MSBuild/ProjectFile/ProjectFileInfoExtensions.cs
+++ b/src/OmniSharp.MSBuild/ProjectFile/ProjectFileInfoExtensions.cs
@@ -76,6 +76,11 @@ public static ProjectInfo CreateProjectInfo(this ProjectFileInfo projectFileInfo
private static IEnumerable ResolveAnalyzerReferencesForProject(ProjectFileInfo projectFileInfo, IAnalyzerAssemblyLoader analyzerAssemblyLoader)
{
+ if (!projectFileInfo.RunAnalyzers || !projectFileInfo.RunAnalyzersDuringLiveAnalysis)
+ {
+ return Enumerable.Empty();
+ }
+
foreach(var analyzerAssemblyPath in projectFileInfo.Analyzers.Distinct())
{
analyzerAssemblyLoader.AddDependencyLocation(analyzerAssemblyPath);
diff --git a/src/OmniSharp.MSBuild/ProjectFile/PropertyNames.cs b/src/OmniSharp.MSBuild/ProjectFile/PropertyNames.cs
index d28f8e1a49..2b1f0806f5 100644
--- a/src/OmniSharp.MSBuild/ProjectFile/PropertyNames.cs
+++ b/src/OmniSharp.MSBuild/ProjectFile/PropertyNames.cs
@@ -32,6 +32,8 @@ internal static class PropertyNames
public const string _ResolveReferenceDependencies = nameof(_ResolveReferenceDependencies);
public const string RootNamespace = nameof(RootNamespace);
public const string RoslynTargetsPath = nameof(RoslynTargetsPath);
+ public const string RunAnalyzers = nameof(RunAnalyzers);
+ public const string RunAnalyzersDuringLiveAnalysis = nameof(RunAnalyzersDuringLiveAnalysis);
public const string SignAssembly = nameof(SignAssembly);
public const string SkipCompilerExecution = nameof(SkipCompilerExecution);
public const string SolutionDir = nameof(SolutionDir);
diff --git a/src/OmniSharp.MSBuild/ProjectManager.cs b/src/OmniSharp.MSBuild/ProjectManager.cs
index 6be793bfec..d14b8bd723 100644
--- a/src/OmniSharp.MSBuild/ProjectManager.cs
+++ b/src/OmniSharp.MSBuild/ProjectManager.cs
@@ -444,6 +444,12 @@ private void UpdateProject(string projectFilePath)
private void UpdateAnalyzerReferences(Project project, ProjectFileInfo projectFileInfo)
{
+ if (!projectFileInfo.RunAnalyzers || !projectFileInfo.RunAnalyzersDuringLiveAnalysis)
+ {
+ _workspace.SetAnalyzerReferences(project.Id, ImmutableArray.Empty);
+ return;
+ }
+
var analyzerFileReferences = projectFileInfo.Analyzers
.Select(analyzerReferencePath => new AnalyzerFileReference(analyzerReferencePath, _analyzerAssemblyLoader))
.ToImmutableArray();
diff --git a/test-assets/test-projects/ProjectWithDisabledAnalyzers/Program.cs b/test-assets/test-projects/ProjectWithDisabledAnalyzers/Program.cs
new file mode 100644
index 0000000000..8168c80511
--- /dev/null
+++ b/test-assets/test-projects/ProjectWithDisabledAnalyzers/Program.cs
@@ -0,0 +1,12 @@
+using System;
+
+namespace HelloWorld
+{
+ class Program
+ {
+ static void Main(string[] args)
+ {
+ Console.WriteLine("Hello World!");
+ }
+ }
+}
diff --git a/test-assets/test-projects/ProjectWithDisabledAnalyzers/ProjectWithDisabledAnalyzers.csproj b/test-assets/test-projects/ProjectWithDisabledAnalyzers/ProjectWithDisabledAnalyzers.csproj
new file mode 100644
index 0000000000..a769c05836
--- /dev/null
+++ b/test-assets/test-projects/ProjectWithDisabledAnalyzers/ProjectWithDisabledAnalyzers.csproj
@@ -0,0 +1,12 @@
+
+
+
+ Exe
+ netcoreapp2.1
+ ./nugets/
+ false
+
+
+
+
+
diff --git a/test-assets/test-projects/ProjectWithDisabledAnalyzers2/Program.cs b/test-assets/test-projects/ProjectWithDisabledAnalyzers2/Program.cs
new file mode 100644
index 0000000000..8168c80511
--- /dev/null
+++ b/test-assets/test-projects/ProjectWithDisabledAnalyzers2/Program.cs
@@ -0,0 +1,12 @@
+using System;
+
+namespace HelloWorld
+{
+ class Program
+ {
+ static void Main(string[] args)
+ {
+ Console.WriteLine("Hello World!");
+ }
+ }
+}
diff --git a/test-assets/test-projects/ProjectWithDisabledAnalyzers2/ProjectWithDisabledAnalyzers2.csproj b/test-assets/test-projects/ProjectWithDisabledAnalyzers2/ProjectWithDisabledAnalyzers2.csproj
new file mode 100644
index 0000000000..bfa10df6be
--- /dev/null
+++ b/test-assets/test-projects/ProjectWithDisabledAnalyzers2/ProjectWithDisabledAnalyzers2.csproj
@@ -0,0 +1,12 @@
+
+
+
+ Exe
+ netcoreapp2.1
+ ./nugets/
+ false
+
+
+
+
+
diff --git a/tests/OmniSharp.MSBuild.Tests/ProjectWithAnalyzersTests.cs b/tests/OmniSharp.MSBuild.Tests/ProjectWithAnalyzersTests.cs
index b219ead2e8..9b1d9219f3 100644
--- a/tests/OmniSharp.MSBuild.Tests/ProjectWithAnalyzersTests.cs
+++ b/tests/OmniSharp.MSBuild.Tests/ProjectWithAnalyzersTests.cs
@@ -67,7 +67,7 @@ public async Task WhenProjectHasAnalyzersItDoesntLockAnalyzerDlls()
public async Task WhenProjectIsLoadedThenItContainsCustomRulesetsFromCsproj()
{
using (var testProject = await TestAssets.Instance.GetTestProjectAsync("ProjectWithAnalyzers"))
- using (var host = CreateMSBuildTestHost(testProject.Directory))
+ using (var host = CreateMSBuildTestHost(testProject.Directory, configurationData: TestHelpers.GetConfigurationDataWithAnalyzerConfig(roslynAnalyzersEnabled: true)))
{
var project = host.Workspace.CurrentSolution.Projects.Single();
@@ -75,6 +75,20 @@ public async Task WhenProjectIsLoadedThenItContainsCustomRulesetsFromCsproj()
}
}
+ [Theory]
+ [InlineData("ProjectWithDisabledAnalyzers")]
+ [InlineData("ProjectWithDisabledAnalyzers2")]
+ public async Task WhenProjectWithRunAnalyzersDisabledIsLoadedThenAnalyzersAreIgnored(string projectName)
+ {
+ using var testProject = await TestAssets.Instance.GetTestProjectAsync(projectName);
+ await RestoreProject(testProject);
+
+ using var host = CreateMSBuildTestHost(testProject.Directory, configurationData: TestHelpers.GetConfigurationDataWithAnalyzerConfig(roslynAnalyzersEnabled: true));
+ var analyzerReferences = host.Workspace.CurrentSolution.Projects.Single().AnalyzerReferences.ToList();
+
+ Assert.Empty(analyzerReferences);
+ }
+
[Fact]
public async Task WhenProjectRulesetFileIsChangedThenUpdateRulesAccordingly()
{