Skip to content

Commit 09e73c9

Browse files
committed
fix: issue #339
1 parent 1a4a3fe commit 09e73c9

File tree

12 files changed

+253
-109
lines changed

12 files changed

+253
-109
lines changed

appveyor.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
version: 3.0.0.{build}
1+
version: 3.0.1.{build}
22
image: Visual Studio 2022
33
# Uncomment following lines to log environment variables
44
#init:

code/.build/Version.cs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,9 @@
2424
// You can specify all the values or you can default the Build and Revision Numbers
2525
// by using the '*' as shown below:
2626
// [assembly: AssemblyVersion("1.0.*")]
27-
[assembly: AssemblyFileVersion("3.0.0.0")]
28-
[assembly: AssemblyVersion("3.0.0.0")]
29-
[assembly: AssemblyInformationalVersion("3.0.0.0-alpha")]
27+
[assembly: AssemblyFileVersion("3.0.1.0")]
28+
[assembly: AssemblyVersion("3.0.1.0")]
29+
[assembly: AssemblyInformationalVersion("3.0.1.0")]
3030

3131
// General Information about an assembly is controlled through the following
3232
// set of attributes. Change these attribute values to modify the information
@@ -35,7 +35,7 @@
3535
[assembly: AssemblyConfiguration("")]
3636
[assembly: AssemblyCompany("Thomas PIERRAIN ([email protected]), Cyrille DUPUYDAUBY (@_dupdob_), Rui CARVALHO, Marc-Antoine LATOUR and Co")]
3737
[assembly: AssemblyProduct("NFluent")]
38-
[assembly: AssemblyCopyright("Copyright © 2013-2020. Licensed under the Apache License, Version 2.0 (http://www.apache.org/licenses/LICENSE-2.0).")]
38+
[assembly: AssemblyCopyright("Copyright © 2013-2023. Licensed under the Apache License, Version 2.0 (http://www.apache.org/licenses/LICENSE-2.0).")]
3939
[assembly: AssemblyTrademark("")]
4040
[assembly: AssemblyCulture("")]
4141

code/Changelog.md

Lines changed: 98 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,101 @@
1+
# V 3.0.0
2+
## Major changes
3+
* You can execute multiple check as a single batch and get every failures, instead of the first one. This can be achieved using:
4+
* `Check.StartBatch`: stores the result of each subsequent check(s) and notifies all the errors when the returned object is disposed. Such as
5+
`using(Check.StartBatch())
6+
{
7+
Check.That(sut).....
8+
Check.That(sut)....
9+
}`
10+
Note that any actual exception thrown during the check phase will prevent any subsequent check from behind executed (1) and may not be reported as it may be replaced by an assertion failure exception.
11+
This comes from C# exeption handling logic.
12+
* You can provide anonymous types and tuples when using IsEqualTo against any type. The check will be made against all
13+
_sut_'s propertie.
14+
* NFluent supports Net 3.5 SP1, Net. 4.5.2 +, Net Standard 2.0+. Dropped support for Net Framework 2.0, 3.0, and 4.0, as well Net Standard<2.0.
15+
If you can't upgrade your framework version to a supported one, please use NFluent 2.7.1.
16+
17+
18+
## New Checks
19+
* `Is`: Checks if _sut == expected_. This is a strongly typed equivalent to `IsEqualTo`.
20+
* `IsGreaterOrEqualThan`: Checks if _sut_ >= _expected_.
21+
* `IsLessOrEqualThan`: Checks if _sut_ <= _expected_.
22+
23+
## New feautres
24+
* You can provide custom comparer for any type, using `Check.RegisterComparer` like this `Check.Register<MyType>(MyCustomComparer)`.
25+
You can also use `RegisterLocalComparer` to limit its usage to a declaration scope.
26+
27+
## Breaking changes
28+
* Equality logic changed for `IDictionary`: dictionaries are considered equals if they have the same keys and
29+
the same values for each key. In NFluent V2, entries needed to be declared in the some order or else they were considered as **different** but **equivalent**.
30+
* You need to specify
31+
* `IsAnInstanceOf<nullableType>(null)` now fails (with an appropriate message). Previously, it did succeed. But,
32+
as captured in issue #68, this behavior was triggered by a bug and kept due to a poor error message when fixed.
33+
* The `IStructCheck<T>` interface has been removed as well as associated extensibility helper. Those were dedicated
34+
to value `types`, you can migrate your existing extensions to the `ICheck<T>` type instead. Please open an issue if
35+
you need help.
36+
37+
## Fixes
38+
* HasFieldWithSameValues resulted in false positive when string fields had the same value.
39+
* IsNotEqualTo now properly preserves expected type
40+
* Improved rerporting of differences for enumerations and dictionaries to make them more consistent and fixed some inaccuracies.
41+
42+
## GitHub Issues
43+
* #325, #327, #330, #332
44+
45+
### Obsolete
46+
#### Marked as obsolet
47+
* `ThatAsyncCode`: you can now use `ThatCode` even for async methods.
48+
49+
Here is the list of methods, classes and other obsolete stuff that have been removed in this version as well
50+
as workaround advices.
51+
* Drop support for Net 2.0 and 3.0: keep using NFluent V2.x versions if you support for these.
52+
* `Check.ThatEnum`has been removed. You must use `Check.That` instead.
53+
* `ILambdaCheck`: the definition was kept to prevent breaking build, but it was no longer used. If this is a
54+
problem for you, open an issue
55+
* `IsPositive` (available for numbers): please use `IsStrictlyPositive` instead.
56+
* `IsNegative` (available for numbers): please use `IsStrictlyNegative` instead.
57+
* `IsLessThan` (available for numbers): please use `IsStrictlyNegative` instead.
58+
* `IsGreaterThan` (available for numbers): please use `IsStrictlyGreaterThan` instead.
59+
* `IsSameReferenceThan`: please use `IsSameReferenceAs` instead.
60+
* `HasFieldsEqualToThose`: please use `HasFieldsWithSameValues` instead.
61+
* `HasFieldsNotEqualToThose`: please use `HasNotFieldsWithSameValues` instead.
62+
* `IsAFaillingCheckWithMessage`: please use `IsAFailingCheckWithMessage` instead.
63+
* `IsAFaillingCheck`: please use `IsAFailingCheck` instead.
64+
* `Properties` (available for enumeration): please use `Extracting` instead.
65+
* `Checker.BuildLinkWhich` (used for custom extension): please use `ExtensibilityHelper.BuildCheckLinkWhich` instead.
66+
* `Checker.ExecuteCheckAndProvideSubItem` (used for custom extension): please 'ExtensibilityHelper' static class methods instead.
67+
68+
# V 2.8.0
69+
## Breaking changes
70+
* Removed typed overload for IsEqualTo. This may degrade autocompletion somewhat;
71+
* Equality comparison logic has been slightly revised to take failing `Equals` result when the expected type provides a specific implementation (only success was used so far).
72+
73+
## New check
74+
* Is : replaces the typed overload for IsEqualTo
75+
76+
## GitHub Issue
77+
* #335
78+
79+
80+
# V 2.7.2
81+
## Fixes
82+
* HasFieldWithSameValues resulted in false positive when string fields had the same value.
83+
* IsZero failed for very small double (<1E-28) in previous versions.
84+
* IsEquivalentTo was not permissive enougth for dictionaries.
85+
86+
## GitHub Issues
87+
* #331, #333#
88+
89+
# V 2.7.1
90+
# Fixes
91+
* HasFieldsWithSameValues failed to properly compare when the expected value contained duplicate string.
92+
More generally, instances where only checked once for equality; any subsequent check was assumed to be succesful.
93+
This could lead to false positive (i.e. checks succeeded when it should have failed).
94+
This regression was introduced by V 2.2.0 in 02/2018. Sorry about that.
95+
96+
# GitHub Issues
97+
* #331
98+
199
## V 2.7.1
2100
### Fixes
3101
* HasFieldsWithSameValues failed to properly compare when the expected value contained duplicate string.

code/NFluent.sln

Lines changed: 30 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,6 @@ EndProject
6868
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "docs", "docs", "{DEE62612-3A5D-4D3F-9DDD-84B869E9184F}"
6969
ProjectSection(SolutionItems) = preProject
7070
..\docs\ArchitectureDecisionRecord.md = ..\docs\ArchitectureDecisionRecord.md
71-
..\docs\Backlog.md = ..\docs\Backlog.md
7271
Changelog.md = Changelog.md
7372
..\docs\DevDoD.md = ..\docs\DevDoD.md
7473
..\docs\ForNCrunchUsers.md = ..\docs\ForNCrunchUsers.md
@@ -133,36 +132,6 @@ EndProject
133132
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "NFluent.Analyzer.Test", "src\Analyzer\NFluent.Analyzer\NFluent.Analyzer.Test\NFluent.Analyzer.Test.csproj", "{4D1E60F2-64ED-452F-9A4F-5A3C8EEFD05A}"
134133
EndProject
135134
Global
136-
GlobalSection(SharedMSBuildProjectFiles) = preSolution
137-
tests\NFluent.Tests.Generated\NFluent.Tests.Generated.projitems*{0014c223-a481-4b87-a480-3d4792a9b276}*SharedItemsImports = 4
138-
tests\NFluent.Tests\NFluent.Tests.projitems*{0014c223-a481-4b87-a480-3d4792a9b276}*SharedItemsImports = 4
139-
tests\NFluent.Tests.ReportedIssues\NFluent.Tests.ReportedIssues.projitems*{0147471a-18d2-4714-8cda-37da471e0e45}*SharedItemsImports = 13
140-
tests\NFluent.Tests\NFluent.Tests.projitems*{0425a660-ca7d-43f6-93ab-f72c95d506e3}*SharedItemsImports = 13
141-
tests\NFluent.Tests.Extensions\NFluent.Tests.Extensions.projitems*{2b7f0e07-9b42-4bd2-8e30-f90fd78faf1f}*SharedItemsImports = 13
142-
tests\NFluent.Tests.Extensions\NFluent.Tests.Extensions.projitems*{308a72a3-462b-4c4e-abae-9d9d49d251e7}*SharedItemsImports = 4
143-
src\NFluent.Generated\NFluent.Generated.projitems*{37fdae31-560d-40b8-8fa7-7def8a53b370}*SharedItemsImports = 13
144-
src\NFluent.Generated\NFluent.Generated.projitems*{3a474510-f384-41ce-9270-539b1e51da7e}*SharedItemsImports = 4
145-
src\NFluent\NFluent.projitems*{3a474510-f384-41ce-9270-539b1e51da7e}*SharedItemsImports = 4
146-
tests\NFluent.Tests.Meta\NFluent.Tests.Meta.projitems*{61d00587-a426-41de-970b-8cdf5c7a0e67}*SharedItemsImports = 13
147-
tests\NFluent.Tests.Extensions\NFluent.Tests.Extensions.projitems*{6954e791-41c2-4d1f-b6e6-ba77c2784311}*SharedItemsImports = 5
148-
tests\NFluent.Tests.Generated\NFluent.Tests.Generated.projitems*{6b88c45a-d45e-40fb-8635-d0e0ef0454e9}*SharedItemsImports = 4
149-
tests\NFluent.Tests\NFluent.Tests.projitems*{6b88c45a-d45e-40fb-8635-d0e0ef0454e9}*SharedItemsImports = 4
150-
tests\NFluent.Tests.Internals\NFluent.Tests.Internals.projitems*{8f0252a6-1bb6-4bf6-a852-33eafb6852ca}*SharedItemsImports = 5
151-
tests\NFluent.Tests.Internals\NFluent.Tests.Internals.projitems*{95799318-9a09-46c8-ae53-2546f053ef40}*SharedItemsImports = 4
152-
tests\NFluent.Tests.Internals\NFluent.Tests.Internals.projitems*{9e500148-4f6c-424a-aa09-801db1749677}*SharedItemsImports = 4
153-
tests\NFluent.Tests.Internals\NFluent.Tests.Internals.projitems*{ab38506b-6cd4-47ed-a085-a77e8a5be26c}*SharedItemsImports = 13
154-
tests\NFluent.Tests.Extensions\NFluent.Tests.Extensions.projitems*{ac520fdb-8125-46f3-85f3-d4962c53c136}*SharedItemsImports = 4
155-
tests\NFluent.Tests.Meta\NFluent.Tests.Meta.projitems*{c2eec8dd-f390-4ecb-a169-25930896e1c1}*SharedItemsImports = 4
156-
src\NFluent.Generated\NFluent.Generated.projitems*{c90111a0-3ab2-40ed-b665-c0ddb8deb26e}*SharedItemsImports = 5
157-
src\NFluent\NFluent.projitems*{c90111a0-3ab2-40ed-b665-c0ddb8deb26e}*SharedItemsImports = 5
158-
src\NFluent.Generated\NFluent.Generated.projitems*{cf1d857f-658f-4e1f-8487-cd751f189e6a}*SharedItemsImports = 4
159-
src\NFluent\NFluent.projitems*{cf1d857f-658f-4e1f-8487-cd751f189e6a}*SharedItemsImports = 4
160-
src\NFluent\NFluent.projitems*{dbfa1137-b129-496a-9201-149f5178747e}*SharedItemsImports = 13
161-
tests\NFluent.Tests.Generated\NFluent.Tests.Generated.projitems*{e298f1af-a6a7-497c-9a2d-ac15584e1ac1}*SharedItemsImports = 13
162-
tests\NFluent.Tests.ReportedIssues\NFluent.Tests.ReportedIssues.projitems*{f4872eaa-bf75-47ec-a8ef-7791a0e89b50}*SharedItemsImports = 5
163-
tests\NFluent.Tests.Generated\NFluent.Tests.Generated.projitems*{fe288842-65f6-47dc-952a-413077247511}*SharedItemsImports = 5
164-
tests\NFluent.Tests\NFluent.Tests.projitems*{fe288842-65f6-47dc-952a-413077247511}*SharedItemsImports = 5
165-
EndGlobalSection
166135
GlobalSection(SolutionConfigurationPlatforms) = preSolution
167136
Debug|Any CPU = Debug|Any CPU
168137
Release|Any CPU = Release|Any CPU
@@ -320,4 +289,34 @@ Global
320289
GlobalSection(ExtensibilityGlobals) = postSolution
321290
SolutionGuid = {A9A6ED20-537A-4D69-82C7-53AF50CEAEE8}
322291
EndGlobalSection
292+
GlobalSection(SharedMSBuildProjectFiles) = preSolution
293+
tests\NFluent.Tests.Generated\NFluent.Tests.Generated.projitems*{0014c223-a481-4b87-a480-3d4792a9b276}*SharedItemsImports = 4
294+
tests\NFluent.Tests\NFluent.Tests.projitems*{0014c223-a481-4b87-a480-3d4792a9b276}*SharedItemsImports = 4
295+
tests\NFluent.Tests.ReportedIssues\NFluent.Tests.ReportedIssues.projitems*{0147471a-18d2-4714-8cda-37da471e0e45}*SharedItemsImports = 13
296+
tests\NFluent.Tests\NFluent.Tests.projitems*{0425a660-ca7d-43f6-93ab-f72c95d506e3}*SharedItemsImports = 13
297+
tests\NFluent.Tests.Extensions\NFluent.Tests.Extensions.projitems*{2b7f0e07-9b42-4bd2-8e30-f90fd78faf1f}*SharedItemsImports = 13
298+
tests\NFluent.Tests.Extensions\NFluent.Tests.Extensions.projitems*{308a72a3-462b-4c4e-abae-9d9d49d251e7}*SharedItemsImports = 4
299+
src\NFluent.Generated\NFluent.Generated.projitems*{37fdae31-560d-40b8-8fa7-7def8a53b370}*SharedItemsImports = 13
300+
src\NFluent.Generated\NFluent.Generated.projitems*{3a474510-f384-41ce-9270-539b1e51da7e}*SharedItemsImports = 4
301+
src\NFluent\NFluent.projitems*{3a474510-f384-41ce-9270-539b1e51da7e}*SharedItemsImports = 4
302+
tests\NFluent.Tests.Meta\NFluent.Tests.Meta.projitems*{61d00587-a426-41de-970b-8cdf5c7a0e67}*SharedItemsImports = 13
303+
tests\NFluent.Tests.Extensions\NFluent.Tests.Extensions.projitems*{6954e791-41c2-4d1f-b6e6-ba77c2784311}*SharedItemsImports = 5
304+
tests\NFluent.Tests.Generated\NFluent.Tests.Generated.projitems*{6b88c45a-d45e-40fb-8635-d0e0ef0454e9}*SharedItemsImports = 4
305+
tests\NFluent.Tests\NFluent.Tests.projitems*{6b88c45a-d45e-40fb-8635-d0e0ef0454e9}*SharedItemsImports = 4
306+
tests\NFluent.Tests.Internals\NFluent.Tests.Internals.projitems*{8f0252a6-1bb6-4bf6-a852-33eafb6852ca}*SharedItemsImports = 5
307+
tests\NFluent.Tests.Internals\NFluent.Tests.Internals.projitems*{95799318-9a09-46c8-ae53-2546f053ef40}*SharedItemsImports = 4
308+
tests\NFluent.Tests.Internals\NFluent.Tests.Internals.projitems*{9e500148-4f6c-424a-aa09-801db1749677}*SharedItemsImports = 4
309+
tests\NFluent.Tests.Internals\NFluent.Tests.Internals.projitems*{ab38506b-6cd4-47ed-a085-a77e8a5be26c}*SharedItemsImports = 13
310+
tests\NFluent.Tests.Extensions\NFluent.Tests.Extensions.projitems*{ac520fdb-8125-46f3-85f3-d4962c53c136}*SharedItemsImports = 4
311+
tests\NFluent.Tests.Meta\NFluent.Tests.Meta.projitems*{c2eec8dd-f390-4ecb-a169-25930896e1c1}*SharedItemsImports = 4
312+
src\NFluent.Generated\NFluent.Generated.projitems*{c90111a0-3ab2-40ed-b665-c0ddb8deb26e}*SharedItemsImports = 5
313+
src\NFluent\NFluent.projitems*{c90111a0-3ab2-40ed-b665-c0ddb8deb26e}*SharedItemsImports = 5
314+
src\NFluent.Generated\NFluent.Generated.projitems*{cf1d857f-658f-4e1f-8487-cd751f189e6a}*SharedItemsImports = 4
315+
src\NFluent\NFluent.projitems*{cf1d857f-658f-4e1f-8487-cd751f189e6a}*SharedItemsImports = 4
316+
src\NFluent\NFluent.projitems*{dbfa1137-b129-496a-9201-149f5178747e}*SharedItemsImports = 13
317+
tests\NFluent.Tests.Generated\NFluent.Tests.Generated.projitems*{e298f1af-a6a7-497c-9a2d-ac15584e1ac1}*SharedItemsImports = 13
318+
tests\NFluent.Tests.ReportedIssues\NFluent.Tests.ReportedIssues.projitems*{f4872eaa-bf75-47ec-a8ef-7791a0e89b50}*SharedItemsImports = 5
319+
tests\NFluent.Tests.Generated\NFluent.Tests.Generated.projitems*{fe288842-65f6-47dc-952a-413077247511}*SharedItemsImports = 5
320+
tests\NFluent.Tests\NFluent.Tests.projitems*{fe288842-65f6-47dc-952a-413077247511}*SharedItemsImports = 5
321+
EndGlobalSection
323322
EndGlobal

code/ReleaseNoteContentToBeInsertedWithinNuspecFile.md

Lines changed: 6 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,9 @@
1+
#V 3.0.0.1
2+
## Fix
3+
* Fix `Check.ThatCode` not awaiting `Task` returning lambdas in V3.0.0. Note that `Task<T>` returning lambdas do work in V3.0.0
4+
* an InvalidOperation is thrown when using `Check.ThatCode` on an async void method/lambda (as those cannot be awaited)
5+
6+
17
# V 3.0.0
28
## Major changes
39
* You can execute multiple check as a single batch and get every failures, instead of the first one. This can be achieved using:
@@ -65,33 +71,3 @@ problem for you, open an issue
6571
* `Checker.BuildLinkWhich` (used for custom extension): please use `ExtensibilityHelper.BuildCheckLinkWhich` instead.
6672
* `Checker.ExecuteCheckAndProvideSubItem` (used for custom extension): please 'ExtensibilityHelper' static class methods instead.
6773

68-
# V 2.8.0
69-
## Breaking changes
70-
* Removed typed overload for IsEqualTo. This may degrade autocompletion somewhat;
71-
* Equality comparison logic has been slightly revised to take failing `Equals` result when the expected type provides a specific implementation (only success was used so far).
72-
73-
## New check
74-
* Is : replaces the typed overload for IsEqualTo
75-
76-
## GitHub Issue
77-
* #335
78-
79-
80-
# V 2.7.2
81-
## Fixes
82-
* HasFieldWithSameValues resulted in false positive when string fields had the same value.
83-
* IsZero failed for very small double (<1E-28) in previous versions.
84-
* IsEquivalentTo was not permissive enougth for dictionaries.
85-
86-
## GitHub Issues
87-
* #331, #333#
88-
89-
# V 2.7.1
90-
# Fixes
91-
* HasFieldsWithSameValues failed to properly compare when the expected value contained duplicate string.
92-
More generally, instances where only checked once for equality; any subsequent check was assumed to be succesful.
93-
This could lead to false positive (i.e. checks succeeded when it should have failed).
94-
This regression was introduced by V 2.2.0 in 02/2018. Sorry about that.
95-
96-
# GitHub Issues
97-
* #331

code/src/NFluent/Extensions/ObjectExtensions.cs

Lines changed: 17 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -16,11 +16,12 @@
1616
namespace NFluent.Extensions
1717
{
1818
using System;
19-
19+
#if !DOTNET_35
20+
using System.Threading.Tasks;
21+
#endif
2022
internal static class ObjectExtensions
2123
{
22-
23-
#if !NETSTANDARD1_3 && !DOTNET_45
24+
#if !DOTNET_45
2425
/// <summary>
2526
/// Stub implementation for GetTypeInfo() for Net Framework.
2627
/// </summary>
@@ -59,5 +60,18 @@ public static bool IsAnEnumeration<T>(this T instance, bool evenWellKnown)
5960
{
6061
return instance!= null && instance.GetTypeWithoutThrowingException().IsAnEnumeration(evenWellKnown);
6162
}
63+
64+
public static bool IsAwaitable<T>(this T instance, out Action waiter)
65+
{
66+
#if !DOTNET_35
67+
if (instance is Task ta && ta.Status != TaskStatus.Created)
68+
{
69+
waiter = () => ta.Wait();
70+
return true;
71+
}
72+
#endif
73+
waiter = () =>{};
74+
return false;
75+
}
6276
}
6377
}

0 commit comments

Comments
 (0)