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

Qodana fixes #2229

Merged
merged 13 commits into from
Jul 4, 2023
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ public ParsingState Parse(char symbol, StringBuilder statement)
}
else if (mode is Mode.RemoveSuperfluousWhitespace)
{
if (precedingSymbol is char value && !char.IsWhiteSpace(value))
if (precedingSymbol is { } value && !char.IsWhiteSpace(value))
jnyrup marked this conversation as resolved.
Show resolved Hide resolved
{
statement.Append(symbol);
}
Expand Down
7 changes: 1 addition & 6 deletions Src/FluentAssertions/Common/Configuration.cs
Original file line number Diff line number Diff line change
Expand Up @@ -40,18 +40,13 @@
{
lock (propertiesAccessLock)
{
if (!valueFormatterDetectionMode.HasValue)
{
valueFormatterDetectionMode = DetermineFormatterDetectionMode();
}

return valueFormatterDetectionMode.Value;
return valueFormatterDetectionMode ??= DetermineFormatterDetectionMode();
}
}

set
{
valueFormatterDetectionMode = value;

Check notice on line 49 in Src/FluentAssertions/Common/Configuration.cs

View workflow job for this annotation

GitHub Actions / Qodana Scan

Use preferred body style (convert into property, indexer, or event with preferred body style)

Inconsistent body style: use expression body

Check notice on line 49 in Src/FluentAssertions/Common/Configuration.cs

View workflow job for this annotation

GitHub Actions / Qodana Scan

Use preferred body style (convert into property, indexer, or event with preferred body style)

Inconsistent body style: use expression body

Check notice on line 49 in Src/FluentAssertions/Common/Configuration.cs

View workflow job for this annotation

GitHub Actions / Qodana Scan

Use preferred body style (convert into property, indexer, or event with preferred body style)

Inconsistent body style: use expression body

Check notice on line 49 in Src/FluentAssertions/Common/Configuration.cs

View workflow job for this annotation

GitHub Actions / Qodana Scan

Use preferred body style (convert into property, indexer, or event with preferred body style)

Inconsistent body style: use expression body

Check notice on line 49 in Src/FluentAssertions/Common/Configuration.cs

View workflow job for this annotation

GitHub Actions / Qodana Scan

Use preferred body style (convert into property, indexer, or event with preferred body style)

Inconsistent body style: use expression body

Check notice on line 49 in Src/FluentAssertions/Common/Configuration.cs

View workflow job for this annotation

GitHub Actions / Qodana Scan

Use preferred body style (convert into property, indexer, or event with preferred body style)

Inconsistent body style: use expression body
}
}

Expand Down
5 changes: 3 additions & 2 deletions Src/FluentAssertions/Common/Guard.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,13 @@
using System.Collections.Generic;
using System.Linq;
using System.Runtime.CompilerServices;
using JetBrains.Annotations;

namespace FluentAssertions.Common;

internal static class Guard
{
public static void ThrowIfArgumentIsNull<T>([ValidatedNotNull] T obj,
public static void ThrowIfArgumentIsNull<T>([ValidatedNotNull][NoEnumeration] T obj,
jnyrup marked this conversation as resolved.
Show resolved Hide resolved
[CallerArgumentExpression(nameof(obj))]
string paramName = "")
{
Expand All @@ -17,7 +18,7 @@ internal static class Guard
}
}

public static void ThrowIfArgumentIsNull<T>([ValidatedNotNull] T obj, string paramName, string message)
public static void ThrowIfArgumentIsNull<T>([ValidatedNotNull][NoEnumeration] T obj, string paramName, string message)
{
if (obj is null)
{
Expand Down
1 change: 0 additions & 1 deletion Src/FluentAssertions/Data/DataTableAssertions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@
using System.Data;
using System.Diagnostics;
using System.Linq;
using System.Xml.Schema;
using FluentAssertions.Common;
using FluentAssertions.Equivalency;
using FluentAssertions.Execution;
Expand Down
15 changes: 5 additions & 10 deletions Src/FluentAssertions/Equivalency/MemberFactory.cs
Original file line number Diff line number Diff line change
Expand Up @@ -8,17 +8,12 @@
{
public static IMember Create(MemberInfo memberInfo, INode parent)
{
if (memberInfo.MemberType == MemberTypes.Field)
return memberInfo.MemberType switch

Check notice on line 11 in Src/FluentAssertions/Equivalency/MemberFactory.cs

View workflow job for this annotation

GitHub Actions / Qodana Scan

Some values of the enum are not processed inside 'switch' expression and are handled via exception in default arm

Some values of the enum are not processed inside switch: All, Constructor, Custom...

Check notice on line 11 in Src/FluentAssertions/Equivalency/MemberFactory.cs

View workflow job for this annotation

GitHub Actions / Qodana Scan

Some values of the enum are not processed inside 'switch' expression and are handled via exception in default arm

Some values of the enum are not processed inside switch: All, Constructor, Custom...

Check notice on line 11 in Src/FluentAssertions/Equivalency/MemberFactory.cs

View workflow job for this annotation

GitHub Actions / Qodana Scan

Some values of the enum are not processed inside 'switch' expression and are handled via exception in default arm

Some values of the enum are not processed inside switch: Constructor, Event, Method...

Check notice on line 11 in Src/FluentAssertions/Equivalency/MemberFactory.cs

View workflow job for this annotation

GitHub Actions / Qodana Scan

Some values of the enum are not processed inside 'switch' expression and are handled via exception in default arm

Some values of the enum are not processed inside switch: Constructor, Event, Method...
{
return new Field((FieldInfo)memberInfo, parent);
}

if (memberInfo.MemberType == MemberTypes.Property)
{
return new Property((PropertyInfo)memberInfo, parent);
}

throw new NotSupportedException($"Don't know how to deal with a {memberInfo.MemberType}");
MemberTypes.Field => new Field((FieldInfo)memberInfo, parent),
MemberTypes.Property => new Property((PropertyInfo)memberInfo, parent),
_ => throw new NotSupportedException($"Don't know how to deal with a {memberInfo.MemberType}")
};
}

internal static IMember Find(object target, string memberName, INode parent)
Expand Down
1 change: 0 additions & 1 deletion Src/FluentAssertions/Equivalency/OrderingRuleCollection.cs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using FluentAssertions.Equivalency.Ordering;

namespace FluentAssertions.Equivalency;
Expand Down
39 changes: 19 additions & 20 deletions Src/FluentAssertions/Equivalency/Steps/DataColumnEquivalencyStep.cs
Original file line number Diff line number Diff line change
Expand Up @@ -106,26 +106,25 @@ private static IMember FindMatchFor(IMember selectedMemberInfo, object subject,
// NOTE: This list of candidate members is duplicated in the XML documentation for the
// DataColumn.BeEquivalentTo extension method in DataColumnAssertions.cs. If this ever
// needs to change, keep them in sync.
private static readonly HashSet<string> CandidateMembers =
new HashSet<string>
{
nameof(DataColumn.AllowDBNull),
nameof(DataColumn.AutoIncrement),
nameof(DataColumn.AutoIncrementSeed),
nameof(DataColumn.AutoIncrementStep),
nameof(DataColumn.Caption),
nameof(DataColumn.ColumnName),
nameof(DataColumn.DataType),
nameof(DataColumn.DateTimeMode),
nameof(DataColumn.DefaultValue),
nameof(DataColumn.Expression),
nameof(DataColumn.ExtendedProperties),
nameof(DataColumn.MaxLength),
nameof(DataColumn.Namespace),
nameof(DataColumn.Prefix),
nameof(DataColumn.ReadOnly),
nameof(DataColumn.Unique),
};
private static readonly HashSet<string> CandidateMembers = new()
{
nameof(DataColumn.AllowDBNull),
nameof(DataColumn.AutoIncrement),
nameof(DataColumn.AutoIncrementSeed),
nameof(DataColumn.AutoIncrementStep),
nameof(DataColumn.Caption),
nameof(DataColumn.ColumnName),
nameof(DataColumn.DataType),
nameof(DataColumn.DateTimeMode),
nameof(DataColumn.DefaultValue),
nameof(DataColumn.Expression),
nameof(DataColumn.ExtendedProperties),
nameof(DataColumn.MaxLength),
nameof(DataColumn.Namespace),
nameof(DataColumn.Prefix),
nameof(DataColumn.ReadOnly),
nameof(DataColumn.Unique),
};

private static IEnumerable<IMember> GetMembersFromExpectation(INode currentNode, Comparands comparands,
IEquivalencyAssertionOptions config)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,16 +19,12 @@ public class DataRowCollectionEquivalencyStep : EquivalencyStep<DataRowCollectio
}
else
{
RowMatchMode rowMatchMode = RowMatchMode.Index;

if (context.Options is DataEquivalencyAssertionOptions<DataSet> dataSetConfig)
{
rowMatchMode = dataSetConfig.RowMatchMode;
}
else if (context.Options is DataEquivalencyAssertionOptions<DataTable> dataTableConfig)
RowMatchMode rowMatchMode = context.Options switch
{
rowMatchMode = dataTableConfig.RowMatchMode;
}
DataEquivalencyAssertionOptions<DataSet> dataSetConfig => dataSetConfig.RowMatchMode,
DataEquivalencyAssertionOptions<DataTable> dataTableConfig => dataTableConfig.RowMatchMode,
_ => RowMatchMode.Index
};

var subject = (DataRowCollection)comparands.Subject;
var expectation = (DataRowCollection)comparands.Expectation;
Expand Down Expand Up @@ -209,15 +205,7 @@ public bool Equals(CompoundKey other)
return false;
}

for (int i = 0; i < values.Length; i++)
{
if (!values[i].Equals(other.values[i]))
{
return false;
}
}

return true;
return values.SequenceEqual(other.values);
}

public override bool Equals(object obj) => Equals(obj as CompoundKey);
Expand All @@ -226,9 +214,9 @@ public override int GetHashCode()
{
int hash = 0;

for (int i = 0; i < values.Length; i++)
foreach (var value in values)
{
hash = hash * 389 ^ values[i].GetHashCode();
hash = hash * 389 ^ value.GetHashCode();
}

return hash;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -96,7 +96,7 @@ private static void CompareScalarProperties(DataSet subject, DataSet expectation
if (selectedMembers.ContainsKey(nameof(expectation.Locale)))
{
AssertionScope.Current
.ForCondition(subject.Locale == expectation.Locale)
.ForCondition(Equals(subject.Locale, expectation.Locale))
.FailWith("Expected {context:DataSet} to have Locale value of {0}{reason}, but found {1} instead",
expectation.Locale, subject.Locale);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,7 @@ public class DataTableEquivalencyStep : EquivalencyStep<DataTable>
if (selectedMembers.ContainsKey(nameof(expectation.Locale)))
{
AssertionScope.Current
.ForCondition(subject.Locale == expectation.Locale)
.ForCondition(Equals(subject.Locale, expectation.Locale))
.FailWith("Expected {context:DataTable} to have Locale value of {0}{reason}, but found {1} instead",
expectation.Locale, subject.Locale);
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using FluentAssertions.Execution;

Expand All @@ -11,7 +9,7 @@
{
#pragma warning disable SA1110 // Allow opening parenthesis on new line to reduce line length
private static readonly MethodInfo AssertDictionaryEquivalenceMethod =
new Action<EquivalencyValidationContext, IEquivalencyValidator, IEquivalencyAssertionOptions,

Check warning on line 12 in Src/FluentAssertions/Equivalency/Steps/GenericDictionaryEquivalencyStep.cs

View workflow job for this annotation

GitHub Actions / Qodana Scan

Possible 'System.NullReferenceException'

Possible 'System.NullReferenceException'
IDictionary<object, object>, IDictionary<object, object>>
(AssertDictionaryEquivalence).GetMethodInfo().GetGenericMethodDefinition();
#pragma warning restore SA1110
Expand Down
1 change: 0 additions & 1 deletion Src/FluentAssertions/Execution/LateBoundTestFramework.cs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
using System;
using System.Diagnostics.CodeAnalysis;
using System.Linq;
using System.Reflection;

namespace FluentAssertions.Execution;
Expand Down
1 change: 0 additions & 1 deletion Src/FluentAssertions/Execution/NSpecFramework.cs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
using System;
using System.Diagnostics.CodeAnalysis;
using System.Linq;
using System.Reflection;

namespace FluentAssertions.Execution;
Expand Down
1 change: 0 additions & 1 deletion Src/FluentAssertions/Formatting/DefaultValueFormatter.cs
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
using System;
using System.Linq;
using System.Reflection;
using System.Runtime.CompilerServices;
using FluentAssertions.Common;
using FluentAssertions.Equivalency;

Expand Down
20 changes: 10 additions & 10 deletions Src/FluentAssertions/Numeric/NumericAssertions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ public AndConstraint<TAssertions> Be(T expected, string because = "", params obj
public AndConstraint<TAssertions> Be(T? expected, string because = "", params object[] becauseArgs)
{
Execute.Assertion
.ForCondition(expected is T value ? Subject?.CompareTo(value) == 0 : !Subject.HasValue)
.ForCondition(expected is { } value ? Subject?.CompareTo(value) == 0 : !Subject.HasValue)
.BecauseOf(because, becauseArgs)
.FailWith("Expected {context:value} to be {0}{reason}, but found {1}" + GenerateDifferenceMessage(expected), expected,
Subject);
Expand Down Expand Up @@ -123,7 +123,7 @@ public AndConstraint<TAssertions> NotBe(T unexpected, string because = "", param
public AndConstraint<TAssertions> NotBe(T? unexpected, string because = "", params object[] becauseArgs)
{
Execute.Assertion
.ForCondition(unexpected is T value ? Subject?.CompareTo(value) != 0 : Subject.HasValue)
.ForCondition(unexpected is { } value ? Subject?.CompareTo(value) != 0 : Subject.HasValue)
.BecauseOf(because, becauseArgs)
.FailWith("Did not expect {context:value} to be {0}{reason}.", unexpected);

Expand Down Expand Up @@ -163,7 +163,7 @@ public AndConstraint<TAssertions> BePositive(string because = "", params object[
public AndConstraint<TAssertions> BeNegative(string because = "", params object[] becauseArgs)
{
Execute.Assertion
.ForCondition(Subject is T value && !IsNaN(value) && value.CompareTo(default) < 0)
.ForCondition(Subject is { } value && !IsNaN(value) && value.CompareTo(default) < 0)
.BecauseOf(because, becauseArgs)
.FailWith("Expected {context:value} to be negative{reason}, but found {0}.", Subject);

Expand All @@ -189,7 +189,7 @@ public AndConstraint<TAssertions> BeLessThan(T expected, string because = "", pa
}

Execute.Assertion
.ForCondition(Subject is T value && !IsNaN(value) && value.CompareTo(expected) < 0)
.ForCondition(Subject is { } value && !IsNaN(value) && value.CompareTo(expected) < 0)
.BecauseOf(because, becauseArgs)
.FailWith("Expected {context:value} to be less than {0}{reason}, but found {1}" + GenerateDifferenceMessage(expected),
expected, Subject);
Expand Down Expand Up @@ -217,7 +217,7 @@ public AndConstraint<TAssertions> BeLessThan(T expected, string because = "", pa
}

Execute.Assertion
.ForCondition(Subject is T value && !IsNaN(value) && value.CompareTo(expected) <= 0)
.ForCondition(Subject is { } value && !IsNaN(value) && value.CompareTo(expected) <= 0)
.BecauseOf(because, becauseArgs)
.FailWith(
"Expected {context:value} to be less than or equal to {0}{reason}, but found {1}" +
Expand Down Expand Up @@ -320,7 +320,7 @@ public AndConstraint<TAssertions> BeLessThan(T expected, string because = "", pa
}

Execute.Assertion
.ForCondition(Subject is T value && value.CompareTo(minimumValue) >= 0 && value.CompareTo(maximumValue) <= 0)
.ForCondition(Subject is { } value && value.CompareTo(minimumValue) >= 0 && value.CompareTo(maximumValue) <= 0)
.BecauseOf(because, becauseArgs)
.FailWith("Expected {context:value} to be between {0} and {1}{reason}, but found {2}.",
minimumValue, maximumValue, Subject);
Expand Down Expand Up @@ -356,7 +356,7 @@ public AndConstraint<TAssertions> BeLessThan(T expected, string because = "", pa
}

Execute.Assertion
.ForCondition(Subject is T value && !(value.CompareTo(minimumValue) >= 0 && value.CompareTo(maximumValue) <= 0))
.ForCondition(Subject is { } value && !(value.CompareTo(minimumValue) >= 0 && value.CompareTo(maximumValue) <= 0))
.BecauseOf(because, becauseArgs)
.FailWith("Expected {context:value} to not be between {0} and {1}{reason}, but found {2}.",
minimumValue, maximumValue, Subject);
Expand Down Expand Up @@ -392,7 +392,7 @@ public AndConstraint<TAssertions> BeOneOf(params T[] validValues)
params object[] becauseArgs)
{
Execute.Assertion
.ForCondition(Subject is T value && validValues.Contains(value))
.ForCondition(Subject is { } value && validValues.Contains(value))
.BecauseOf(because, becauseArgs)
.FailWith("Expected {context:value} to be one of {0}{reason}, but found {1}.", validValues, Subject);

Expand Down Expand Up @@ -421,7 +421,7 @@ public AndConstraint<TAssertions> BeOfType(Type expectedType, string because = "

if (expectedType.IsGenericTypeDefinition && subjectType?.IsGenericType == true)
{
(subjectType?.GetGenericTypeDefinition()).Should().Be(expectedType, because, becauseArgs);
subjectType.GetGenericTypeDefinition().Should().Be(expectedType, because, becauseArgs);
}
else
{
Expand Down Expand Up @@ -508,7 +508,7 @@ private string GenerateDifferenceMessage(T? expected)
{
const string noDifferenceMessage = ".";

if (Subject is not T subject || expected is not T expectedValue)
if (Subject is not { } subject || expected is not T expectedValue)
{
return noDifferenceMessage;
}
Expand Down
12 changes: 6 additions & 6 deletions Src/FluentAssertions/Primitives/EnumAssertions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -195,7 +195,7 @@ public AndConstraint<TAssertions> NotBeDefined(string because = "", params objec
public AndConstraint<TAssertions> HaveValue(decimal expected, string because = "", params object[] becauseArgs)
{
Execute.Assertion
.ForCondition(Subject is TEnum value && GetValue(value) == expected)
.ForCondition(Subject is { } value && GetValue(value) == expected)
.BecauseOf(because, becauseArgs)
.FailWith("Expected {context:the enum} to have value {0}{reason}, but found {1}.",
expected, Subject);
Expand All @@ -217,7 +217,7 @@ public AndConstraint<TAssertions> HaveValue(decimal expected, string because = "
public AndConstraint<TAssertions> NotHaveValue(decimal unexpected, string because = "", params object[] becauseArgs)
{
Execute.Assertion
.ForCondition(!(Subject is TEnum value && GetValue(value) == unexpected))
.ForCondition(!(Subject is { } value && GetValue(value) == unexpected))
.BecauseOf(because, becauseArgs)
.FailWith("Expected {context:the enum} to not have value {0}{reason}, but found {1}.",
unexpected, Subject);
Expand All @@ -240,7 +240,7 @@ public AndConstraint<TAssertions> HaveSameValueAs<T>(T expected, string because
where T : struct, Enum
{
Execute.Assertion
.ForCondition(Subject is TEnum value && GetValue(value) == GetValue(expected))
.ForCondition(Subject is { } value && GetValue(value) == GetValue(expected))
.BecauseOf(because, becauseArgs)
.FailWith("Expected {context:the enum} to have same value as {0}{reason}, but found {1}.",
expected, Subject);
Expand All @@ -263,7 +263,7 @@ public AndConstraint<TAssertions> NotHaveSameValueAs<T>(T unexpected, string bec
where T : struct, Enum
{
Execute.Assertion
.ForCondition(!(Subject is TEnum value && GetValue(value) == GetValue(unexpected)))
.ForCondition(!(Subject is { } value && GetValue(value) == GetValue(unexpected)))
.BecauseOf(because, becauseArgs)
.FailWith("Expected {context:the enum} to not have same value as {0}{reason}, but found {1}.",
unexpected, Subject);
Expand All @@ -286,7 +286,7 @@ public AndConstraint<TAssertions> HaveSameNameAs<T>(T expected, string because =
where T : struct, Enum
{
Execute.Assertion
.ForCondition(Subject is TEnum value && GetName(value) == GetName(expected))
.ForCondition(Subject is { } value && GetName(value) == GetName(expected))
.BecauseOf(because, becauseArgs)
.FailWith("Expected {context:the enum} to have same name as {0}{reason}, but found {1}.",
expected, Subject);
Expand All @@ -309,7 +309,7 @@ public AndConstraint<TAssertions> NotHaveSameNameAs<T>(T unexpected, string beca
where T : struct, Enum
{
Execute.Assertion
.ForCondition(!(Subject is TEnum value && GetName(value) == GetName(unexpected)))
.ForCondition(!(Subject is { } value && GetName(value) == GetName(unexpected)))
.BecauseOf(because, becauseArgs)
.FailWith("Expected {context:the enum} to not have same name as {0}{reason}, but found {1}.",
unexpected, Subject);
Expand Down
2 changes: 1 addition & 1 deletion Src/FluentAssertions/Primitives/GuidAssertions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ public AndConstraint<TAssertions> BeEmpty(string because = "", params object[] b
public AndConstraint<TAssertions> NotBeEmpty(string because = "", params object[] becauseArgs)
{
Execute.Assertion
.ForCondition(Subject is Guid value && value != Guid.Empty)
.ForCondition(Subject is { } value && value != Guid.Empty)
.BecauseOf(because, becauseArgs)
.FailWith("Did not expect {context:Guid} to be empty{reason}.");

Expand Down
2 changes: 1 addition & 1 deletion Src/FluentAssertions/Types/MethodInfoSelector.cs
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ namespace FluentAssertions.Types;
/// </summary>
public class MethodInfoSelector : IEnumerable<MethodInfo>
{
private IEnumerable<MethodInfo> selectedMethods = new List<MethodInfo>();
private IEnumerable<MethodInfo> selectedMethods;

/// <summary>
/// Initializes a new instance of the <see cref="MethodInfoSelector"/> class.
Expand Down