Skip to content

Commit cd6bb2a

Browse files
committed
Introduced the [CustomAssertionsAssembly] to mark an entire assembly as one that contains custom assertions.
1 parent 514ed4c commit cd6bb2a

File tree

14 files changed

+111
-6
lines changed

14 files changed

+111
-6
lines changed

FluentAssertions.sln

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,8 @@ Project("{778DAE3C-4631-46EA-AA77-85C1314464D9}") = "VB.Specs", "Tests\VB.Specs\
5151
EndProject
5252
Project("{6EC3EE1D-3C4E-46DD-8F32-0CC8E7565705}") = "FSharp.Specs", "Tests\FSharp.Specs\FSharp.Specs.fsproj", "{0A69DC62-CA14-44E5-BAF9-2EB2E2E2CADF}"
5353
EndProject
54+
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ExampleExtensions", "Tests\ExampleExtensions\ExampleExtensions.csproj", "{8DF4A6FE-AAD0-41E5-B2F4-34166D1B139C}"
55+
EndProject
5456
Global
5557
GlobalSection(SolutionConfigurationPlatforms) = preSolution
5658
CI|Any CPU = CI|Any CPU
@@ -141,6 +143,12 @@ Global
141143
{0A69DC62-CA14-44E5-BAF9-2EB2E2E2CADF}.Debug|Any CPU.Build.0 = Debug|Any CPU
142144
{0A69DC62-CA14-44E5-BAF9-2EB2E2E2CADF}.Release|Any CPU.ActiveCfg = Release|Any CPU
143145
{0A69DC62-CA14-44E5-BAF9-2EB2E2E2CADF}.Release|Any CPU.Build.0 = Release|Any CPU
146+
{8DF4A6FE-AAD0-41E5-B2F4-34166D1B139C}.CI|Any CPU.ActiveCfg = Debug|Any CPU
147+
{8DF4A6FE-AAD0-41E5-B2F4-34166D1B139C}.CI|Any CPU.Build.0 = Debug|Any CPU
148+
{8DF4A6FE-AAD0-41E5-B2F4-34166D1B139C}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
149+
{8DF4A6FE-AAD0-41E5-B2F4-34166D1B139C}.Debug|Any CPU.Build.0 = Debug|Any CPU
150+
{8DF4A6FE-AAD0-41E5-B2F4-34166D1B139C}.Release|Any CPU.ActiveCfg = Release|Any CPU
151+
{8DF4A6FE-AAD0-41E5-B2F4-34166D1B139C}.Release|Any CPU.Build.0 = Release|Any CPU
144152
EndGlobalSection
145153
GlobalSection(SolutionProperties) = preSolution
146154
HideSolutionNode = FALSE
@@ -160,6 +168,7 @@ Global
160168
{A946043D-D3F8-46A4-B485-A88412C417FE} = {963262D0-9FD5-4741-8C0E-E2F34F110EF3}
161169
{0C0211B6-D185-4518-A15A-38AC092EDC50} = {963262D0-9FD5-4741-8C0E-E2F34F110EF3}
162170
{0A69DC62-CA14-44E5-BAF9-2EB2E2E2CADF} = {963262D0-9FD5-4741-8C0E-E2F34F110EF3}
171+
{8DF4A6FE-AAD0-41E5-B2F4-34166D1B139C} = {963262D0-9FD5-4741-8C0E-E2F34F110EF3}
163172
EndGlobalSection
164173
GlobalSection(ExtensibilityGlobals) = postSolution
165174
SolutionGuid = {75DDA3D8-9D6F-4865-93F4-DDE11DEE8290}

Src/FluentAssertions/CallerIdentifier.cs

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
using System.Globalization;
44
using System.IO;
55
using System.Linq;
6+
using System.Reflection;
67
using System.Text.RegularExpressions;
78
using System.Threading;
89
using FluentAssertions.CallerIdentification;
@@ -137,7 +138,16 @@ internal static bool OnlyOneFluentAssertionScopeOnCallStack()
137138

138139
private static bool IsCustomAssertion(StackFrame frame)
139140
{
140-
return frame.GetMethod()?.IsDecoratedWithOrInherit<CustomAssertionAttribute>() == true;
141+
MethodBase getMethod = frame.GetMethod();
142+
143+
if (getMethod is not null)
144+
{
145+
return
146+
getMethod.IsDecoratedWithOrInherit<CustomAssertionAttribute>() ||
147+
getMethod.ReflectedType?.Assembly.IsDefined(typeof(CustomAssertionsAssemblyAttribute)) == true;
148+
}
149+
150+
return false;
141151
}
142152

143153
private static bool IsDynamic(StackFrame frame)
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
using System;
2+
3+
namespace FluentAssertions;
4+
5+
/// <summary>
6+
/// Marks an assembly as containing extensions to Fluent Assertions that either uses the built-in assertions
7+
/// internally, or directly uses the <c>Execute.Assertion</c>.
8+
/// </summary>
9+
[AttributeUsage(AttributeTargets.Assembly)]
10+
public sealed class CustomAssertionsAssemblyAttribute : Attribute
11+
{
12+
}

Tests/Approval.Tests/ApprovedApi/FluentAssertions/net47.verified.txt

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -193,6 +193,11 @@ namespace FluentAssertions
193193
{
194194
public CustomAssertionAttribute() { }
195195
}
196+
[System.AttributeUsage(System.AttributeTargets.Assembly)]
197+
public sealed class CustomAssertionsAssemblyAttribute : System.Attribute
198+
{
199+
public CustomAssertionsAssemblyAttribute() { }
200+
}
196201
public static class EnumAssertionsExtensions
197202
{
198203
public static FluentAssertions.Primitives.EnumAssertions<TEnum> Should<TEnum>(this TEnum @enum)

Tests/Approval.Tests/ApprovedApi/FluentAssertions/net6.0.verified.txt

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -206,6 +206,11 @@ namespace FluentAssertions
206206
{
207207
public CustomAssertionAttribute() { }
208208
}
209+
[System.AttributeUsage(System.AttributeTargets.Assembly)]
210+
public sealed class CustomAssertionsAssemblyAttribute : System.Attribute
211+
{
212+
public CustomAssertionsAssemblyAttribute() { }
213+
}
209214
public static class EnumAssertionsExtensions
210215
{
211216
public static FluentAssertions.Primitives.EnumAssertions<TEnum> Should<TEnum>(this TEnum @enum)

Tests/Approval.Tests/ApprovedApi/FluentAssertions/netstandard2.0.verified.txt

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -192,6 +192,11 @@ namespace FluentAssertions
192192
{
193193
public CustomAssertionAttribute() { }
194194
}
195+
[System.AttributeUsage(System.AttributeTargets.Assembly)]
196+
public sealed class CustomAssertionsAssemblyAttribute : System.Attribute
197+
{
198+
public CustomAssertionsAssemblyAttribute() { }
199+
}
195200
public static class EnumAssertionsExtensions
196201
{
197202
public static FluentAssertions.Primitives.EnumAssertions<TEnum> Should<TEnum>(this TEnum @enum)

Tests/Approval.Tests/ApprovedApi/FluentAssertions/netstandard2.1.verified.txt

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -193,6 +193,11 @@ namespace FluentAssertions
193193
{
194194
public CustomAssertionAttribute() { }
195195
}
196+
[System.AttributeUsage(System.AttributeTargets.Assembly)]
197+
public sealed class CustomAssertionsAssemblyAttribute : System.Attribute
198+
{
199+
public CustomAssertionsAssemblyAttribute() { }
200+
}
196201
public static class EnumAssertionsExtensions
197202
{
198203
public static FluentAssertions.Primitives.EnumAssertions<TEnum> Should<TEnum>(this TEnum @enum)
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
using FluentAssertions;
2+
3+
[assembly: CustomAssertionsAssembly]
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
<Project Sdk="Microsoft.NET.Sdk">
2+
3+
<PropertyGroup>
4+
<TargetFramework>netstandard2.0</TargetFramework>
5+
<ImplicitUsings>enable</ImplicitUsings>
6+
<Nullable>disable</Nullable>
7+
<IsPackable>false</IsPackable>
8+
<SignAssembly>True</SignAssembly>
9+
<AssemblyOriginatorKeyFile>..\..\Src\FluentAssertions\FluentAssertions.snk</AssemblyOriginatorKeyFile>
10+
</PropertyGroup>
11+
12+
<ItemGroup>
13+
<ProjectReference Include="..\..\Src\FluentAssertions\FluentAssertions.csproj" />
14+
</ItemGroup>
15+
16+
</Project>
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
using FluentAssertions;
2+
using FluentAssertions.Primitives;
3+
4+
namespace ExampleExtensions;
5+
6+
public static class StringAssertionExtensions
7+
{
8+
public static void BePalindromic(this StringAssertions assertions)
9+
{
10+
char[] charArray = assertions.Subject.ToCharArray();
11+
Array.Reverse(charArray);
12+
string reversedSubject = new string(charArray);
13+
14+
assertions.Subject.Should().Be(reversedSubject);
15+
}
16+
}

0 commit comments

Comments
 (0)