static bool isEnabledWithAnalyzerConfigOptions( DiagnosticDescriptor descriptor, SeverityFilter severityFilter, Compilation? compilation, AnalyzerOptions? analyzerOptions, CancellationToken cancellationToken) { if (compilation != null && compilation.Options.SyntaxTreeOptionsProvider is { } treeOptions) { foreach (var tree in compilation.SyntaxTrees) { // Check if diagnostic is enabled by SyntaxTree.DiagnosticOptions or Bulk configuration from AnalyzerConfigOptions. if (treeOptions.TryGetDiagnosticValue(tree, descriptor.Id, cancellationToken, out var configuredValue) || analyzerOptions.TryGetSeverityFromBulkConfiguration(tree, compilation, descriptor, cancellationToken, out configuredValue)) { if (configuredValue != ReportDiagnostic.Suppress && !severityFilter.Contains(configuredValue)) { return true; } } } } return false; }
public static ImmutableArray <Diagnostic> GetAnalyzerDiagnostics <TCompilation>( this TCompilation c, DiagnosticAnalyzer[] analyzers, TestValidationMode validationMode, AnalyzerOptions?options = null) where TCompilation : Compilation { var compilationWithAnalyzers = c.WithAnalyzers(analyzers.ToImmutableArray(), options, CancellationToken.None); var diagnostics = c.GetDiagnostics(); if (validationMode != TestValidationMode.AllowCompileErrors) { CompilationUtils.ValidateNoCompileErrors(diagnostics); } var diagnosticDescriptors = analyzers.SelectMany(analyzer => analyzer.SupportedDiagnostics); var analyzerDiagnosticIds = diagnosticDescriptors.Select(diagnosticDescriptor => diagnosticDescriptor.Id); var allDiagnosticIds = new HashSet <string>(analyzerDiagnosticIds, StringComparer.Ordinal) { "AD0001" // Failures caught by the Analyzer Driver. }; var allDiagnostics = compilationWithAnalyzers.GetAllDiagnosticsAsync().Result; var resultDiagnostics = allDiagnostics.Where(diagnostic => allDiagnosticIds.Contains(diagnostic.Id)); return(resultDiagnostics.ToImmutableArray()); }
/// <summary> /// Returns a new compilation with attached diagnostic analyzers. /// </summary> /// <param name="compilation">Compilation to which analyzers are to be added.</param> /// <param name="analyzers">The set of analyzers to include in future analyses.</param> /// <param name="options">Options that are passed to analyzers.</param> /// <param name="cancellationToken">A cancellation token that can be used to abort analysis.</param> public static CompilationWithAnalyzers WithAnalyzers( this Compilation compilation, ImmutableArray <DiagnosticAnalyzer> analyzers, AnalyzerOptions?options = null, CancellationToken cancellationToken = default ) { return(new CompilationWithAnalyzers(compilation, analyzers, options, cancellationToken)); }
/// <summary> /// Tries to get configured severity for the given <paramref name="descriptor"/> /// for the given <paramref name="tree"/> from bulk configuration analyzer config options, i.e. /// 'dotnet_analyzer_diagnostic.category-%RuleCategory%.severity = %severity%' /// or /// 'dotnet_analyzer_diagnostic.severity = %severity%' /// </summary> public static bool TryGetSeverityFromBulkConfiguration( this AnalyzerOptions?analyzerOptions, SyntaxTree tree, Compilation compilation, DiagnosticDescriptor descriptor, out ReportDiagnostic severity) { // Analyzer bulk configuration does not apply to: // 1. Disabled by default diagnostics // 2. Compiler diagnostics // 3. Non-configurable diagnostics if (analyzerOptions == null || !descriptor.IsEnabledByDefault || descriptor.CustomTags.Any(tag => tag == WellKnownDiagnosticTags.Compiler || tag == WellKnownDiagnosticTags.NotConfigurable)) { severity = default; return(false); } // If user has explicitly configured severity for this diagnostic ID, that should be respected. if (compilation.Options.SpecificDiagnosticOptions.TryGetValue(descriptor.Id, out severity)) { return(true); } // If user has explicitly configured severity for this diagnostic ID, that should be respected. // For example, 'dotnet_diagnostic.CA1000.severity = error' if (tree.DiagnosticOptions.TryGetValue(descriptor.Id, out severity)) { return(true); } var analyzerConfigOptions = analyzerOptions.AnalyzerConfigOptionsProvider.GetOptions(tree); // If user has explicitly configured default severity for the diagnostic category, that should be respected. // For example, 'dotnet_analyzer_diagnostic.category-security.severity = error' var categoryBasedKey = GetCategoryBasedDotnetAnalyzerDiagnosticSeverityKey(descriptor.Category); if (analyzerConfigOptions.TryGetValue(categoryBasedKey, out var value) && TryParseSeverity(value, out severity)) { return(true); } // Otherwise, if user has explicitly configured default severity for all analyzer diagnostics, that should be respected. // For example, 'dotnet_analyzer_diagnostic.severity = error' if (analyzerConfigOptions.TryGetValue(DotnetAnalyzerDiagnosticSeverityKey, out value) && TryParseSeverity(value, out severity)) { return(true); } severity = default; return(false); }
/// <summary> /// Tries to get configured severity for the given <paramref name="descriptor"/> /// for the given <paramref name="tree"/> from bulk configuration analyzer config options, i.e. /// 'dotnet_analyzer_diagnostic.category-%RuleCategory%.severity = %severity%' /// or /// 'dotnet_analyzer_diagnostic.severity = %severity%' /// </summary> public static bool TryGetSeverityFromBulkConfiguration( this AnalyzerOptions?analyzerOptions, SyntaxTree tree, Compilation compilation, DiagnosticDescriptor descriptor, CancellationToken cancellationToken, out ReportDiagnostic severity) { // Analyzer bulk configuration does not apply to: // 1. Disabled by default diagnostics // 2. Compiler diagnostics // 3. Non-configurable diagnostics if (analyzerOptions == null || !descriptor.IsEnabledByDefault || descriptor.IsCompilerOrNotConfigurable()) { severity = default; return(false); } // If user has explicitly configured severity for this diagnostic ID, that should be respected and // bulk configuration should not be applied. // For example, 'dotnet_diagnostic.CA1000.severity = error' if (compilation.Options.SpecificDiagnosticOptions.ContainsKey(descriptor.Id) || compilation.Options.SyntaxTreeOptionsProvider?.TryGetDiagnosticValue(tree, descriptor.Id, cancellationToken, out _) == true || compilation.Options.SyntaxTreeOptionsProvider?.TryGetGlobalDiagnosticValue(descriptor.Id, cancellationToken, out _) == true) { severity = default; return(false); } var analyzerConfigOptions = analyzerOptions.AnalyzerConfigOptionsProvider.GetOptions(tree); // If user has explicitly configured default severity for the diagnostic category, that should be respected. // For example, 'dotnet_analyzer_diagnostic.category-security.severity = error' var categoryBasedKey = GetCategoryBasedDotnetAnalyzerDiagnosticSeverityKey(descriptor.Category); if (analyzerConfigOptions.TryGetValue(categoryBasedKey, out var value) && AnalyzerConfigSet.TryParseSeverity(value, out severity)) { return(true); } // Otherwise, if user has explicitly configured default severity for all analyzer diagnostics, that should be respected. // For example, 'dotnet_analyzer_diagnostic.severity = error' if (analyzerConfigOptions.TryGetValue(DotnetAnalyzerDiagnosticSeverityKey, out value) && AnalyzerConfigSet.TryParseSeverity(value, out severity)) { return(true); } severity = default; return(false); }
public CompilationWithAnalyzersOptions( AnalyzerOptions?options, Action <Exception, DiagnosticAnalyzer, Diagnostic>?onAnalyzerException, bool concurrentAnalysis, bool logAnalyzerExecutionTime, bool reportSuppressedDiagnostics, Func <Exception, bool>?analyzerExceptionFilter) { _options = options; _onAnalyzerException = onAnalyzerException; _analyzerExceptionFilter = analyzerExceptionFilter; _concurrentAnalysis = concurrentAnalysis; _logAnalyzerExecutionTime = logAnalyzerExecutionTime; _reportSuppressedDiagnostics = reportSuppressedDiagnostics; }
public async Task <ImmutableArray <Diagnostic> > GetDiagnosticsAsync(CancellationToken cancellationToken) { var compilation = await Project.GetCompilationAsync(cancellationToken).ConfigureAwait(false); var solution = Project.Solution; if (_lastWorkspaceAnalyzerOptionsSolution != solution) { _workspaceAnalyzerOptions = RoslynReflection.NewWorkspaceAnalyzerOptions(EmptyAnalyzerOptions, EmptyOptionSet, solution); _lastWorkspaceAnalyzerOptionsSolution = solution; } return(await compilation.WithAnalyzers(Analyzers, _workspaceAnalyzerOptions, cancellationToken) .GetAllDiagnosticsAsync(cancellationToken) .ConfigureAwait(false)); }
private static DiagnosticSeverity GetSeverity( this DiagnosticAnalyzer analyzer, Document document, AnalyzerOptions?analyzerOptions, OptionSet options, Compilation compilation) { var severity = DiagnosticSeverity.Hidden; if (!document.TryGetSyntaxTree(out var tree)) { return(severity); } foreach (var descriptor in analyzer.SupportedDiagnostics) { if (severity == DiagnosticSeverity.Error) { break; } if (analyzerOptions.TryGetSeverityFromBulkConfiguration(tree, compilation, descriptor, out var reportDiagnostic)) { var configuredSeverity = ToSeverity(reportDiagnostic); if (configuredSeverity > severity) { severity = configuredSeverity; } continue; } if (TryGetSeverityFromCodeStyleOption(descriptor, compilation, options, out var codeStyleSeverity)) { if (codeStyleSeverity > severity) { severity = codeStyleSeverity; } continue; } if (descriptor.DefaultSeverity > severity) { severity = descriptor.DefaultSeverity; } } return(severity);
public AnalysisScope( Compilation compilation, AnalyzerOptions?analyzerOptions, ImmutableArray <DiagnosticAnalyzer> analyzers, bool hasAllAnalyzers, bool concurrentAnalysis, bool categorizeDiagnostics ) : this( compilation.SyntaxTrees, analyzerOptions?.AdditionalFiles ?? ImmutableArray <AdditionalText> .Empty, analyzers, isPartialAnalysis : !hasAllAnalyzers, filterFile : null, filterSpanOpt : null, isSyntacticSingleFileAnalysis : false, concurrentAnalysis : concurrentAnalysis, categorizeDiagnostics : categorizeDiagnostics ) { }
public AsaAnalyzer(AnalyzerOptions?opts = null) : base(opts) { CustomPropertyExtractionDelegates.Add(ParseCustomAsaProperties); CustomObjectToValuesDelegates.Add(ParseCustomAsaObjectValues); }
// Analysis public static async Task <Diagnostic[]> AnalyzeAsync(Compilation compilation, DiagnosticAnalyzer[] analyzers, AnalyzerOptions?analyzerOptions, CancellationToken cancellationToken) { var compilationWithAnalyzers = compilation.WithAnalyzers(analyzers.ToImmutableArray(), analyzerOptions, cancellationToken); var diagnostics = await compilationWithAnalyzers.GetAllDiagnosticsAsync(cancellationToken).ConfigureAwait(false); return(diagnostics.Where(i => !IsCompilerDiagnostic(i)).OrderBy(i => i.Id).ThenBy(i => i.Location.SourceTree?.FilePath).ThenBy(i => i.Location.SourceSpan).ToArray()); }