Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update AnalyzersExtensions and SettingsHelper to use cached JsonValue objects where possible #3642

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
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
67 changes: 9 additions & 58 deletions StyleCop.Analyzers/StyleCop.Analyzers/AnalyzerExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ namespace StyleCop.Analyzers
using System;
using System.Collections.Concurrent;
using System.Collections.Immutable;
using System.Diagnostics.CodeAnalysis;
using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.Diagnostics;
using StyleCop.Analyzers.Settings.ObjectModel;
Expand All @@ -23,72 +24,19 @@ internal static class AnalyzerExtensions
/// </summary>
/// <param name="context">The analysis context.</param>
/// <param name="action">Action to be executed at completion of parsing of a document.</param>
public static void RegisterSyntaxTreeAction(this AnalysisContext context, Action<SyntaxTreeAnalysisContext, StyleCopSettings> action)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

📝 So this is a bit of a strange situation. The AnalysisContext.TryGetValue<TValue> method is effectively static - it doesn't access any state of AnalysisContext. In theory, you could do something like this:

delegate bool TryGetStyleCopSettingsFileJson(SourceText text, SourceTextValueProvider<Lazy<JsonValue>> valueProvider, out Lazy<JsonValue> value);

// This delegate can be captured and used in the callback
TryGetStyleCopSettingsFileJson tryGetValue = context.TryGetValue<Lazy<JsonValue>>;

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For cases where more than one callback is registered, it does seem like it would be more efficient to use an explicit start callback and only compute it once.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The big problem right now is re-creating the settings object over and over. Holding on to these two comments for later, when most of the work is done.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For cases where more than one callback is registered, it does seem like it would be more efficient to use an explicit start callback and only compute it once.

Handled in #3648

{
context.RegisterSyntaxTreeAction(
context =>
{
StyleCopSettings settings = context.GetStyleCopSettings(context.CancellationToken);
action(context, settings);
});
}

/// <summary>
/// Register an action to be executed at completion of parsing of a code document. A syntax tree action reports
/// diagnostics about the <see cref="SyntaxTree"/> of a document.
/// </summary>
/// <param name="context">The analysis context.</param>
/// <param name="action">Action to be executed at completion of parsing of a document.</param>
[SuppressMessage("MicrosoftCodeAnalysisPerformance", "RS1012:Start action has no registered actions", Justification = "This is not a start action")]
public static void RegisterSyntaxTreeAction(this CompilationStartAnalysisContext context, Action<SyntaxTreeAnalysisContext, StyleCopSettings> action)
{
var settingsFile = context.GetStyleCopSettingsFile(context.CancellationToken);

context.RegisterSyntaxTreeAction(
context =>
{
StyleCopSettings settings = context.GetStyleCopSettings(context.CancellationToken);
StyleCopSettings settings = context.GetStyleCopSettings(settingsFile);
action(context, settings);
});
}

/// <summary>
/// Register an action to be executed at completion of semantic analysis of a <see cref="SyntaxNode"/> with an
/// appropriate kind. A syntax node action can report diagnostics about a <see cref="SyntaxNode"/>, and can also
/// collect state information to be used by other syntax node actions or code block end actions.
/// </summary>
/// <param name="context">The analysis context.</param>
/// <param name="action">Action to be executed at completion of semantic analysis of a
/// <see cref="SyntaxNode"/>.</param>
/// <param name="syntaxKind">The kind of syntax that should be analyzed.</param>
/// <typeparam name="TLanguageKindEnum">Enum type giving the syntax node kinds of the source language for which
/// the action applies.</typeparam>
public static void RegisterSyntaxNodeAction<TLanguageKindEnum>(this AnalysisContext context, Action<SyntaxNodeAnalysisContext, StyleCopSettings> action, TLanguageKindEnum syntaxKind)
where TLanguageKindEnum : struct
{
context.RegisterSyntaxNodeAction(action, LanguageKindArrays<TLanguageKindEnum>.GetOrCreateArray(syntaxKind));
}

/// <summary>
/// Register an action to be executed at completion of semantic analysis of a <see cref="SyntaxNode"/> with an
/// appropriate kind. A syntax node action can report diagnostics about a <see cref="SyntaxNode"/>, and can also
/// collect state information to be used by other syntax node actions or code block end actions.
/// </summary>
/// <param name="context">The analysis context.</param>
/// <param name="action">Action to be executed at completion of semantic analysis of a
/// <see cref="SyntaxNode"/>.</param>
/// <param name="syntaxKinds">The kinds of syntax that should be analyzed.</param>
/// <typeparam name="TLanguageKindEnum">Enum type giving the syntax node kinds of the source language for which
/// the action applies.</typeparam>
public static void RegisterSyntaxNodeAction<TLanguageKindEnum>(this AnalysisContext context, Action<SyntaxNodeAnalysisContext, StyleCopSettings> action, ImmutableArray<TLanguageKindEnum> syntaxKinds)
where TLanguageKindEnum : struct
{
context.RegisterSyntaxNodeAction(
context =>
{
StyleCopSettings settings = context.GetStyleCopSettings(context.CancellationToken);
action(context, settings);
},
syntaxKinds);
}

/// <summary>
/// Register an action to be executed at completion of semantic analysis of a <see cref="SyntaxNode"/> with an
/// appropriate kind. A syntax node action can report diagnostics about a <see cref="SyntaxNode"/>, and can also
Expand Down Expand Up @@ -117,13 +65,16 @@ public static void RegisterSyntaxNodeAction<TLanguageKindEnum>(this CompilationS
/// <param name="syntaxKinds">The kinds of syntax that should be analyzed.</param>
/// <typeparam name="TLanguageKindEnum">Enum type giving the syntax node kinds of the source language for which
/// the action applies.</typeparam>
[SuppressMessage("MicrosoftCodeAnalysisPerformance", "RS1012:Start action has no registered actions", Justification = "This is not a start action")]
public static void RegisterSyntaxNodeAction<TLanguageKindEnum>(this CompilationStartAnalysisContext context, Action<SyntaxNodeAnalysisContext, StyleCopSettings> action, ImmutableArray<TLanguageKindEnum> syntaxKinds)
where TLanguageKindEnum : struct
{
var settingsFile = context.GetStyleCopSettingsFile(context.CancellationToken);

context.RegisterSyntaxNodeAction(
context =>
{
StyleCopSettings settings = context.GetStyleCopSettings(context.CancellationToken);
StyleCopSettings settings = context.GetStyleCopSettings(settingsFile);
action(context, settings);
},
syntaxKinds);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -58,16 +58,19 @@ public override void Initialize(AnalysisContext context)
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.EnableConcurrentExecution();

context.RegisterSyntaxNodeAction(this.methodDeclarationAction, SyntaxKind.MethodDeclaration);
context.RegisterSyntaxNodeAction(this.constructorDeclarationAction, SyntaxKind.ConstructorDeclaration);
context.RegisterSyntaxNodeAction(this.delegateDeclarationAction, SyntaxKind.DelegateDeclaration);
context.RegisterSyntaxNodeAction(this.indexerDeclarationAction, SyntaxKind.IndexerDeclaration);
context.RegisterSyntaxNodeAction(this.operatorDeclarationAction, SyntaxKind.OperatorDeclaration);
context.RegisterSyntaxNodeAction(this.conversionOperatorDeclarationAction, SyntaxKind.ConversionOperatorDeclaration);
context.RegisterSyntaxNodeAction(this.baseTypeDeclarationAction, SyntaxKinds.BaseTypeDeclaration);
context.RegisterSyntaxNodeAction(this.fieldDeclarationAction, SyntaxKind.FieldDeclaration);
context.RegisterSyntaxNodeAction(this.propertyDeclarationAction, SyntaxKind.PropertyDeclaration);
context.RegisterSyntaxNodeAction(this.enumMemberDeclarationAction, SyntaxKind.EnumMemberDeclaration);
context.RegisterCompilationStartAction(context =>
{
context.RegisterSyntaxNodeAction(this.methodDeclarationAction, SyntaxKind.MethodDeclaration);
context.RegisterSyntaxNodeAction(this.constructorDeclarationAction, SyntaxKind.ConstructorDeclaration);
context.RegisterSyntaxNodeAction(this.delegateDeclarationAction, SyntaxKind.DelegateDeclaration);
context.RegisterSyntaxNodeAction(this.indexerDeclarationAction, SyntaxKind.IndexerDeclaration);
context.RegisterSyntaxNodeAction(this.operatorDeclarationAction, SyntaxKind.OperatorDeclaration);
context.RegisterSyntaxNodeAction(this.conversionOperatorDeclarationAction, SyntaxKind.ConversionOperatorDeclaration);
context.RegisterSyntaxNodeAction(this.baseTypeDeclarationAction, SyntaxKinds.BaseTypeDeclaration);
context.RegisterSyntaxNodeAction(this.fieldDeclarationAction, SyntaxKind.FieldDeclaration);
context.RegisterSyntaxNodeAction(this.propertyDeclarationAction, SyntaxKind.PropertyDeclaration);
context.RegisterSyntaxNodeAction(this.enumMemberDeclarationAction, SyntaxKind.EnumMemberDeclaration);
});
}

/// <summary>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,15 +49,18 @@ public override void Initialize(AnalysisContext context)
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.EnableConcurrentExecution();

context.RegisterSyntaxNodeAction(this.typeDeclarationAction, SyntaxKinds.BaseTypeDeclaration);
context.RegisterSyntaxNodeAction(this.methodDeclarationAction, SyntaxKind.MethodDeclaration);
context.RegisterSyntaxNodeAction(this.constructorDeclarationAction, SyntaxKind.ConstructorDeclaration);
context.RegisterSyntaxNodeAction(this.destructorDeclarationAction, SyntaxKind.DestructorDeclaration);
context.RegisterSyntaxNodeAction(this.propertyDeclarationAction, SyntaxKind.PropertyDeclaration);
context.RegisterSyntaxNodeAction(this.indexerDeclarationAction, SyntaxKind.IndexerDeclaration);
context.RegisterSyntaxNodeAction(this.fieldDeclarationAction, SyntaxKinds.BaseFieldDeclaration);
context.RegisterSyntaxNodeAction(this.delegateDeclarationAction, SyntaxKind.DelegateDeclaration);
context.RegisterSyntaxNodeAction(this.eventDeclarationAction, SyntaxKind.EventDeclaration);
context.RegisterCompilationStartAction(context =>
{
context.RegisterSyntaxNodeAction(this.typeDeclarationAction, SyntaxKinds.BaseTypeDeclaration);
context.RegisterSyntaxNodeAction(this.methodDeclarationAction, SyntaxKind.MethodDeclaration);
context.RegisterSyntaxNodeAction(this.constructorDeclarationAction, SyntaxKind.ConstructorDeclaration);
context.RegisterSyntaxNodeAction(this.destructorDeclarationAction, SyntaxKind.DestructorDeclaration);
context.RegisterSyntaxNodeAction(this.propertyDeclarationAction, SyntaxKind.PropertyDeclaration);
context.RegisterSyntaxNodeAction(this.indexerDeclarationAction, SyntaxKind.IndexerDeclaration);
context.RegisterSyntaxNodeAction(this.fieldDeclarationAction, SyntaxKinds.BaseFieldDeclaration);
context.RegisterSyntaxNodeAction(this.delegateDeclarationAction, SyntaxKind.DelegateDeclaration);
context.RegisterSyntaxNodeAction(this.eventDeclarationAction, SyntaxKind.EventDeclaration);
});
}

/// <summary>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,8 +37,11 @@ public override void Initialize(AnalysisContext context)
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.EnableConcurrentExecution();

context.RegisterSyntaxNodeAction(this.typeDeclarationAction, SyntaxKinds.TypeDeclaration);
context.RegisterSyntaxNodeAction(this.methodDeclarationAction, SyntaxKind.MethodDeclaration);
context.RegisterCompilationStartAction(context =>
{
context.RegisterSyntaxNodeAction(this.typeDeclarationAction, SyntaxKinds.TypeDeclaration);
context.RegisterSyntaxNodeAction(this.methodDeclarationAction, SyntaxKind.MethodDeclaration);
});
}

/// <summary>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,10 @@ public override void Initialize(AnalysisContext context)
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.EnableConcurrentExecution();

context.RegisterSyntaxNodeAction(this.propertyDeclarationAction, SyntaxKind.PropertyDeclaration);
context.RegisterCompilationStartAction(context =>
{
context.RegisterSyntaxNodeAction(this.propertyDeclarationAction, SyntaxKind.PropertyDeclaration);
});
}

/// <summary>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -112,16 +112,19 @@ public override void Initialize(AnalysisContext context)
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.EnableConcurrentExecution();

context.RegisterSyntaxNodeAction(BaseTypeDeclarationAction, BaseTypeDeclarationKinds);
context.RegisterSyntaxNodeAction(MethodDeclarationAction, SyntaxKind.MethodDeclaration);
context.RegisterSyntaxNodeAction(ConstructorDeclarationAction, SyntaxKind.ConstructorDeclaration);
context.RegisterSyntaxNodeAction(DestructorDeclarationAction, SyntaxKind.DestructorDeclaration);
context.RegisterSyntaxNodeAction(PropertyDeclarationAction, SyntaxKind.PropertyDeclaration);
context.RegisterSyntaxNodeAction(IndexerDeclarationAction, SyntaxKind.IndexerDeclaration);
context.RegisterSyntaxNodeAction(FieldDeclarationAction, SyntaxKind.FieldDeclaration);
context.RegisterSyntaxNodeAction(DelegateDeclarationAction, SyntaxKind.DelegateDeclaration);
context.RegisterSyntaxNodeAction(EventDeclarationAction, SyntaxKind.EventDeclaration);
context.RegisterSyntaxNodeAction(EventFieldDeclarationAction, SyntaxKind.EventFieldDeclaration);
context.RegisterCompilationStartAction(context =>
{
context.RegisterSyntaxNodeAction(BaseTypeDeclarationAction, BaseTypeDeclarationKinds);
context.RegisterSyntaxNodeAction(MethodDeclarationAction, SyntaxKind.MethodDeclaration);
context.RegisterSyntaxNodeAction(ConstructorDeclarationAction, SyntaxKind.ConstructorDeclaration);
context.RegisterSyntaxNodeAction(DestructorDeclarationAction, SyntaxKind.DestructorDeclaration);
context.RegisterSyntaxNodeAction(PropertyDeclarationAction, SyntaxKind.PropertyDeclaration);
context.RegisterSyntaxNodeAction(IndexerDeclarationAction, SyntaxKind.IndexerDeclaration);
context.RegisterSyntaxNodeAction(FieldDeclarationAction, SyntaxKind.FieldDeclaration);
context.RegisterSyntaxNodeAction(DelegateDeclarationAction, SyntaxKind.DelegateDeclaration);
context.RegisterSyntaxNodeAction(EventDeclarationAction, SyntaxKind.EventDeclaration);
context.RegisterSyntaxNodeAction(EventFieldDeclarationAction, SyntaxKind.EventFieldDeclaration);
});
}

private static class Analyzer
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -97,8 +97,11 @@ public override void Initialize(AnalysisContext context)
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.EnableConcurrentExecution();

context.RegisterSyntaxNodeAction(BaseTypeDeclarationAction, BaseTypeDeclarationKinds);
context.RegisterSyntaxNodeAction(MethodDeclarationAction, SyntaxKind.MethodDeclaration);
context.RegisterCompilationStartAction(context =>
{
context.RegisterSyntaxNodeAction(BaseTypeDeclarationAction, BaseTypeDeclarationKinds);
context.RegisterSyntaxNodeAction(MethodDeclarationAction, SyntaxKind.MethodDeclaration);
});
}

private static class Analyzer
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,10 @@ public override void Initialize(AnalysisContext context)
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.EnableConcurrentExecution();

context.RegisterSyntaxNodeAction(EnumMemberDeclarationAction, SyntaxKind.EnumMemberDeclaration);
context.RegisterCompilationStartAction(context =>
{
context.RegisterSyntaxNodeAction(EnumMemberDeclarationAction, SyntaxKind.EnumMemberDeclaration);
});
}

private static class Analyzer
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -54,8 +54,11 @@ public override void Initialize(AnalysisContext context)
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.EnableConcurrentExecution();

context.RegisterSyntaxNodeAction(MethodDeclarationAction, SyntaxKind.MethodDeclaration);
context.RegisterSyntaxNodeAction(DelegateDeclarationAction, SyntaxKind.DelegateDeclaration);
context.RegisterCompilationStartAction(context =>
{
context.RegisterSyntaxNodeAction(MethodDeclarationAction, SyntaxKind.MethodDeclaration);
context.RegisterSyntaxNodeAction(DelegateDeclarationAction, SyntaxKind.DelegateDeclaration);
});
}

private static void HandleMethodDeclaration(SyntaxNodeAnalysisContext context, StyleCopSettings settings)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -55,9 +55,12 @@ public override void Initialize(AnalysisContext context)
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.EnableConcurrentExecution();

context.RegisterSyntaxNodeAction(TypeDeclarationAction, SyntaxKinds.TypeDeclaration);
context.RegisterSyntaxNodeAction(MethodDeclarationAction, SyntaxKind.MethodDeclaration);
context.RegisterSyntaxNodeAction(DelegateDeclarationAction, SyntaxKind.DelegateDeclaration);
context.RegisterCompilationStartAction(context =>
{
context.RegisterSyntaxNodeAction(TypeDeclarationAction, SyntaxKinds.TypeDeclaration);
context.RegisterSyntaxNodeAction(MethodDeclarationAction, SyntaxKind.MethodDeclaration);
context.RegisterSyntaxNodeAction(DelegateDeclarationAction, SyntaxKind.DelegateDeclaration);
});
}

private static void HandleTypeDeclaration(SyntaxNodeAnalysisContext context, StyleCopSettings settings)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,10 @@ public override void Initialize(AnalysisContext context)
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.EnableConcurrentExecution();

context.RegisterSyntaxNodeAction(TypeDeclarationAction, SyntaxKinds.TypeDeclaration);
context.RegisterCompilationStartAction(context =>
{
context.RegisterSyntaxNodeAction(TypeDeclarationAction, SyntaxKinds.TypeDeclaration);
});
}

private static void HandleTypeDeclaration(SyntaxNodeAnalysisContext context, StyleCopSettings settings)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -119,7 +119,10 @@ public override void Initialize(AnalysisContext context)
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.EnableConcurrentExecution();

context.RegisterSyntaxNodeAction(ConstructorDeclarationAction, SyntaxKind.ConstructorDeclaration);
context.RegisterCompilationStartAction(context =>
{
context.RegisterSyntaxNodeAction(ConstructorDeclarationAction, SyntaxKind.ConstructorDeclaration);
});
}

private static void HandleConstructorDeclaration(SyntaxNodeAnalysisContext context, StyleCopSettings settings)
Expand Down
Loading