Skip to content

Commit

Permalink
Fix the SetupSetAnalyzer.
Browse files Browse the repository at this point in the history
  • Loading branch information
GillesTourreau committed Oct 24, 2024
1 parent a06e5b9 commit 74df299
Show file tree
Hide file tree
Showing 3 changed files with 27 additions and 15 deletions.
6 changes: 3 additions & 3 deletions src/Moq.Analyzers/Analyzers/SetupSetAnalyzer.cs
Original file line number Diff line number Diff line change
Expand Up @@ -48,13 +48,13 @@ private static void Analyze(SyntaxNodeAnalysisContext context)

var methodSymbol = context.SemanticModel.GetSymbolInfo(invocationExpression, context.CancellationToken);

// Check if not obsolete extension
if (moqSymbols.IsObsoleteMockExtension(methodSymbol.Symbol))
// Check if SetupSet() method.
if (!moqSymbols.IsSetupSetMethod(methodSymbol.Symbol))
{
return;
}

// Check is Setup() method.
// Check is SetupSet<T>() method.
if (!moqSymbols.IsSetupSetMethodWithoutGenericArgument(methodSymbol.Symbol))
{
var nameSyntax = ((MemberAccessExpressionSyntax)invocationExpression.Expression).Name;
Expand Down
30 changes: 18 additions & 12 deletions src/Moq.Analyzers/MoqSymbols.cs
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ internal sealed class MoqSymbols

private readonly Lazy<IMethodSymbol> setupSetMethodWithoutGenericArgument;

private readonly Lazy<INamedTypeSymbol> obsoleteExtensionsClass;
private readonly Lazy<IReadOnlyList<IMethodSymbol>> setupSetMethods;

private MoqSymbols(INamedTypeSymbol mockGenericClass, Compilation compilation)
{
Expand All @@ -57,7 +57,6 @@ private MoqSymbols(INamedTypeSymbol mockGenericClass, Compilation compilation)
this.isAnyTypeClass = new Lazy<INamedTypeSymbol>(() => compilation.GetTypeByMetadataName("Moq.It+IsAnyType")!);
this.isAnyMethod = new Lazy<ISymbol>(() => compilation.GetTypeByMetadataName("Moq.It")!.GetMembers("IsAny").Single());
this.verifiesInterface = new Lazy<INamedTypeSymbol>(() => compilation.GetTypeByMetadataName("Moq.Language.IVerifies")!);
this.obsoleteExtensionsClass = new Lazy<INamedTypeSymbol>(() => compilation.GetTypeByMetadataName("Moq.ObsoleteMockExtensions")!);

this.setupMethods = new Lazy<IReadOnlyList<IMethodSymbol>>(() => mockGenericClass.GetMembers("Setup").Concat(setupConditionResultInterface.Value.GetMembers("Setup")).OfType<IMethodSymbol>().ToArray());
this.mockBehaviorStrictField = new Lazy<ISymbol>(() => this.mockBehaviorEnum.Value.GetMembers("Strict").First());
Expand All @@ -73,7 +72,9 @@ private MoqSymbols(INamedTypeSymbol mockGenericClass, Compilation compilation)
this.mockOfMethods = new Lazy<IReadOnlyList<IMethodSymbol>>(() => mockGenericClass.BaseType!.GetMembers("Of").Where(m => m.IsStatic).OfType<IMethodSymbol>().ToArray());

this.mockConstructorWithFactory = new Lazy<IMethodSymbol>(() => mockGenericClass.Constructors.Single(c => c.Parameters.Length == 2 && c.Parameters[0].Type.Name == "Expression"));

this.setupSetMethodWithoutGenericArgument = new Lazy<IMethodSymbol>(() => mockGenericClass.GetMembers("SetupSet").OfType<IMethodSymbol>().Single(c => c.TypeArguments.Length == 1));
this.setupSetMethods = new Lazy<IReadOnlyList<IMethodSymbol>>(() => mockGenericClass.GetMembers("SetupSet").OfType<IMethodSymbol>().ToArray());
}

public static MoqSymbols? FromCompilation(Compilation compilation)
Expand Down Expand Up @@ -128,22 +129,27 @@ public bool IsMock(ISymbol? symbol)
return true;
}

public bool IsObsoleteMockExtension(ISymbol? symbol)
public bool IsSetupMethod(ISymbol? symbol)
{
if (symbol is null)
{
return false;
}

if (!SymbolEqualityComparer.Default.Equals(symbol.ContainingType, this.obsoleteExtensionsClass.Value))
var originalDefinition = symbol.OriginalDefinition;

foreach (var setupMethod in this.setupMethods.Value)
{
return false;
if (SymbolEqualityComparer.Default.Equals(originalDefinition, setupMethod))
{
return true;
}
}

return true;
return false;
}

public bool IsSetupMethod(ISymbol? symbol)
public bool IsSetupProtectedMethod(ISymbol? symbol)
{
if (symbol is null)
{
Expand All @@ -152,9 +158,9 @@ public bool IsSetupMethod(ISymbol? symbol)

var originalDefinition = symbol.OriginalDefinition;

foreach (var setupMethod in this.setupMethods.Value)
foreach (var setupProtectedMethod in this.setupProtectedMethods.Value)
{
if (SymbolEqualityComparer.Default.Equals(originalDefinition, setupMethod))
if (SymbolEqualityComparer.Default.Equals(originalDefinition, setupProtectedMethod))
{
return true;
}
Expand All @@ -163,7 +169,7 @@ public bool IsSetupMethod(ISymbol? symbol)
return false;
}

public bool IsSetupProtectedMethod(ISymbol? symbol)
public bool IsSetupSetMethod(ISymbol? symbol)
{
if (symbol is null)
{
Expand All @@ -172,9 +178,9 @@ public bool IsSetupProtectedMethod(ISymbol? symbol)

var originalDefinition = symbol.OriginalDefinition;

foreach (var setupProtectedMethod in this.setupProtectedMethods.Value)
foreach (var setupSetMethod in this.setupSetMethods.Value)
{
if (SymbolEqualityComparer.Default.Equals(originalDefinition, setupProtectedMethod))
if (SymbolEqualityComparer.Default.Equals(originalDefinition, setupSetMethod))
{
return true;
}
Expand Down
6 changes: 6 additions & 0 deletions tests/Moq.Analyzers.Tests/Analyzers/SetupSetAnalyzerTest.cs
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,9 @@ public void TestMethod()
var mock1 = new Mock<I>();
mock1.SetupSet<int>(i => i.TestProperty = 1234);
mock1.SetupSet(i => i.TestProperty); // Ignored because Obsolete by Moq
var s = ""The string"";
s.ToString(); // Invocation should be ignored
}
}
Expand Down Expand Up @@ -53,6 +56,9 @@ public void TestMethod()
{
var mock1 = new Mock<I>();
mock1.[|SetupSet|](i => i.TestProperty = 1234);
var s = ""The string"";
s.ToString(); // Invocation should be ignored
}
}
Expand Down

0 comments on commit 74df299

Please sign in to comment.