-
Notifications
You must be signed in to change notification settings - Fork 935
/
Copy pathLinqBatchItem.cs
103 lines (88 loc) · 2.81 KB
/
LinqBatchItem.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using NHibernate.Linq;
using Remotion.Linq.Parsing.ExpressionVisitors;
namespace NHibernate.Multi
{
interface ILinqBatchItem
{
List<TResult> GetTypedResults<TResult>();
}
public static class LinqBatchItem
{
public static LinqBatchItem<TResult> Create<T, TResult>(IQueryable<T> query, Expression<Func<IQueryable<T>, TResult>> selector)
{
if (query == null)
throw new ArgumentNullException(nameof(query));
if (selector == null)
throw new ArgumentNullException(nameof(selector));
var expression = ReplacingExpressionVisitor
.Replace(selector.Parameters.Single(), query.Expression, selector.Body);
return GetForQuery<TResult>(query, expression);
}
public static LinqBatchItem<T> Create<T>(IQueryable<T> query)
{
return GetForQuery<T>(query, null);
}
private static LinqBatchItem<TResult> GetForQuery<TResult>(IQueryable query, Expression ex = null)
{
if (query == null)
throw new ArgumentNullException(nameof(query));
var prov = (ISupportFutureBatchNhQueryProvider) query.Provider;
var q = prov.GetPreparedQuery(ex ?? query.Expression, out var linqEx);
return new LinqBatchItem<TResult>(q, linqEx);
}
}
/// <summary>
/// Create instance via <see cref="LinqBatchItem.Create"/> methods
/// </summary>
/// <typeparam name="T">Result type</typeparam>
public partial class LinqBatchItem<T> : QueryBatchItem<T>, ILinqBatchItem
{
private readonly Delegate _postExecuteTransformer;
private readonly System.Type _resultTypeOverride;
public LinqBatchItem(IQuery query) : base(query)
{
}
internal LinqBatchItem(IQuery query, NhLinqExpression linq) : base(query)
{
_postExecuteTransformer = linq.ExpressionToHqlTranslationResults.PostExecuteTransformer;
_resultTypeOverride = linq.ExpressionToHqlTranslationResults.ExecuteResultTypeOverride;
}
protected override IList<T> GetResultsNonBatched()
{
if (_postExecuteTransformer == null)
{
return base.GetResultsNonBatched();
}
return GetTransformedResults(Query.List());
}
protected override List<T> DoGetResults()
{
if (_postExecuteTransformer != null)
{
IList transformerList = _resultTypeOverride == null
? base.DoGetResults()
//see LinqToFutureValueFixture tests that cover this scenario
: LinqBatchReflectHelper.GetTypedResults(this, _resultTypeOverride);
return GetTransformedResults(transformerList);
}
return base.DoGetResults();
}
private List<T> GetTransformedResults(IList transformerList)
{
var res = _postExecuteTransformer.DynamicInvoke(transformerList.AsQueryable());
return new List<T>
{
(T) res
};
}
List<TResult> ILinqBatchItem.GetTypedResults<TResult>()
{
return GetTypedResults<TResult>();
}
}
}