[#120]支持linq方式顺序和非顺序查询

This commit is contained in:
xuejiaming 2022-02-16 23:44:48 +08:00
parent f72a5819dc
commit ae373e21d6
14 changed files with 189 additions and 26 deletions

View File

@ -188,6 +188,32 @@ namespace Sample.SqlServer.Controllers
});
}
[HttpGet]
public async Task<IActionResult> Get2a1([FromQuery] int p, [FromQuery] int s)
{
Stopwatch sp = new Stopwatch();
sp.Start();
var shardingPageResultAsync = await _defaultTableDbContext.Set<SysUserMod>().UseConnectionMode(1).OrderBy(o => o.Age).ToShardingPageAsync(p, s);
sp.Stop();
return Ok(new
{
sp.ElapsedMilliseconds,
shardingPageResultAsync
});
}
[HttpGet]
public async Task<IActionResult> Get2a2([FromQuery] int p, [FromQuery] int s)
{
Stopwatch sp = new Stopwatch();
sp.Start();
var shardingPageResultAsync = await _defaultTableDbContext.Set<SysUserMod>().UseConnectionMode(1).OrderBy(o => o.Age).ToShardingPageAsync(p, s);
sp.Stop();
return Ok(new
{
sp.ElapsedMilliseconds,
shardingPageResultAsync
});
}
[HttpGet]
public IActionResult Get2([FromQuery] int p, [FromQuery] int s)
{
Stopwatch sp = new Stopwatch();

View File

@ -2,12 +2,12 @@ using System;
namespace ShardingCore.Core
{
/*
* @Author: xjm
* @Description:
* @Date: Friday, 05 February 2021 12:53:46
* @Email: 326308290@qq.com
*/
/*
* @Author: xjm
* @Description:
* @Date: Friday, 05 February 2021 12:53:46
* @Email: 326308290@qq.com
*/
/// <summary>
/// 数据源分库规则字段
/// </summary>

View File

@ -2,12 +2,12 @@
namespace ShardingCore.Core
{
/*
* @Author: xjm
* @Description:
* @Date: Wednesday, 16 December 2020 11:04:51
* @Email: 326308290@qq.com
*/
/*
* @Author: xjm
* @Description:
* @Date: Wednesday, 16 December 2020 11:04:51
* @Email: 326308290@qq.com
*/
/// <summary>
/// 分片额外配置
/// </summary>

View File

@ -2,12 +2,12 @@
namespace ShardingCore.Core
{
/*
* @Author: xjm
* @Description:
* @Date: Wednesday, 16 December 2020 11:04:51
* @Email: 326308290@qq.com
*/
/*
* @Author: xjm
* @Description:
* @Date: Wednesday, 16 December 2020 11:04:51
* @Email: 326308290@qq.com
*/
/// <summary>
/// AbstractVirtualTableRoute 最基础分表规则 需要自己解析如何分表
/// 仅ShardingMode为Custom:以下接口提供自定义分表

View File

@ -36,6 +36,14 @@ namespace ShardingCore.Extensions.ShardingQueryableExtensions
.Where(m => m.Name == nameof(UseConnectionMode))
.Single(m => m.GetParameters().Any(p => p.ParameterType == typeof(ShardingQueryableUseConnectionModeOptions)));
internal static readonly MethodInfo AsSequenceModeMethodInfo
= typeof(EntityFrameworkShardingQueryableExtension)
.GetTypeInfo()
.GetMethods(BindingFlags.Instance | BindingFlags.Static | BindingFlags.NonPublic)
.Where(m => m.Name == nameof(AsSequence))
.Single(m => m.GetParameters().Any(p => p.ParameterType == typeof(ShardingQueryableAsSequenceOptions)));
//internal static readonly MethodInfo ReadWriteSeparationMethodInfo
// = typeof(EntityFrameworkShardingQueryableExtension)
// .GetTypeInfo()
@ -124,6 +132,46 @@ namespace ShardingCore.Extensions.ShardingQueryableExtensions
Expression.Constant(shardingQueryableUseConnectionModeOptions)))
: source;
}
/// <summary>
/// 不使用顺序查询
/// </summary>
/// <typeparam name="TEntity"></typeparam>
/// <param name="source"></param>
/// <returns></returns>
public static IQueryable<TEntity> AsNoSequence<TEntity>(this IQueryable<TEntity> source)
{
Check.NotNull(source, nameof(source));
return source.AsSequence(new ShardingQueryableAsSequenceOptions(true, false));
}
/// <summary>
/// 使用顺序查询
/// </summary>
/// <typeparam name="TEntity"></typeparam>
/// <param name="source"></param>
/// <param name="comparerWithShardingComparer"></param>
/// <returns></returns>
public static IQueryable<TEntity> AsSequence<TEntity>(this IQueryable<TEntity> source,
bool comparerWithShardingComparer)
{
Check.NotNull(source, nameof(source));
return source.AsSequence(new ShardingQueryableAsSequenceOptions(comparerWithShardingComparer,true));
}
internal static IQueryable<TEntity> AsSequence<TEntity>(this IQueryable<TEntity> source, ShardingQueryableAsSequenceOptions shardingQueryableAsSequenceOptions)
{
Check.NotNull(source, nameof(source));
return
source.Provider is EntityQueryProvider
? source.Provider.CreateQuery<TEntity>(
Expression.Call(
(Expression)null,
AsSequenceModeMethodInfo.MakeGenericMethod(typeof(TEntity)),
source.Expression,
Expression.Constant(shardingQueryableAsSequenceOptions)))
: source;
}
///// <summary>
///// 走读库

View File

@ -0,0 +1,20 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ShardingCore.Extensions.ShardingQueryableExtensions
{
internal class ShardingQueryableAsSequenceOptions
{
public bool SameWithShardingComparer { get; }
public bool AsSequence { get; }
public ShardingQueryableAsSequenceOptions(bool sameWithShardingComparer,bool asSequence)
{
SameWithShardingComparer = sameWithShardingComparer;
AsSequence = asSequence;
}
}
}

View File

@ -51,5 +51,8 @@ namespace ShardingCore.Sharding.ShardingExecutors.Abstractions
/// </summary>
/// <returns></returns>
Action<ShardingRouteContext> GetAsRoute();
bool? IsSequence();
bool? SameWithShardingComparer();
}
}

View File

@ -38,5 +38,7 @@ namespace ShardingCore.Sharding.ShardingExecutors.Abstractions
int? GetMaxQueryConnectionsLimit();
ConnectionModeEnum? GetConnectionMode();
bool? IsSequence();
bool? SameWithShardingComparer();
}
}

View File

@ -25,6 +25,8 @@ namespace ShardingCore.ShardingExecutors
private readonly ConnectionModeEnum? _connectionMode;
private readonly bool? _readOnly;
private readonly Action<ShardingRouteContext> _shardingRouteConfigure;
private readonly bool? _isSequence;
private readonly bool? _sameWithShardingComparer;
public CompileParameter(IShardingDbContext shardingDbContext,Expression shardingQueryExpression)
{
_shardingDbContext = shardingDbContext;
@ -39,6 +41,10 @@ namespace ShardingCore.ShardingExecutors
{
_readOnly = extractShardingParameter?.ShardingQueryableReadWriteSeparationOptions?.RouteReadConnect??shardingDbContext.CurrentIsReadWriteSeparation();
}
_isSequence = extractShardingParameter.ShardingQueryableAsSequenceOptions?.AsSequence;
_sameWithShardingComparer = extractShardingParameter.ShardingQueryableAsSequenceOptions
?.SameWithShardingComparer;
}
public IShardingDbContext GetShardingDbContext()
@ -75,5 +81,15 @@ namespace ShardingCore.ShardingExecutors
{
return _shardingRouteConfigure;
}
public bool? IsSequence()
{
return _isSequence;
}
public bool? SameWithShardingComparer()
{
return _sameWithShardingComparer;
}
}
}

View File

@ -125,6 +125,16 @@ namespace ShardingCore.Sharding.ShardingExecutors
return _queryCompilerContext.GetConnectionMode();
}
public bool? IsSequence()
{
return _queryCompilerContext.IsSequence();
}
public bool? SameWithShardingComparer()
{
return _queryCompilerContext.SameWithShardingComparer();
}
public QueryCompilerExecutor GetQueryCompilerExecutor()
{
if (!hasQueryCompilerExecutor.HasValue)

View File

@ -28,6 +28,8 @@ namespace ShardingCore.Sharding.ShardingExecutors
private readonly bool _isNotSupport;
private readonly int? _maxQueryConnectionsLimit;
private readonly ConnectionModeEnum? _connectionMode;
private readonly bool? _isSequence;
private readonly bool? _sameWithShardingComparer;
private QueryCompilerContext(ICompileParameter compileParameter)
{
@ -45,6 +47,8 @@ namespace ShardingCore.Sharding.ShardingExecutors
//原生对象的原生查询如果是读写分离就需要启用并行查询
_isParallelQuery = compileParameter.ReadOnly().GetValueOrDefault();
_isSequence = compileParameter.IsSequence();
_sameWithShardingComparer = compileParameter.SameWithShardingComparer();
}
public static QueryCompilerContext Create(ICompileParameter compileParameter)
@ -118,6 +122,16 @@ namespace ShardingCore.Sharding.ShardingExecutors
return _connectionMode;
}
public bool? IsSequence()
{
return _isSequence;
}
public bool? SameWithShardingComparer()
{
return _sameWithShardingComparer;
}
public QueryCompilerExecutor GetQueryCompilerExecutor()
{

View File

@ -143,16 +143,27 @@ namespace ShardingCore.Sharding
}
}
var propertyOrders = Orders as PropertyOrder[] ?? Orders.ToArray();
if (TryGetSequenceQuery(propertyOrders, singleShardingEntityType, virtualTable, methodName,
out var tailComparerIsAsc))
var isSequence = mergeQueryCompilerContext.IsSequence();
var sameWithShardingComparer = mergeQueryCompilerContext.SameWithShardingComparer();
if (isSequence.HasValue && sameWithShardingComparer.HasValue)
{
_seqQuery = true;
if (!tailComparerIsAsc)
_seqQuery = isSequence.Value;
TailComparerNeedReverse = sameWithShardingComparer.Value;
}
else
{
var propertyOrders = Orders as PropertyOrder[] ?? Orders.ToArray();
if (TryGetSequenceQuery(propertyOrders, singleShardingEntityType, virtualTable, methodName,
out var tailComparerIsAsc))
{
TailComparerNeedReverse = !TailComparerNeedReverse;
_seqQuery = true;
if (!tailComparerIsAsc)
{
TailComparerNeedReverse = !TailComparerNeedReverse;
}
}
}
}
}

View File

@ -15,16 +15,19 @@ namespace ShardingCore.Sharding.Visitors.ShardingExtractParameters
public ShardingQueryableAsRouteOptions ShardingQueryableAsRouteOptions { get; }
public ShardingQueryableUseConnectionModeOptions ShardingQueryableUseConnectionModeOptions { get; }
public ShardingQueryableReadWriteSeparationOptions ShardingQueryableReadWriteSeparationOptions { get; }
public ShardingQueryableAsSequenceOptions ShardingQueryableAsSequenceOptions { get; }
public ShardingExtParameter(bool isNotSupport,
ShardingQueryableAsRouteOptions shardingQueryableAsRouteOptions,
ShardingQueryableUseConnectionModeOptions shardingQueryableUseConnectionModeOptions,
ShardingQueryableReadWriteSeparationOptions shardingQueryableReadWriteSeparationOptions)
ShardingQueryableReadWriteSeparationOptions shardingQueryableReadWriteSeparationOptions,
ShardingQueryableAsSequenceOptions shardingQueryableAsSequenceOptions)
{
IsNotSupport = isNotSupport;
ShardingQueryableAsRouteOptions = shardingQueryableAsRouteOptions;
ShardingQueryableUseConnectionModeOptions = shardingQueryableUseConnectionModeOptions;
ShardingQueryableReadWriteSeparationOptions = shardingQueryableReadWriteSeparationOptions;
ShardingQueryableAsSequenceOptions = shardingQueryableAsSequenceOptions;
}
}
}

View File

@ -17,10 +17,11 @@ namespace ShardingCore.Sharding.Visitors.ShardingExtractParameters
private ShardingQueryableUseConnectionModeOptions shardingQueryableUseConnectionModeOptions;
private ShardingQueryableAsRouteOptions shardingQueryableAsRouteOptions;
private ShardingQueryableReadWriteSeparationOptions shardingQueryableReadWriteSeparationOptions;
private ShardingQueryableAsSequenceOptions shardingQueryableAsSequenceOptions;
public ShardingExtParameter ExtractShardingParameter()
{
return new ShardingExtParameter(isNotSupport, shardingQueryableAsRouteOptions, shardingQueryableUseConnectionModeOptions, shardingQueryableReadWriteSeparationOptions);
return new ShardingExtParameter(isNotSupport, shardingQueryableAsRouteOptions, shardingQueryableUseConnectionModeOptions, shardingQueryableReadWriteSeparationOptions, shardingQueryableAsSequenceOptions);
}
protected override Expression VisitMethodCall(MethodCallExpression node)
{
@ -52,6 +53,15 @@ namespace ShardingCore.Sharding.Visitors.ShardingExtractParameters
.Last();
return Visit(node.Arguments[0]);
}
else if (genericMethodDefinition == EntityFrameworkShardingQueryableExtension.AsSequenceModeMethodInfo)
{
shardingQueryableAsSequenceOptions = node.Arguments
.OfType<ConstantExpression>()
.Where(o => o.Value is ShardingQueryableAsSequenceOptions)
.Select(o => (ShardingQueryableAsSequenceOptions)o.Value)
.Last();
return Visit(node.Arguments[0]);
}
//else if (genericMethodDefinition == EntityFrameworkShardingQueryableExtension.ReadWriteSeparationMethodInfo)
//{
// shardingQueryableReadWriteSeparationOptions = node.Arguments