Skip to content

Commit

Permalink
ci: improve test coverage and add snapshot tests for object conditions
Browse files Browse the repository at this point in the history
Signed-off-by: Alexander Linne <[email protected]>
  • Loading branch information
alexanderlinne committed Aug 26, 2024
1 parent 0ebfbdf commit 897a3c7
Show file tree
Hide file tree
Showing 56 changed files with 10,100 additions and 20 deletions.
21 changes: 19 additions & 2 deletions .config/dotnet-tools.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,24 @@
"tools": {
"csharpier": {
"version": "0.28.2",
"commands": ["dotnet-csharpier"]
"commands": [
"dotnet-csharpier"
],
"rollForward": false
},
"verify.tool": {
"version": "0.6.0",
"commands": [
"dotnet-verify"
],
"rollForward": false
},
"dotnet-reportgenerator-globaltool": {
"version": "5.3.8",
"commands": [
"reportgenerator"
],
"rollForward": false
}
}
}
}
21 changes: 10 additions & 11 deletions ArchUnitNET/Fluent/Syntax/Elements/ObjectConditionsDefinition.cs
Original file line number Diff line number Diff line change
Expand Up @@ -374,12 +374,11 @@ public static ICondition<TRuleType> DependOnAny(
)
{
var patternList = patterns.ToList();

bool Condition(TRuleType ruleType)
bool Condition(TRuleType ruleType, Architecture architecture)
{
return !ruleType.GetTypeDependencies().IsNullOrEmpty()
return !ruleType.GetTypeDependencies(architecture).IsNullOrEmpty()
&& ruleType
.GetTypeDependencies()
.GetTypeDependencies(architecture)
.Any(target =>
patternList.Any(pattern =>
target.FullNameMatches(pattern, useRegularExpressions)
Expand Down Expand Up @@ -421,7 +420,7 @@ bool Condition(TRuleType ruleType)
);
}

return new SimpleCondition<TRuleType>(Condition, description, failDescription);
return new ArchitectureCondition<TRuleType>(Condition, description, failDescription);
}

public static ICondition<TRuleType> DependOnAny(IType firstType, params IType[] moreTypes)
Expand Down Expand Up @@ -1943,7 +1942,7 @@ bool Condition(TRuleType obj, Architecture architecture)
goto NextAttribute;
}
}
else if (!argumentList.Contains(arg))
else if (!attributeArgs.Contains(arg))
{
goto NextAttribute;
}
Expand Down Expand Up @@ -2034,7 +2033,7 @@ bool Condition(TRuleType obj, Architecture architecture)
goto NextAttribute;
}
}
else if (!argumentList.Contains(arg))
else if (!attributeArgs.Contains(arg))
{
goto NextAttribute;
}
Expand Down Expand Up @@ -2136,7 +2135,7 @@ bool Condition(TRuleType obj, Architecture architecture)
goto NextAttribute;
}
}
else if (!argumentList.Contains(arg))
else if (!attributeArgs.Contains(arg))
{
goto NextAttribute;
}
Expand Down Expand Up @@ -3742,7 +3741,7 @@ bool Condition(TRuleType obj, Architecture architecture)
goto NextAttribute;
}
}
else if (!argumentList.Contains(arg))
else if (!attributeArgs.Contains(arg))
{
goto NextAttribute;
}
Expand Down Expand Up @@ -3833,7 +3832,7 @@ bool Condition(TRuleType obj, Architecture architecture)
goto NextAttribute;
}
}
else if (!argumentList.Contains(arg))
else if (!attributeArgs.Contains(arg))
{
goto NextAttribute;
}
Expand Down Expand Up @@ -3935,7 +3934,7 @@ bool Condition(TRuleType obj, Architecture architecture)
goto NextAttribute;
}
}
else if (!argumentList.Contains(arg))
else if (!attributeArgs.Contains(arg))
{
goto NextAttribute;
}
Expand Down
6 changes: 5 additions & 1 deletion ArchUnitNETTests/ArchUnitNETTests.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,9 @@
<ItemGroup>
<ProjectReference Include="..\ArchUnitNET.xUnit\ArchUnitNET.xUnit.csproj" />
<ProjectReference Include="..\TestAssembly\TestAssembly.csproj" />
<ProjectReference Include="..\TestAssemblies\AttributeAssembly\AttributeAssembly.csproj" />
<ProjectReference Include="..\TestAssemblies\DependencyAssembly\DependencyAssembly.csproj" />
<ProjectReference Include="..\TestAssemblies\VisibilityAssembly\VisibilityAssembly.csproj" />
</ItemGroup>

<ItemGroup>
Expand All @@ -18,7 +21,8 @@
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
<PrivateAssets>all</PrivateAssets>
</PackageReference>
<PackageReference Include="xunit" Version="2.7.1" />
<PackageReference Include="Verify.xunit" Version="26.1.6" />
<PackageReference Include="xunit" Version="2.9.0" />
<PackageReference Include="xunit.runner.visualstudio" Version="2.4.3" />
</ItemGroup>

Expand Down
89 changes: 89 additions & 0 deletions ArchUnitNETTests/AssemblyTestHelper/AssemblyTestHelper.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,89 @@
using System.Collections.Generic;
using System.Linq;
using System.Runtime.CompilerServices;
using System.Text;
using System.Threading.Tasks;
using ArchUnitNET.Domain;
using ArchUnitNET.Fluent;
using ArchUnitNET.Fluent.Extensions;
using VerifyXunit;
using Xunit;

namespace ArchUnitNETTests.AssemblyTestHelper;

public abstract class AssemblyTestHelper
{
private StringBuilder snapshot = new StringBuilder();

public readonly string NonExistentObjectName = "NotTheNameOfAnyObject";

public abstract Architecture Architecture { get; }

public void AddSnapshotHeader(string header)
{
snapshot.AppendLine("===== " + header + " =====\n");
}

private string FormatSnapshot(IArchRule rule, IEnumerable<EvaluationResult> results)
{
var formatted = new StringBuilder();
formatted.Append("Query: ");
formatted.AppendLine(rule.Description);
foreach (var result in results)
{
formatted.Append("Result: ");
formatted.AppendLine(result.Passed.ToString());
formatted.Append("Description: ");
formatted.AppendLine(result.ToString());
}
formatted.AppendLine("Message: ");
formatted.AppendLine(results.ToErrorMessage());
formatted.AppendLine();
return formatted.ToString();
}

public void AssertNoViolations(IArchRule rule)
{
var results = rule.Evaluate(Architecture);
var output = FormatSnapshot(rule, results);
if (!results.All(result => result.Passed))
{
Assert.Fail(output);
}
snapshot.Append(output);
}

public void AssertAnyViolations(IArchRule rule)
{
var results = rule.Evaluate(Architecture);
var output = FormatSnapshot(rule, results);
if (results.All(result => !result.Passed))
{
Assert.Fail("AssertOnlyViolations should be used for tests without passing results.");
}
if (results.All(result => result.Passed))
{
Assert.Fail(output);
}
snapshot.Append(output);
}

public void AssertOnlyViolations(IArchRule rule)
{
var results = rule.Evaluate(Architecture);
var output = FormatSnapshot(rule, results);
if (results.Any(result => result.Passed))
{
Assert.Fail(output);
}
snapshot.Append(output);
}

public Task AssertSnapshotMatches([CallerFilePath] string sourceFile = "")
{
return Verifier
.Verify(snapshot.ToString(), null, sourceFile)
.DisableDiff() // Don't open diff tool during the test
.UseDirectory("Snapshots");
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
using System.Runtime.CompilerServices;
using System.Threading.Tasks;
using ArchUnitNET.Fluent;

namespace ArchUnitNETTests.AssemblyTestHelper;

public static class AssemblyTestHelperExtensions
{
public static void AssertNoViolations(this IArchRule archRule, AssemblyTestHelper testHelper)
{
testHelper.AssertNoViolations(archRule);
}

public static void AssertAnyViolations(this IArchRule archRule, AssemblyTestHelper testHelper)
{
testHelper.AssertAnyViolations(archRule);
}

public static void AssertOnlyViolations(this IArchRule archRule, AssemblyTestHelper testHelper)
{
testHelper.AssertOnlyViolations(archRule);
}
}
127 changes: 127 additions & 0 deletions ArchUnitNETTests/AssemblyTestHelper/AttributeAssemblyTestHelper.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,127 @@
using System.Linq;
using ArchUnitNET.Domain;
using ArchUnitNET.Domain.Extensions;
using AttributeNamespace;

namespace ArchUnitNETTests.AssemblyTestHelper;

public class AttributeAssemblyTestHelpers : AssemblyTestHelper
{
public override Architecture Architecture
{
get => StaticTestArchitectures.AttributeArchitecture;
}

public string NonExistentAttributeValue = "NotTheValueOfAnyAttribute";

public object Attribute1Parameter1Value = "Argument";
public object Attribute1Parameter2Value = 0;
public object Attribute1Parameter3Value = typeof(TypeArgument);
public object Attribute1Parameter3InvalidValue = typeof(OtherTypeArgument);

public string Attribute1NamedParameter1Name = "NamedParameter1";
public object Attribute1NamedParameter1Value = typeof(NamedTypeArgument);
public (string, object) Attribute1NamedParameter1Pair = (
"NamedParameter1",
typeof(NamedTypeArgument)
);
public (string, object) Attribute1NamedParameter1InvalidNamePair = (
"OtherNamedParameter1",
typeof(NamedTypeArgument)
);
public (string, object) Attribute1NamedParameter1InvalidValuePair = (
"NamedParameter1",
typeof(OtherNamedTypeArgument)
);
public string Attribute1NamedParameter2Name = "NamedParameter2";
public object Attribute1NamedParameter2Value = "NamedArgument";
public (string, object) Attribute1NamedParameter2Pair = ("NamedParameter2", "NamedArgument");
public (string, object) Attribute1NamedParameter2InvalidNamePair = (
"OtherNamedParameter2",
"NamedArgument"
);
public (string, object) Attribute1NamedParameter2InvalidValuePair = (
"NamedParameter2",
"OtherNamedArgument"
);
public string Attribute1NamedParameter3Name = "NamedParameter3";
public object Attribute1NamedParameter3Value = 1;
public (string, object) Attribute1NamedParameter3Pair = ("NamedParameter3", 1);

public object Attribute2Parameter1Value = typeof(OtherTypeArgument);
public object Attribute2Parameter2Value = "OtherArgument";
public object Attribute2Parameter3Value = 2;

public string Attribute2NamedParameter1Name = "OtherNamedParameter1";
public object Attribute2NamedParameter1Value = "OtherNamedArgument";
public (string, object) Attribute2NamedParameter1Pair = (
"OtherNamedParameter1",
"OtherNamedArgument"
);
public string Attribute2NamedParameter2Name = "OtherNamedParameter2";
public object Attribute2NamedParameter2Value = 3;
public (string, object) Attribute2NamedParameter2Pair = ("OtherNamedParameter2", 3);
public string Attribute2NamedParameter3Name = "OtherNamedParameter3";
public object Attribute2NamedParameter3Value = typeof(OtherNamedTypeArgument);
public (string, object) Attribute2NamedParameter3Pair = (
"OtherNamedParameter3",
typeof(OtherNamedTypeArgument)
);

public string UnusedParameterName = "UnusedParameter";
public object UnusedParameterValue = "UnusedValueArgument";
public object UnusedTypeParameterValue = typeof(UnusedTypeArgument);

public Attribute Attribute1;
public System.Type Attribute1SystemType = typeof(Attribute1);

public Attribute Attribute2;
public System.Type Attribute2SystemType = typeof(Attribute2);

public Attribute UnusedAttribute;
public System.Type UnusedAttributeSystemType = typeof(UnusedAttribute);

public Class ClassWithoutAttributes;
public System.Type ClassWithoutAttributesSystemType = typeof(ClassWithoutAttributes);

public Class OtherClassWithoutAttributes;
public System.Type OtherClassWithoutAttributesSystemType = typeof(OtherClassWithoutAttributes);

public Class ClassWithSingleAttribute;
public System.Type ClassWithSingleAttributeSystemType = typeof(ClassWithSingleAttribute);

public Class OtherClassWithSingleAttribute;
public System.Type OtherClassWithSingleAttributeSystemType =
typeof(OtherClassWithSingleAttribute);

public Class ClassWithAttributes;
public System.Type ClassWithAttributesSystemType = typeof(ClassWithAttributes);

public Class OtherClassWithAttributes;
public System.Type OtherClassWithAttributesSystemType = typeof(OtherClassWithAttributes);

public Class ClassWithArguments;
public System.Type ClassWithArgumentsSystemType = typeof(ClassWithArguments);

public Class OtherClassWithArguments;
public System.Type OtherClassWithArgumentsSystemType = typeof(OtherClassWithArguments);

public AttributeAssemblyTestHelpers()
{
Attribute1 = Architecture.GetAttributeOfType(typeof(Attribute1));
Attribute2 = Architecture.GetAttributeOfType(typeof(Attribute2));
UnusedAttribute = Architecture.GetAttributeOfType(typeof(UnusedAttribute));
ClassWithoutAttributes = Architecture.GetClassOfType(typeof(ClassWithoutAttributes));
OtherClassWithoutAttributes = Architecture.GetClassOfType(
typeof(OtherClassWithoutAttributes)
);
ClassWithSingleAttribute = Architecture.GetClassOfType(typeof(ClassWithSingleAttribute));
OtherClassWithSingleAttribute = Architecture.GetClassOfType(
typeof(OtherClassWithSingleAttribute)
);
ClassWithAttributes = Architecture.GetClassOfType(typeof(ClassWithAttributes));
OtherClassWithAttributes = Architecture.GetClassOfType(typeof(OtherClassWithAttributes));
ClassWithArguments = Architecture.GetClassOfType(typeof(ClassWithArguments));
OtherClassWithArguments = Architecture.GetClassOfType(typeof(OtherClassWithArguments));
}
}
Loading

0 comments on commit 897a3c7

Please sign in to comment.