Skip to content

Commit 684be5c

Browse files
committed
CSHARP-5572: Refactor to use a single IsSetEqualsMethod implementation
1 parent 75f8411 commit 684be5c

File tree

4 files changed

+62
-47
lines changed

4 files changed

+62
-47
lines changed

src/MongoDB.Driver/Linq/Linq3Implementation/Misc/TypeExtensions.cs

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -190,6 +190,18 @@ public static bool ImplementsIQueryableOf(this Type type, Type itemType)
190190
actualItemType == itemType;
191191
}
192192

193+
public static bool ImplementsISet(this Type type, out Type itemType)
194+
{
195+
if (TryGetISetGenericInterface(type, out var isetType))
196+
{
197+
itemType = isetType.GetGenericArguments()[0];
198+
return true;
199+
}
200+
201+
itemType = null;
202+
return false;
203+
}
204+
193205
public static bool Is(this Type type, Type comparand)
194206
{
195207
if (type == comparand)
@@ -436,6 +448,9 @@ public static bool TryGetIOrderedQueryableGenericInterface(this Type type, out T
436448
public static bool TryGetIQueryableGenericInterface(this Type type, out Type iqueryableGenericInterface)
437449
=> TryGetGenericInterface(type, typeof(IQueryable<>), out iqueryableGenericInterface);
438450

451+
public static bool TryGetISetGenericInterface(this Type type, out Type isetGenericInterface)
452+
=> TryGetGenericInterface(type, typeof(ISet<>), out isetGenericInterface);
453+
439454
private static TValue GetDefaultValueGeneric<TValue>()
440455
{
441456
return default(TValue);
Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
/* Copyright 2010-present MongoDB Inc.
2+
*
3+
* Licensed under the Apache License, Version 2.0 (the "License");
4+
* you may not use this file except in compliance with the License.
5+
* You may obtain a copy of the License at
6+
*
7+
* http://www.apache.org/licenses/LICENSE-2.0
8+
*
9+
* Unless required by applicable law or agreed to in writing, software
10+
* distributed under the License is distributed on an "AS IS" BASIS,
11+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
* See the License for the specific language governing permissions and
13+
* limitations under the License.
14+
*/
15+
16+
using System.Collections.Generic;
17+
using System.Reflection;
18+
using MongoDB.Driver.Linq.Linq3Implementation.Misc;
19+
20+
namespace MongoDB.Driver.Linq.Linq3Implementation.Reflection
21+
{
22+
internal static class ISetMethod
23+
{
24+
// public static methods
25+
public static bool IsSetEqualsMethod(MethodInfo method)
26+
{
27+
// many types implement a SetEquals method but the declaringType should always implement ISet<T>
28+
var declaringType = method.DeclaringType;
29+
return
30+
declaringType.ImplementsISet(out var itemType) &&
31+
method.IsPublic &&
32+
!method.IsStatic &&
33+
method.ReturnType == typeof(bool) &&
34+
method.Name == "SetEquals" &&
35+
method.GetParameters() is var parameters &&
36+
parameters.Length == 1 &&
37+
parameters[0] is var otherParameter &&
38+
otherParameter.ParameterType == typeof(IEnumerable<>).MakeGenericType(itemType);
39+
}
40+
}
41+
}

src/MongoDB.Driver/Linq/Linq3Implementation/SerializerFinders/SerializerFinderVisitMethodCall.cs

Lines changed: 1 addition & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -2939,7 +2939,7 @@ void DeduceSequenceEqualMethodSerializers()
29392939

29402940
void DeduceSetEqualsMethodSerializers()
29412941
{
2942-
if (IsSetEqualsMethod(method))
2942+
if (ISetMethod.IsSetEqualsMethod(method))
29432943
{
29442944
var objectExpression = node.Object;
29452945
var otherExpression = arguments[0];
@@ -2951,22 +2951,6 @@ void DeduceSetEqualsMethodSerializers()
29512951
{
29522952
DeduceUnknownMethodSerializer();
29532953
}
2954-
2955-
static bool IsSetEqualsMethod(MethodInfo method)
2956-
{
2957-
var declaringType = method.DeclaringType;
2958-
var parameters = method.GetParameters();
2959-
return
2960-
method.IsPublic &&
2961-
method.IsStatic == false &&
2962-
method.ReturnType == typeof(bool) &&
2963-
method.Name == "SetEquals" &&
2964-
parameters.Length == 1 &&
2965-
parameters[0] is var otherParameter &&
2966-
declaringType.ImplementsIEnumerable(out var declaringTypeItemType) &&
2967-
otherParameter.ParameterType.ImplementsIEnumerable(out var otherTypeItemType) &&
2968-
otherTypeItemType == declaringTypeItemType;
2969-
}
29702954
}
29712955

29722956
void DeduceSetWindowFieldsMethodSerializers()

src/MongoDB.Driver/Linq/Linq3Implementation/Translators/ExpressionToAggregationExpressionTranslators/MethodTranslators/SetEqualsMethodToAggregationExpressionTranslator.cs

Lines changed: 5 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -17,15 +17,19 @@
1717
using MongoDB.Bson.Serialization.Serializers;
1818
using MongoDB.Driver.Linq.Linq3Implementation.Ast.Expressions;
1919
using MongoDB.Driver.Linq.Linq3Implementation.Misc;
20+
using MongoDB.Driver.Linq.Linq3Implementation.Reflection;
2021

2122
namespace MongoDB.Driver.Linq.Linq3Implementation.Translators.ExpressionToAggregationExpressionTranslators.MethodTranslators
2223
{
2324
internal static class SetEqualsMethodToAggregationExpressionTranslator
2425
{
2526
public static TranslatedExpression Translate(TranslationContext context, MethodCallExpression expression)
2627
{
27-
if (IsSetEqualsMethod(expression, out var objectExpression, out var otherExpression))
28+
if (ISetMethod.IsSetEqualsMethod(expression.Method))
2829
{
30+
var objectExpression = expression.Object;
31+
var otherExpression = expression.Arguments[0];
32+
2933
var objectTranslation = ExpressionToAggregationExpressionTranslator.Translate(context, objectExpression);
3034
var otherTranslation = ExpressionToAggregationExpressionTranslator.Translate(context, otherExpression);
3135
var ast = AstExpression.SetEquals(objectTranslation.Ast, otherTranslation.Ast);
@@ -34,34 +38,5 @@ public static TranslatedExpression Translate(TranslationContext context, MethodC
3438
}
3539
throw new ExpressionNotSupportedException(expression);
3640
}
37-
38-
private static bool IsSetEqualsMethod(MethodCallExpression expression, out Expression objectExpression, out Expression otherExpression)
39-
{
40-
var method = expression.Method;
41-
var arguments = expression.Arguments;
42-
43-
if (!method.IsStatic &&
44-
method.ReturnType == typeof(bool) &&
45-
method.Name == "SetEquals" &&
46-
arguments.Count == 1)
47-
{
48-
objectExpression = expression.Object;
49-
otherExpression = arguments[0];
50-
if (objectExpression.Type.TryGetIEnumerableGenericInterface(out var objectEnumerableInterface) &&
51-
otherExpression.Type.TryGetIEnumerableGenericInterface(out var otherEnumerableInterface))
52-
{
53-
var objectItemType = objectEnumerableInterface.GetGenericArguments()[0];
54-
var otherItemType = otherEnumerableInterface.GetGenericArguments()[0];
55-
if (objectItemType == otherItemType)
56-
{
57-
return true;
58-
}
59-
}
60-
}
61-
62-
objectExpression = null;
63-
otherExpression = null;
64-
return false;
65-
}
6641
}
6742
}

0 commit comments

Comments
 (0)