@@ -5,7 +5,7 @@ using Microsoft.Extensions.Logging; | |||||
using Newtonsoft.Json; | using Newtonsoft.Json; | ||||
using SqlSugar; | using SqlSugar; | ||||
namespace BPA.Component.DbClient.RepositoryModel | |||||
namespace BPA.Component.DbClient | |||||
{ | { | ||||
/// <summary> | /// <summary> | ||||
/// 数据库客户端基类 | /// 数据库客户端基类 | ||||
@@ -19,7 +19,7 @@ namespace BPA.Component.DbClient.RepositoryModel | |||||
private readonly ILogger<TDbClient> _logger; | private readonly ILogger<TDbClient> _logger; | ||||
/// <summary> | /// <summary> | ||||
/// 是否打印日志 | |||||
/// 是否打印SQL | |||||
/// </summary> | /// </summary> | ||||
private readonly bool _isLogSql; | private readonly bool _isLogSql; | ||||
@@ -1,4 +1,5 @@ | |||||
using BPA.Component.DbClient.RepositoryModel; | |||||
using BPA.Component.DbClient; | |||||
using BPA.Component.DbClient.RepositoryModel; | |||||
using Microsoft.Extensions.Logging; | using Microsoft.Extensions.Logging; | ||||
using SqlSugar; | using SqlSugar; | ||||
@@ -4,7 +4,7 @@ | |||||
"commandName": "Project", | "commandName": "Project", | ||||
"environmentVariables": { | "environmentVariables": { | ||||
"ASPNETCORE_ENVIRONMENT": "Development", | "ASPNETCORE_ENVIRONMENT": "Development", | ||||
"APOLLO_META_SERVER_URL": "http://192.168.1.222:28080", | |||||
"APOLLO_META_SERVER_URL": "http://10.2.1.21:28080", | |||||
"APOLLO_COMMON_NAMESPACE": "Dev.Common", | "APOLLO_COMMON_NAMESPACE": "Dev.Common", | ||||
"APP_NAME": "BPA-DEV" | "APP_NAME": "BPA-DEV" | ||||
} | } | ||||
@@ -18,6 +18,7 @@ | |||||
</PropertyGroup> | </PropertyGroup> | ||||
<ItemGroup> | <ItemGroup> | ||||
<PackageReference Include="BPA.Component.Extensions" Version="1.0.1" /> | <PackageReference Include="BPA.Component.Extensions" Version="1.0.1" /> | ||||
<PackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="6.0.0" /> | |||||
<PackageReference Include="MongoDB.Driver" Version="2.15.0" /> | <PackageReference Include="MongoDB.Driver" Version="2.15.0" /> | ||||
<PackageReference Include="Nuget.Tools.V2" Version="1.1.6"> | <PackageReference Include="Nuget.Tools.V2" Version="1.1.6"> | ||||
<PrivateAssets>all</PrivateAssets> | <PrivateAssets>all</PrivateAssets> | ||||
@@ -1,631 +0,0 @@ | |||||
using System.Linq.Expressions; | |||||
using MongoDB.Driver; | |||||
using MongoDB.Driver.Linq; | |||||
namespace BPA.Component.MongoClient | |||||
{ | |||||
/// <summary> | |||||
/// MongoDb基础仓储 | |||||
/// </summary> | |||||
public abstract class BaseMGRepository<TDocument> : IMGRepository<TDocument> where TDocument : new() | |||||
{ | |||||
/// <summary> | |||||
/// 当前企业(商户)Id | |||||
/// </summary> | |||||
public long CorpId { protected set; get; } | |||||
/// <summary> | |||||
/// 当前MongoDB上下文 | |||||
/// </summary> | |||||
public MongoDbContext CurrMongoDbContext { protected set; get; } | |||||
/// <summary> | |||||
/// 当前需要操作的文档集 | |||||
/// </summary> | |||||
public IMongoCollection<TDocument> CurrentCollection { protected set; get; } | |||||
/// <summary> | |||||
/// MongoDbProvider | |||||
/// </summary> | |||||
public MongoDbProvider MongoDbProvider { protected set; get; } | |||||
/// <summary> | |||||
/// 构造方法 | |||||
/// </summary> | |||||
/// <param name="mongoDbProvider"></param> | |||||
public BaseMGRepository(MongoDbProvider mongoDbProvider) | |||||
{ | |||||
MongoDbProvider = mongoDbProvider; | |||||
} | |||||
/// <summary> | |||||
/// 切换企业Id | |||||
/// </summary> | |||||
/// <param name="corpId"></param> | |||||
public virtual void ChangeCorpId(long corpId) | |||||
{ | |||||
CorpId = corpId; | |||||
CurrMongoDbContext = MongoDbProvider.GetDbContext(corpId); | |||||
CurrentCollection = CurrMongoDbContext.GetCollection<TDocument>(null); | |||||
} | |||||
/// <summary> | |||||
/// 检查当前文档集 | |||||
/// </summary> | |||||
private void CheckCurrentCollection() | |||||
{ | |||||
if (CurrentCollection == null) | |||||
throw new ArgumentNullException($"当前要操作的文档集为空,请调用{nameof(ChangeCorpId)}方法切换企业Id!"); | |||||
} | |||||
#region 插入扩展 | |||||
/// <summary> | |||||
/// 插入一个 ,等同使用:<code>IMongoCollection.InsertOne</code> | |||||
/// </summary> | |||||
/// <param name="document">文档对象</param> | |||||
/// <param name="options">插入配置选项</param> | |||||
public void InsertOne(TDocument document, InsertOneOptions? options = null) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
CurrentCollection.InsertOne(document, options); | |||||
} | |||||
/// <summary> | |||||
/// 插入多个,等同使用: | |||||
/// <code>IMongoCollection.InsertMany(IClientSessionHandle, IEnumerable{TDocument}, InsertManyOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="documents">文档对象</param> | |||||
/// <param name="options">插入配置选项</param> | |||||
public void InsertMany(IEnumerable<TDocument> documents, InsertManyOptions? options = null) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
CurrentCollection.InsertMany(documents, options); | |||||
} | |||||
/// <summary> | |||||
/// 插入一个 ,等同使用:<code>IMongoCollection.InsertOneAsync</code> | |||||
/// </summary> | |||||
/// <param name="document">文档对象</param> | |||||
/// <param name="options">插入配置选项</param> | |||||
public Task InsertOneAsync(TDocument document, InsertOneOptions? options = null) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.InsertOneAsync(document, options); | |||||
} | |||||
/// <summary> | |||||
/// 插入多个,等同使用: | |||||
/// <code>IMongoCollection.InsertManyAsync(IEnumerable{TDocument}, InsertManyOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="documents">文档对象</param> | |||||
/// <param name="options">插入配置选项</param> | |||||
public Task InsertManyAsync(IEnumerable<TDocument> documents, InsertManyOptions? options = null) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.InsertManyAsync(documents, options); | |||||
} | |||||
#endregion | |||||
#region 更新扩展 | |||||
/// <summary> | |||||
/// 更新满足条件的第一条数据, | |||||
/// <code>IMongoCollection.UpdateOne(FilterDefinition{TDocument}, UpdateDefinition{TDocument}, UpdateOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document"></param> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="options"></param> | |||||
public UpdateResult UpdateOne(TDocument document, Expression<Func<TDocument, bool>> whereExpression, | |||||
UpdateOptions options = null) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.UpdateOne(document, whereExpression, options); | |||||
} | |||||
/// <summary> | |||||
/// 更新满足条件的第一条数据, | |||||
/// <code>IMongoCollection.UpdateOneAsync(FilterDefinition{TDocument}, UpdateDefinition{TDocument}, UpdateOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document"></param> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="options"></param> | |||||
public Task<UpdateResult> UpdateOneAsync(TDocument document, Expression<Func<TDocument, bool>> whereExpression, | |||||
UpdateOptions options = null) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.UpdateOneAsync(document, whereExpression, options); | |||||
} | |||||
/// <summary> | |||||
/// 更新满足条件的多条数据, | |||||
/// <code>IMongoCollection.UpdateOne(FilterDefinition{TDocument}, UpdateDefinition{TDocument},UpdateOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document"></param> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="options"></param> | |||||
public UpdateResult UpdateMany(TDocument document, Expression<Func<TDocument, bool>> whereExpression, | |||||
UpdateOptions options = null) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.UpdateMany(document, whereExpression, options); | |||||
} | |||||
/// <summary> | |||||
/// 更新满足条件的多条数据, | |||||
/// <code>IMongoCollection.UpdateOne(FilterDefinition{TDocument}, UpdateDefinition{TDocument},UpdateOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document"></param> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="options"></param> | |||||
public Task<UpdateResult> UpdateManyAsync(TDocument document, Expression<Func<TDocument, bool>> whereExpression, | |||||
UpdateOptions options = null) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.UpdateManyAsync(document, whereExpression, options); | |||||
} | |||||
/// <summary> | |||||
/// 自定义字段更新 更新满足条件的第一条数据,实体键_id不允许更新 | |||||
/// </summary> | |||||
/// <param name="whereExpression">更新条件</param> | |||||
/// <param name="columnsExp">更新字段表达式:x=>new TDocument{ F1=1,F2=2 }</param> | |||||
/// <returns></returns> | |||||
public UpdateResult UpdateOne(Expression<Action<TDocument>> columnsExp, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.UpdateOne(columnsExp, whereExpression); | |||||
} | |||||
/// <summary> | |||||
/// 自定义字段更新 更新满足条件的第一条数据,实体键_id不允许更新 | |||||
/// </summary> | |||||
/// <param name="whereExpression">更新条件</param> | |||||
/// <param name="columnsExp">更新字段表达式:x=>new TDocument{ F1=1,F2=2 }</param> | |||||
/// <returns></returns> | |||||
public Task<UpdateResult> UpdateOneAsync(Expression<Action<TDocument>> columnsExp, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.UpdateOneAsync(columnsExp, whereExpression); | |||||
} | |||||
/// <summary> | |||||
/// 自定义更新字段和条件,更新单条符合条件的数据 | |||||
/// </summary> | |||||
/// <param name="filter"></param> | |||||
/// <param name="update"></param> | |||||
/// <param name="options"></param> | |||||
/// <returns></returns> | |||||
public UpdateResult UpdateOne(FilterDefinition<TDocument> filter, UpdateDefinition<TDocument> update, | |||||
UpdateOptions options = null) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.UpdateOne(filter, update, options); | |||||
} | |||||
/// <summary> | |||||
/// 自定义更新字段和条件,更新单条符合条件的数据 | |||||
/// </summary> | |||||
/// <param name="filter"></param> | |||||
/// <param name="update"></param> | |||||
/// <param name="options"></param> | |||||
/// <returns></returns> | |||||
public Task<UpdateResult> UpdateOneAsync(FilterDefinition<TDocument> filter, UpdateDefinition<TDocument> update, | |||||
UpdateOptions options = null) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.UpdateOneAsync(filter, update, options); | |||||
} | |||||
/// <summary> | |||||
/// 自定义更新字段和条件,更新条符合条件的数据 | |||||
/// </summary> | |||||
/// <param name="filter"></param> | |||||
/// <param name="update"></param> | |||||
/// <param name="options"></param> | |||||
/// <returns></returns> | |||||
public UpdateResult UpdateMany(FilterDefinition<TDocument> filter, UpdateDefinition<TDocument> update, | |||||
UpdateOptions options = null) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.UpdateMany(filter, update, options); | |||||
} | |||||
/// <summary> | |||||
/// 自定义更新字段和条件,更新条符合条件的数据 | |||||
/// </summary> | |||||
/// <param name="filter"></param> | |||||
/// <param name="update"></param> | |||||
/// <param name="options"></param> | |||||
/// <returns></returns> | |||||
public Task<UpdateResult> UpdateManyAsync(FilterDefinition<TDocument> filter, | |||||
UpdateDefinition<TDocument> update, | |||||
UpdateOptions options = null) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.UpdateManyAsync(filter, update, options); | |||||
} | |||||
/// <summary> | |||||
/// 自定义字段更新 更新满足条件的多条数据,实体键_id不允许更新 | |||||
/// </summary> | |||||
/// <param name="whereExpression">更新条件</param> | |||||
/// <param name="columnsExp">更新字段表达式:x=>new TDocument{ F1=1,F2=2 }</param> | |||||
/// <returns></returns> | |||||
public UpdateResult UpdateMany(Expression<Action<TDocument>> columnsExp, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.UpdateMany(columnsExp, whereExpression); | |||||
} | |||||
/// <summary> | |||||
/// 自定义字段更新 更新满足条件的多条数据,实体键_id不允许更新 | |||||
/// </summary> | |||||
/// <param name="whereExpression">更新条件</param> | |||||
/// <param name="columnsExp">更新字段表达式:x=>new TDocument{ F1=1,F2=2 }</param> | |||||
/// <returns></returns> | |||||
public Task<UpdateResult> UpdateManyAsync(Expression<Action<TDocument>> columnsExp, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.UpdateManyAsync(columnsExp, whereExpression); | |||||
} | |||||
/// <summary> | |||||
/// 异步覆盖更新满足条件的第一条数据,主键字段名称必须是 Id,等同 | |||||
/// <code>IMongoCollection.ReplaceOne(FilterDefinition{TDocument}, TDocument, ReplaceOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document">文档对象对象</param> | |||||
/// <returns></returns> | |||||
public ReplaceOneResult ReplaceOneById(TDocument document) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.ReplaceOneById(document); | |||||
} | |||||
/// <summary> | |||||
/// 异步覆盖更新满足条件的第一条数据,主键字段名称必须是 Id,等同 | |||||
/// <code>IMongoCollection.ReplaceOne(FilterDefinition{TDocument}, TDocument, ReplaceOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document">文档对象对象</param> | |||||
/// <returns></returns> | |||||
public Task<ReplaceOneResult> ReplaceOneByIdAsync(TDocument document) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.ReplaceOneByIdAsync(document); | |||||
} | |||||
/// <summary> | |||||
/// 异步覆盖更新满足条件的第一条数据,主键字段名称必须是 ID,等同 | |||||
/// <code>IMongoCollection.ReplaceOne(FilterDefinition{TDocument}, TDocument, ReplaceOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document">文档对象对象</param> | |||||
/// <param name="whereExpression">查询添加表达式</param> | |||||
/// <returns></returns> | |||||
public ReplaceOneResult ReplaceOne(TDocument document, Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.ReplaceOne(document, whereExpression); | |||||
} | |||||
/// <summary> | |||||
/// 异步覆盖更新满足条件的第一条数据,主键字段名称必须是 ID,等同 | |||||
/// <code>IMongoCollection.ReplaceOne(FilterDefinition{TDocument}, TDocument, ReplaceOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document">文档对象对象</param> | |||||
/// <param name="whereExpression">查询添加表达式</param> | |||||
/// <returns></returns> | |||||
public Task<ReplaceOneResult> ReplaceOneAsync(TDocument document, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.ReplaceOneAsync(document, whereExpression); | |||||
} | |||||
#endregion | |||||
#region 删除扩展 | |||||
/// <summary> | |||||
/// 删除满足条件的第一条数据,等同于 | |||||
/// <code>IMongoCollection.DeleteOne(FilterDefinition{TDocument}, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="whereExpression">删除条件表达式</param> | |||||
public DeleteResult DeleteOne(Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.DeleteOne(whereExpression); | |||||
} | |||||
/// <summary> | |||||
/// 删除满足条件的第一条数据,等同于 | |||||
/// <code>IMongoCollection.DeleteOne(FilterDefinition{TDocument}, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="whereExpression">删除条件表达式</param> | |||||
public Task<DeleteResult> DeleteOneAsync(Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.DeleteOneAsync(whereExpression); | |||||
} | |||||
/// <summary> | |||||
/// 批量删除满足条件的多条数据,等同于 | |||||
/// <code>IMongoCollection.DeleteMany(FilterDefinition{TDocument}, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="whereExpression">删除条件表达式</param> | |||||
public DeleteResult DeleteMany(Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.DeleteMany(whereExpression); | |||||
} | |||||
/// <summary> | |||||
/// 批量删除满足条件的多条数据,等同于 | |||||
/// <code>IMongoCollection.DeleteMany(FilterDefinition{TDocument}, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="whereExpression">删除条件表达式</param> | |||||
public Task<DeleteResult> DeleteManyAsync(Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.DeleteManyAsync(whereExpression); | |||||
} | |||||
#endregion | |||||
#region 查询扩展 | |||||
/// <summary> | |||||
/// 根据条件查询 | |||||
/// </summary> | |||||
/// <param name="filter"></param> | |||||
/// <param name="options"></param> | |||||
/// <returns></returns> | |||||
public IFindFluent<TDocument, TDocument> Find(FilterDefinition<TDocument> filter, FindOptions? options) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Find(filter, options); | |||||
} | |||||
/// <summary> | |||||
/// 根据条件查询 | |||||
/// </summary> | |||||
/// <param name="filter"></param> | |||||
/// <param name="options"></param> | |||||
/// <returns></returns> | |||||
public Task<IAsyncCursor<TDocument>> FindAsync( | |||||
FilterDefinition<TDocument> filter, | |||||
FindOptions<TDocument, TDocument>? options) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.FindAsync(filter, options); | |||||
} | |||||
/// <summary> | |||||
/// 可查询 <see cref="IMongoCollectionExtensions.AsQueryable{TDocument}(IMongoCollection{TDocument}, AggregateOptions)"/> | |||||
/// </summary> | |||||
/// <returns></returns> | |||||
public IMongoQueryable<TDocument> Queryable() | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Queryable(); | |||||
} | |||||
/// <summary> | |||||
/// 可查询 根据条件 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <returns></returns> | |||||
public IMongoQueryable<TDocument> Queryable(Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Queryable().Where(whereExpression); | |||||
} | |||||
/// <summary> | |||||
/// 可查询 根据条件 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="selectExpression"></param> | |||||
/// <returns></returns> | |||||
public IMongoQueryable<TResult> Queryable<TResult>(Expression<Func<TDocument, bool>> whereExpression, | |||||
Expression<Func<TDocument, TResult>> selectExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Queryable().Where(whereExpression).Select(selectExpression); | |||||
} | |||||
/// <summary> | |||||
/// 根据条件判断是否存在 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <returns></returns> | |||||
public bool Any(Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Queryable().Where(whereExpression).Any(); | |||||
} | |||||
/// <summary> | |||||
/// 根据ID获取entity | |||||
/// </summary> | |||||
/// <param name="id"></param> | |||||
/// <returns></returns> | |||||
public TDocument GetById(dynamic id) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
FilterDefinition<TDocument> filter = Builders<TDocument>.Filter.Eq("_id", id); | |||||
var find = CurrentCollection.Find(filter, null); | |||||
return find.FirstOrDefault(); | |||||
} | |||||
/// <summary> | |||||
/// 根据ID获取entity | |||||
/// </summary> | |||||
/// <param name="id"></param> | |||||
/// <returns></returns> | |||||
public async Task<TDocument> GetByIdAsync(dynamic id) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
FilterDefinition<TDocument> filter = Builders<TDocument>.Filter.Eq("_id", id); | |||||
var find = await CurrentCollection.FindAsync(filter, null); | |||||
return find.FirstOrDefault(); | |||||
} | |||||
/// <summary> | |||||
/// 根据ID获取entity | |||||
/// </summary> | |||||
/// <param name="id"></param> | |||||
/// <param name="selectExpression">需要返会的字段表达式</param> | |||||
/// <returns></returns> | |||||
public TResult GetById<TResult>(dynamic id, Expression<Func<TDocument, TResult>> selectExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
FilterDefinition<TDocument> filter = Builders<TDocument>.Filter.Eq("_id", id); | |||||
var find = CurrentCollection.Find(filter, null); | |||||
return find.Select(selectExpression).FirstOrDefault(); | |||||
} | |||||
/// <summary> | |||||
/// 根据条件 获取第一条数据 | |||||
/// </summary> | |||||
/// <param name="whereExpression">条件</param> | |||||
/// <param name="selectExpression">返回的新对象选择表达式</param> | |||||
/// <returns></returns> | |||||
public TResult? First<TResult>(Expression<Func<TDocument, bool>> whereExpression, | |||||
Expression<Func<TDocument, TResult>> selectExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Queryable().Where(whereExpression).Select(selectExpression).FirstOrDefault(); | |||||
} | |||||
/// <summary> | |||||
/// 根据条件 获取第一条数据 | |||||
/// </summary> | |||||
/// <param name="whereExpression">条件</param> | |||||
/// <param name="selectExpression">返回的新对象选择表达式</param> | |||||
/// <returns></returns> | |||||
public Task<TResult> FirstAsync<TResult>(Expression<Func<TDocument, bool>> whereExpression, | |||||
Expression<Func<TDocument, TResult>> selectExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Queryable().Where(whereExpression).Select(selectExpression).FirstOrDefaultAsync(); | |||||
} | |||||
/// <summary> | |||||
/// 根据条件 获取第一条数据 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <returns></returns> | |||||
public TDocument? First(Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Queryable().Where(whereExpression).FirstOrDefault(); | |||||
} | |||||
/// <summary> | |||||
/// 根据条件 获取第一条数据 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <returns></returns> | |||||
public Task<TDocument> FirstAsync(Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Queryable().Where(whereExpression).FirstOrDefaultAsync(); | |||||
} | |||||
/// <summary> | |||||
/// 根据条件获取集合 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <returns></returns> | |||||
public List<TDocument> QueryList(Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Queryable().Where(whereExpression).ToList(); | |||||
} | |||||
/// <summary> | |||||
/// 根据条件获取集合 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <returns></returns> | |||||
public Task<List<TDocument>> QueryListAsync(Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Queryable().Where(whereExpression).ToListAsync(); | |||||
} | |||||
/// <summary> | |||||
/// 根据条件获取集合 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="selectExpression"></param> | |||||
/// <returns></returns> | |||||
public List<TResult> QueryList<TResult>(Expression<Func<TDocument, bool>> whereExpression, | |||||
Expression<Func<TDocument, TResult>> selectExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Queryable().Where(whereExpression).Select(selectExpression).ToList(); | |||||
} | |||||
/// <summary> | |||||
/// 根据条件获取集合 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="selectExpression"></param> | |||||
/// <returns></returns> | |||||
public Task<List<TResult>> QueryListAsync<TResult>(Expression<Func<TDocument, bool>> whereExpression, | |||||
Expression<Func<TDocument, TResult>> selectExpression) | |||||
{ | |||||
CheckCurrentCollection(); | |||||
return CurrentCollection.Queryable().Where(whereExpression).Select(selectExpression).ToListAsync(); | |||||
} | |||||
#endregion | |||||
#region 创建 查询 、索引、更新、排序 条件定义 | |||||
/// <summary> | |||||
/// 创建过滤条件定义 | |||||
/// </summary> | |||||
public FilterDefinitionBuilder<TDocument> BuilderFilter() => Builders<TDocument>.Filter; | |||||
/// <summary> | |||||
/// 创建索引条件定义 | |||||
/// </summary> | |||||
public IndexKeysDefinitionBuilder<TDocument> BuilderIndexKeys() => Builders<TDocument>.IndexKeys; | |||||
/// <summary> | |||||
/// 创建更新条件定义 | |||||
/// </summary> | |||||
public UpdateDefinitionBuilder<TDocument> BuilderUpdate() => Builders<TDocument>.Update; | |||||
/// <summary> | |||||
/// 创建排序条件定义 | |||||
/// </summary> | |||||
public SortDefinitionBuilder<TDocument> BuilderSort() => Builders<TDocument>.Sort; | |||||
/// <summary> | |||||
/// Filter | |||||
/// </summary> | |||||
public FilterDefinitionBuilder<TDocument> Filter => Builders<TDocument>.Filter; | |||||
/// <summary> | |||||
/// Update | |||||
/// </summary> | |||||
public UpdateDefinitionBuilder<TDocument> Update => Builders<TDocument>.Update; | |||||
/// <summary> | |||||
/// Sort | |||||
/// </summary> | |||||
public SortDefinitionBuilder<TDocument> Sort => Builders<TDocument>.Sort; | |||||
#endregion | |||||
} | |||||
} |
@@ -0,0 +1,49 @@ | |||||
using System.Runtime.CompilerServices; | |||||
using Microsoft.Extensions.Logging; | |||||
using MongoDB.Driver.Core.Configuration; | |||||
namespace BPA.Component.MongoClient; | |||||
public class BaseMongoDbClient<TMongoDbClient> : MongoDB.Driver.MongoClient | |||||
where TMongoDbClient : BaseMongoDbClient<TMongoDbClient> | |||||
{ | |||||
/// <summary> | |||||
/// Logger | |||||
/// </summary> | |||||
private readonly ILogger<TMongoDbClient> _logger; | |||||
/// <summary> | |||||
/// MongoConfig | |||||
/// </summary> | |||||
private static MongoConfig _config; | |||||
/// <summary> | |||||
/// CurrentDatabaseName | |||||
/// </summary> | |||||
protected internal readonly string CurrentDatabaseName; | |||||
/// <summary> | |||||
/// BaseMongoDbClient | |||||
/// </summary> | |||||
/// <param name="config"></param> | |||||
/// <param name="logger"></param> | |||||
public BaseMongoDbClient(MongoConfig config, ILogger<TMongoDbClient> logger = null) | |||||
{ | |||||
CurrentDatabaseName = config.DatabasesName; | |||||
_config = config; | |||||
_logger = logger; | |||||
} | |||||
/// <summary> | |||||
/// BuildMongoConfig | |||||
/// </summary> | |||||
/// <param name="connectionString"></param> | |||||
/// <param name="databaseName"></param> | |||||
/// <returns></returns> | |||||
protected static MongoConfig BuildMongoConfig(string connectionString, string databaseName) | |||||
{ | |||||
_config = new MongoConfig {ConnectionString = connectionString, DatabasesName = databaseName}; | |||||
return _config; | |||||
} | |||||
} |
@@ -1,425 +0,0 @@ | |||||
using System.Linq.Expressions; | |||||
using MongoDB.Driver; | |||||
using MongoDB.Driver.Linq; | |||||
namespace BPA.Component.MongoClient | |||||
{ | |||||
/// <summary> | |||||
/// MongoDB仓储接口 | |||||
/// </summary> | |||||
public interface IMGRepository<TDocument> where TDocument : new() | |||||
{ | |||||
/// <summary> | |||||
/// 当前企业(商户)Id | |||||
/// </summary> | |||||
long CorpId { get; } | |||||
/// <summary> | |||||
/// 切换企业Id | |||||
/// </summary> | |||||
/// <param name="corpId"></param> | |||||
void ChangeCorpId(long corpId); | |||||
/// <summary> | |||||
/// MongonDbProvider | |||||
/// </summary> | |||||
MongoDbProvider MongoDbProvider { get; } | |||||
/// <summary> | |||||
/// 当前MongoDB上下文 | |||||
/// </summary> | |||||
MongoDbContext CurrMongoDbContext { get; } | |||||
/// <summary> | |||||
/// 当前需要操作的文档集 | |||||
/// </summary> | |||||
IMongoCollection<TDocument> CurrentCollection { get; } | |||||
#region 插入扩展 | |||||
/// <summary> | |||||
/// 插入一个 ,等同使用:<code>IMongoCollection.InsertOne</code> | |||||
/// </summary> | |||||
/// <param name="document">文档对象</param> | |||||
/// <param name="options">插入配置选项</param> | |||||
void InsertOne(TDocument document, InsertOneOptions? options = null); | |||||
/// <summary> | |||||
/// 插入多个,等同使用: | |||||
/// <code>IMongoCollection.InsertMany(IClientSessionHandle, IEnumerable{TDocument}, InsertManyOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="documents">文档对象</param> | |||||
/// <param name="options">插入配置选项</param> | |||||
void InsertMany(IEnumerable<TDocument> documents, InsertManyOptions? options = null); | |||||
/// <summary> | |||||
/// 插入一个 ,等同使用:<code>IMongoCollection.InsertOneAsync</code> | |||||
/// </summary> | |||||
/// <param name="document">文档对象</param> | |||||
/// <param name="options">插入配置选项</param> | |||||
Task InsertOneAsync(TDocument document, InsertOneOptions options = null); | |||||
/// <summary> | |||||
/// 插入多个,等同使用: | |||||
/// <code>IMongoCollection.InsertManyAsync(IEnumerable{TDocument}, InsertManyOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="documents">文档对象</param> | |||||
/// <param name="options">插入配置选项</param> | |||||
Task InsertManyAsync(IEnumerable<TDocument> documents, InsertManyOptions options = null); | |||||
#endregion | |||||
#region 更新扩展 | |||||
/// <summary> | |||||
/// 更新满足条件的第一条数据, | |||||
/// <code>IMongoCollection.UpdateOne(FilterDefinition{TDocument}, UpdateDefinition{TDocument}, UpdateOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document"></param> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="options"></param> | |||||
UpdateResult UpdateOne(TDocument document, Expression<Func<TDocument, bool>> whereExpression, UpdateOptions options = null); | |||||
/// <summary> | |||||
/// 更新满足条件的第一条数据, | |||||
/// <code>IMongoCollection.UpdateOneAsync(FilterDefinition{TDocument}, UpdateDefinition{TDocument}, UpdateOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document"></param> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="options"></param> | |||||
Task<UpdateResult> UpdateOneAsync(TDocument document, Expression<Func<TDocument, bool>> whereExpression, | |||||
UpdateOptions options = null); | |||||
/// <summary> | |||||
/// 更新满足条件的多条数据, | |||||
/// <code>IMongoCollection.UpdateOne(FilterDefinition{TDocument}, UpdateDefinition{TDocument},UpdateOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document"></param> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="options"></param> | |||||
UpdateResult UpdateMany(TDocument document, Expression<Func<TDocument, bool>> whereExpression, UpdateOptions options = null); | |||||
/// <summary> | |||||
/// 更新满足条件的多条数据, | |||||
/// <code>IMongoCollection.UpdateOne(FilterDefinition{TDocument}, UpdateDefinition{TDocument},UpdateOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document"></param> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="options"></param> | |||||
Task<UpdateResult> UpdateManyAsync(TDocument document, Expression<Func<TDocument, bool>> whereExpression, | |||||
UpdateOptions options = null); | |||||
/// <summary> | |||||
/// 自定义字段更新 更新满足条件的第一条数据,实体键_id不允许更新 | |||||
/// </summary> | |||||
/// <param name="whereExpression">更新条件</param> | |||||
/// <param name="columnsExp">更新字段表达式:x=>new TDocument{ F1=1,F2=2 }</param> | |||||
/// <returns></returns> | |||||
UpdateResult UpdateOne(Expression<Action<TDocument>> columnsExp, Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 自定义字段更新 更新满足条件的第一条数据,实体键_id不允许更新 | |||||
/// </summary> | |||||
/// <param name="whereExpression">更新条件</param> | |||||
/// <param name="columnsExp">更新字段表达式:x=>new TDocument{ F1=1,F2=2 }</param> | |||||
/// <returns></returns> | |||||
Task<UpdateResult> UpdateOneAsync(Expression<Action<TDocument>> columnsExp, Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 自定义字段更新 更新满足条件的多条数据,实体键_id不允许更新 | |||||
/// </summary> | |||||
/// <param name="whereExpression">更新条件</param> | |||||
/// <param name="columnsExp">更新字段表达式:x=>new TDocument{ F1=1,F2=2 }</param> | |||||
/// <returns></returns> | |||||
UpdateResult UpdateMany(Expression<Action<TDocument>> columnsExp, Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 自定义字段更新 更新满足条件的多条数据,实体键_id不允许更新 | |||||
/// </summary> | |||||
/// <param name="whereExpression">更新条件</param> | |||||
/// <param name="columnsExp">更新字段表达式:x=>new TDocument{ F1=1,F2=2 }</param> | |||||
/// <returns></returns> | |||||
Task<UpdateResult> UpdateManyAsync(Expression<Action<TDocument>> columnsExp, Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 自定义更新字段和条件,更新单条符合条件的数据 | |||||
/// </summary> | |||||
/// <param name="filter"></param> | |||||
/// <param name="update"></param> | |||||
/// <param name="options"></param> | |||||
/// <returns></returns> | |||||
UpdateResult UpdateOne(FilterDefinition<TDocument> filter, UpdateDefinition<TDocument> update, UpdateOptions options = null); | |||||
/// <summary> | |||||
/// 自定义更新字段和条件,更新单条符合条件的数据 | |||||
/// </summary> | |||||
/// <param name="filter"></param> | |||||
/// <param name="update"></param> | |||||
/// <param name="options"></param> | |||||
/// <returns></returns> | |||||
Task<UpdateResult> UpdateOneAsync(FilterDefinition<TDocument> filter, UpdateDefinition<TDocument> update, | |||||
UpdateOptions options = null); | |||||
/// <summary> | |||||
/// 自定义更新字段和条件,更新条符合条件的数据 | |||||
/// </summary> | |||||
/// <param name="filter"></param> | |||||
/// <param name="update"></param> | |||||
/// <param name="options"></param> | |||||
/// <returns></returns> | |||||
UpdateResult UpdateMany(FilterDefinition<TDocument> filter, UpdateDefinition<TDocument> update, UpdateOptions options = null); | |||||
/// <summary> | |||||
/// 自定义更新字段和条件,更新条符合条件的数据 | |||||
/// </summary> | |||||
/// <param name="filter"></param> | |||||
/// <param name="update"></param> | |||||
/// <param name="options"></param> | |||||
/// <returns></returns> | |||||
Task<UpdateResult> UpdateManyAsync(FilterDefinition<TDocument> filter, UpdateDefinition<TDocument> update, | |||||
UpdateOptions options = null); | |||||
/// <summary> | |||||
/// 异步覆盖更新满足条件的第一条数据,主键字段名称必须是 Id,等同 | |||||
/// <code>IMongoCollection.ReplaceOne(FilterDefinition{TDocument}, TDocument, ReplaceOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document">文档对象对象</param> | |||||
/// <returns></returns> | |||||
ReplaceOneResult ReplaceOneById(TDocument document); | |||||
/// <summary> | |||||
/// 异步覆盖更新满足条件的第一条数据,主键字段名称必须是 Id,等同 | |||||
/// <code>IMongoCollection.ReplaceOne(FilterDefinition{TDocument}, TDocument, ReplaceOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document">文档对象对象</param> | |||||
/// <returns></returns> | |||||
Task<ReplaceOneResult> ReplaceOneByIdAsync(TDocument document); | |||||
/// <summary> | |||||
/// 异步覆盖更新满足条件的第一条数据,主键字段名称必须是 ID,等同 | |||||
/// <code>IMongoCollection.ReplaceOne(FilterDefinition{TDocument}, TDocument, ReplaceOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document">文档对象对象</param> | |||||
/// <param name="whereExpression">查询添加表达式</param> | |||||
/// <returns></returns> | |||||
ReplaceOneResult ReplaceOne(TDocument document, Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 异步覆盖更新满足条件的第一条数据,主键字段名称必须是 ID,等同 | |||||
/// <code>IMongoCollection.ReplaceOne(FilterDefinition{TDocument}, TDocument, ReplaceOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="document">文档对象对象</param> | |||||
/// <param name="whereExpression">查询添加表达式</param> | |||||
/// <returns></returns> | |||||
Task<ReplaceOneResult> ReplaceOneAsync(TDocument document, Expression<Func<TDocument, bool>> whereExpression); | |||||
#endregion | |||||
#region 删除扩展 | |||||
/// <summary> | |||||
/// 删除满足条件的第一条数据,等同于 | |||||
/// <code>IMongoCollection.DeleteOne(FilterDefinition{TDocument}, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="whereExpression">删除条件表达式</param> | |||||
DeleteResult DeleteOne(Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 删除满足条件的第一条数据,等同于 | |||||
/// <code>IMongoCollection.DeleteOne(FilterDefinition{TDocument}, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="whereExpression">删除条件表达式</param> | |||||
Task<DeleteResult> DeleteOneAsync(Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 批量删除满足条件的多条数据,等同于 | |||||
/// <code>IMongoCollection.DeleteMany(FilterDefinition{TDocument}, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="whereExpression">删除条件表达式</param> | |||||
DeleteResult DeleteMany(Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 批量删除满足条件的多条数据,等同于 | |||||
/// <code>IMongoCollection.DeleteMany(FilterDefinition{TDocument}, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <param name="whereExpression">删除条件表达式</param> | |||||
Task<DeleteResult> DeleteManyAsync(Expression<Func<TDocument, bool>> whereExpression); | |||||
#endregion | |||||
#region 查询扩展 | |||||
/// <summary> | |||||
/// 根据条件查询 | |||||
/// </summary> | |||||
/// <param name="filter"></param> | |||||
/// <param name="options"></param> | |||||
/// <returns></returns> | |||||
IFindFluent<TDocument, TDocument> Find(FilterDefinition<TDocument> filter, FindOptions options = null); | |||||
/// <summary> | |||||
/// 根据条件查询 | |||||
/// </summary> | |||||
/// <param name="filter"></param> | |||||
/// <param name="options"></param> | |||||
/// <returns></returns> | |||||
Task<IAsyncCursor<TDocument>> FindAsync(FilterDefinition<TDocument> filter, FindOptions<TDocument, TDocument> options = null); | |||||
/// <summary> | |||||
/// 可查询 <see cref="IMongoCollectionExtensions.AsQueryable{TDocument}(IMongoCollection{TDocument}, AggregateOptions)"/> | |||||
/// , 同步时用ToList, 异步时用 ToListAsync | |||||
/// </summary> | |||||
/// <returns></returns> | |||||
IMongoQueryable<TDocument> Queryable(); | |||||
/// <summary> | |||||
/// 可查询 根据条件 , 同步时用ToList, 异步时用 ToListAsync | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <returns></returns> | |||||
IMongoQueryable<TDocument> Queryable(Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 可查询 根据条件 , 同步时用ToList , 异步时用 ToListAsync | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="selectExpression"></param> | |||||
/// <returns></returns> | |||||
IMongoQueryable<TResult> Queryable<TResult>(Expression<Func<TDocument, bool>> whereExpression, | |||||
Expression<Func<TDocument, TResult>> selectExpression); | |||||
/// <summary> | |||||
/// 根据条件判断是否存在 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <returns></returns> | |||||
bool Any(Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 根据ID获取entity | |||||
/// </summary> | |||||
/// <param name="id"></param> | |||||
/// <returns></returns> | |||||
TDocument GetById(dynamic id); | |||||
/// <summary> | |||||
/// 根据ID获取entity | |||||
/// </summary> | |||||
/// <param name="id"></param> | |||||
/// <returns></returns> | |||||
Task<TDocument> GetByIdAsync(dynamic id); | |||||
/// <summary> | |||||
/// 根据ID获取entity | |||||
/// </summary> | |||||
/// <param name="id"></param> | |||||
/// <param name="selectExpression">需要返回的字段表达式</param> | |||||
/// <returns></returns> | |||||
TResult GetById<TResult>(dynamic id, Expression<Func<TDocument, TResult>> selectExpression); | |||||
/// <summary> | |||||
/// 根据条件 获取第一条数据 | |||||
/// </summary> | |||||
/// <param name="whereExpression">条件</param> | |||||
/// <param name="selectExpression">返回的新对象选择表达式</param> | |||||
/// <returns></returns> | |||||
TResult? First<TResult>(Expression<Func<TDocument, bool>> whereExpression, Expression<Func<TDocument, TResult>> selectExpression); | |||||
/// <summary> | |||||
/// 根据条件 获取第一条数据 | |||||
/// </summary> | |||||
/// <param name="whereExpression">条件</param> | |||||
/// <param name="selectExpression">返回的新对象选择表达式</param> | |||||
/// <returns></returns> | |||||
Task<TResult> FirstAsync<TResult>(Expression<Func<TDocument, bool>> whereExpression, | |||||
Expression<Func<TDocument, TResult>> selectExpression); | |||||
/// <summary> | |||||
/// 根据条件 获取第一条数据 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <returns></returns> | |||||
TDocument? First(Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 根据条件 获取第一条数据 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <returns></returns> | |||||
Task<TDocument> FirstAsync(Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 根据条件获取集合 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <returns></returns> | |||||
List<TDocument> QueryList(Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 根据条件获取集合 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <returns></returns> | |||||
Task<List<TDocument>> QueryListAsync(Expression<Func<TDocument, bool>> whereExpression); | |||||
/// <summary> | |||||
/// 根据条件获取集合 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="selectExpression"></param> | |||||
/// <returns></returns> | |||||
List<TResult> QueryList<TResult>(Expression<Func<TDocument, bool>> whereExpression, | |||||
Expression<Func<TDocument, TResult>> selectExpression); | |||||
/// <summary> | |||||
/// 根据条件获取集合 | |||||
/// </summary> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="selectExpression"></param> | |||||
/// <returns></returns> | |||||
Task<List<TResult>> QueryListAsync<TResult>(Expression<Func<TDocument, bool>> whereExpression, | |||||
Expression<Func<TDocument, TResult>> selectExpression); | |||||
#endregion | |||||
#region 创建 查询 、索引、更新、排序 条件定义 | |||||
/// <summary> | |||||
/// Filter | |||||
/// </summary> | |||||
FilterDefinitionBuilder<TDocument> Filter { get; } | |||||
/// <summary> | |||||
/// Update | |||||
/// </summary> | |||||
UpdateDefinitionBuilder<TDocument> Update { get; } | |||||
/// <summary> | |||||
/// Sort | |||||
/// </summary> | |||||
SortDefinitionBuilder<TDocument> Sort { get; } | |||||
/// <summary> | |||||
/// 创建过滤条件定义 | |||||
/// </summary> | |||||
FilterDefinitionBuilder<TDocument> BuilderFilter(); | |||||
/// <summary> | |||||
/// 创建索引条件定义 | |||||
/// </summary> | |||||
IndexKeysDefinitionBuilder<TDocument> BuilderIndexKeys(); | |||||
/// <summary> | |||||
/// 创建更新条件定义 | |||||
/// </summary> | |||||
UpdateDefinitionBuilder<TDocument> BuilderUpdate(); | |||||
/// <summary> | |||||
/// 创建排序条件定义 | |||||
/// </summary> | |||||
SortDefinitionBuilder<TDocument> BuilderSort(); | |||||
#endregion | |||||
} | |||||
} |
@@ -3,20 +3,15 @@ | |||||
/// <summary> | /// <summary> | ||||
/// MongoDb配置 | /// MongoDb配置 | ||||
/// </summary> | /// </summary> | ||||
public class MongoDbConfig | |||||
public class MongoConfig | |||||
{ | { | ||||
/// <summary> | |||||
/// 别名,同一种的业务数据库的可以有多个,但是每个的别名都不能相同 | |||||
/// </summary> | |||||
public string Alias { set; get; } | |||||
/// <summary> | /// <summary> | ||||
/// 连接字符串 | /// 连接字符串 | ||||
/// </summary> | /// </summary> | ||||
public string ConnectionString { set; get; } | public string ConnectionString { set; get; } | ||||
/// <summary> | /// <summary> | ||||
/// 数据库名称 | |||||
/// 数据库名称 | 可空 | |||||
/// </summary> | /// </summary> | ||||
public string DatabasesName { set; get; } | public string DatabasesName { set; get; } | ||||
} | } |
@@ -1,177 +0,0 @@ | |||||
using BPA.Component.MongoClient.Conventions; | |||||
using MongoDB.Bson; | |||||
using MongoDB.Bson.Serialization; | |||||
using MongoDB.Bson.Serialization.Conventions; | |||||
using MongoDB.Bson.Serialization.Serializers; | |||||
using MongoDB.Driver; | |||||
using Newtonsoft.Json.Linq; | |||||
namespace BPA.Component.MongoClient | |||||
{ | |||||
/// <summary> | |||||
/// MongoDbContext | |||||
/// </summary> | |||||
public class MongoDbContext : IDisposable | |||||
{ | |||||
static MongoDbContext() | |||||
{ | |||||
var serializer = new DateTimeSerializer(DateTimeKind.Local, BsonType.DateTime); | |||||
BsonSerializer.RegisterSerializer(typeof(DateTime), serializer); | |||||
BsonSerializer.RegisterSerializer(typeof(JObject), new JObjectSerializer()); | |||||
BsonSerializer.RegisterSerializer(typeof(JArray), new JArraySerializer()); | |||||
BsonSerializer.RegisterSerializer(typeof(Dictionary<string, object>), new DictionarySerializerSerializer()); | |||||
BsonSerializer.RegisterSerializer(typeof(decimal), new DecimalSerializer(BsonType.Decimal128)); | |||||
BsonSerializer.RegisterSerializer(typeof(decimal?), | |||||
new NullableSerializer<decimal>(new DecimalSerializer(BsonType.Decimal128))); | |||||
BsonSerializer.RegisterSerializationProvider(new BPASerializationProvider()); | |||||
ConventionRegistry.Register("IgnoreExtraElements", | |||||
new ConventionPack | |||||
{ | |||||
new IgnoreExtraElementsConvention(true), new BPACamelCaseElementNameConvention(), | |||||
new EnumRepresentationConvention(BsonType.String) | |||||
}, _ => true); | |||||
} | |||||
/// <summary> | |||||
/// 当前连接 | |||||
/// </summary> | |||||
public readonly IMongoClient MongoClient; | |||||
/// <summary> | |||||
/// 当前操作数据库 | |||||
/// </summary> | |||||
public readonly IMongoDatabase Database; | |||||
/// <summary> | |||||
/// 企业ID | |||||
/// </summary> | |||||
public readonly long CorpId; | |||||
/// <summary> | |||||
/// 构造方法 | |||||
/// </summary> | |||||
/// <param name="corpId"></param> | |||||
/// <param name="mongoClient"></param> | |||||
/// <param name="database"></param> | |||||
public MongoDbContext(long corpId, IMongoClient mongoClient, IMongoDatabase database) | |||||
{ | |||||
CorpId = corpId; | |||||
MongoClient = mongoClient; | |||||
Database = database; | |||||
} | |||||
/// <summary> | |||||
/// 检查数据库是否存在 | |||||
/// </summary> | |||||
/// <param name="mongoClient"></param> | |||||
/// <param name="databaseName"></param> | |||||
/// <returns></returns> | |||||
public bool DatabaseExists(MongoDB.Driver.MongoClient mongoClient, string databaseName) | |||||
{ | |||||
try | |||||
{ | |||||
var dbNames = mongoClient.ListDatabases().ToList().Select(db => db.GetValue("name").AsString); | |||||
return dbNames.Contains(databaseName); | |||||
} | |||||
catch | |||||
{ | |||||
return true; | |||||
} | |||||
} | |||||
/// <summary> | |||||
/// 检查文档集是否存在 | |||||
/// </summary> | |||||
/// <param name="mongoDatabase"></param> | |||||
/// <param name="collectionName"></param> | |||||
/// <returns></returns> | |||||
public bool CollectionExists(IMongoDatabase mongoDatabase, string collectionName) | |||||
{ | |||||
var options = new ListCollectionsOptions | |||||
{ | |||||
Filter = Builders<BsonDocument>.Filter.Eq("name", collectionName) | |||||
}; | |||||
return mongoDatabase.ListCollections(options).ToEnumerable().Any(); | |||||
} | |||||
/// <summary> | |||||
/// 获取文档集接口 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <param name="collectionName"></param> | |||||
/// <param name="settings"></param> | |||||
/// <returns></returns> | |||||
public IMongoCollection<TDocument> GetCollection<TDocument>(string collectionName, | |||||
MongoCollectionSettings? settings) | |||||
{ | |||||
return Database.GetCollection<TDocument>(collectionName, settings); | |||||
} | |||||
/// <summary> | |||||
/// 根据企业名称和文档集类型构建 文档集名称 | |||||
/// <code> | |||||
/// 返回文档集格式:{typeof(TDocument).Name}{corpId}, | |||||
/// </code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <param name="corpId">企业ID</param> | |||||
/// <returns></returns> | |||||
public string BuildCollectionName<TDocument>(long corpId) | |||||
{ | |||||
return $"{typeof(TDocument).Name}{corpId}"; | |||||
} | |||||
/// <summary> | |||||
/// 根据企业ID获取,获取文档集接口 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <param name="settings"></param> | |||||
/// <returns></returns> | |||||
public IMongoCollection<TDocument> GetCollection<TDocument>(MongoCollectionSettings? settings) | |||||
{ | |||||
var collectionName = BuildCollectionName<TDocument>(CorpId); | |||||
return GetCollection<TDocument>(collectionName, settings); | |||||
} | |||||
/// <summary> | |||||
/// 检查文档集是否存在 | |||||
/// </summary> | |||||
/// <param name="collectionName">文档集名称</param> | |||||
/// <returns></returns> | |||||
public bool CollectionExists(string collectionName) | |||||
{ | |||||
var options = new ListCollectionsOptions | |||||
{ | |||||
Filter = Builders<BsonDocument>.Filter.Eq("name", collectionName) | |||||
}; | |||||
return Database.ListCollections(options).ToEnumerable().Any(); | |||||
} | |||||
/// <summary> | |||||
/// 清空文档集数据 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
public IMongoCollection<TDocument> ClearCollection<TDocument>() | |||||
{ | |||||
var collectionName = BuildCollectionName<TDocument>(CorpId); | |||||
//删除文档集 | |||||
Database.DropCollection(collectionName); | |||||
if (!CollectionExists(Database, collectionName)) | |||||
{ | |||||
this.CreateCollection<TDocument>(collectionName); | |||||
} | |||||
return Database.GetCollection<TDocument>(collectionName); | |||||
} | |||||
/// <summary> | |||||
/// 销毁 | |||||
/// </summary> | |||||
public void Dispose() | |||||
{ | |||||
} | |||||
} | |||||
} |
@@ -1,714 +0,0 @@ | |||||
using System.Linq.Expressions; | |||||
using MongoDB.Bson; | |||||
using MongoDB.Driver; | |||||
using MongoDB.Driver.Linq; | |||||
namespace BPA.Component.MongoClient | |||||
{ | |||||
/// <summary> | |||||
/// MongoDB 文件集扩展类 | |||||
/// </summary> | |||||
public static class MongoDbExtensions | |||||
{ | |||||
/// <summary> | |||||
/// 聚合默认选项 | |||||
/// </summary> | |||||
public static readonly AggregateOptions DefaultAggregateOptions = new AggregateOptions {AllowDiskUse = true}; | |||||
#region 文档集操作扩展 | |||||
/// <summary> | |||||
/// 创建文档集 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档集类型</typeparam> | |||||
/// <param name="mongoDbContent"></param> | |||||
/// <param name="collectionName">文档集名称</param> | |||||
/// <param name="options"></param> | |||||
public static void CreateCollection<TDocument>(this MongoDbContext mongoDbContent, string collectionName, | |||||
CreateCollectionOptions options = null) | |||||
{ | |||||
mongoDbContent.Database.CreateCollection(collectionName, options); | |||||
} | |||||
/// <summary> | |||||
/// 创建文档集索引,倒序 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <param name="collection"></param> | |||||
/// <param name="indexFields"></param> | |||||
/// <param name="model"></param> | |||||
/// <param name="options"></param> | |||||
public static void CreateIndex<TDocument>(this IMongoCollection<TDocument> collection, string[] indexFields, | |||||
CreateIndexModel<TDocument> model, CreateOneIndexOptions options = null) | |||||
{ | |||||
if (indexFields == null) | |||||
return; | |||||
var indexKeys = Builders<TDocument>.IndexKeys; | |||||
IndexKeysDefinition<TDocument> keys = null; | |||||
if (indexFields.Length > 0) | |||||
{ | |||||
keys = indexKeys.Descending(indexFields[0]); | |||||
} | |||||
for (var i = 1; i < indexFields.Length; i++) | |||||
{ | |||||
var strIndex = indexFields[i]; | |||||
keys = keys.Descending(strIndex); | |||||
} | |||||
if (keys != null) | |||||
{ | |||||
collection.Indexes.CreateOne(model, options); | |||||
} | |||||
} | |||||
#endregion | |||||
#region 插入扩展 | |||||
/// <summary> | |||||
/// 插入一个 ,等同使用:<code>IMongoCollection.InsertOne</code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档集类型</typeparam> | |||||
/// <param name="collection">文档集</param> | |||||
/// <param name="document">文档对象</param> | |||||
/// <param name="options">插入配置选项</param> | |||||
public static void InsertOne<TDocument>(this IMongoCollection<TDocument> collection, TDocument document, | |||||
InsertOneOptions options = null) | |||||
{ | |||||
collection.InsertOne(document, options, default); | |||||
} | |||||
/// <summary> | |||||
/// 插入多个,等同使用: | |||||
/// <code>IMongoCollection.InsertMany(IClientSessionHandle, IEnumerable{TDocument}, InsertManyOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档集类型</typeparam> | |||||
/// <param name="collection">文档集</param> | |||||
/// <param name="documents">文档对象</param> | |||||
/// <param name="options">插入配置选项</param> | |||||
public static void InsertMany<TDocument>(this IMongoCollection<TDocument> collection, | |||||
IEnumerable<TDocument> documents, | |||||
InsertManyOptions options = null) | |||||
{ | |||||
collection.InsertMany(documents, options, default); | |||||
} | |||||
#endregion | |||||
#region 更新扩展 | |||||
/// <summary> | |||||
/// 构建更新操作定义 | |||||
/// </summary> | |||||
/// <param name="document">bsondocument文档</param> | |||||
/// <param name="parent"></param> | |||||
/// <returns></returns> | |||||
private static List<UpdateDefinition<BsonDocument>> BuildUpdateDefinition(BsonDocument document, string parent) | |||||
{ | |||||
var updates = new List<UpdateDefinition<BsonDocument>>(); | |||||
foreach (var element in document.Elements) | |||||
{ | |||||
var key = parent == null ? element.Name : $"{parent}.{element.Name}"; | |||||
//子元素是对象 | |||||
if (element.Value.IsBsonDocument) | |||||
{ | |||||
updates.AddRange(BuildUpdateDefinition(element.Value.ToBsonDocument(), key)); | |||||
} | |||||
//子元素是对象数组 | |||||
else if (element.Value.IsBsonArray) | |||||
{ | |||||
var arrayDocs = element.Value.AsBsonArray; | |||||
var i = 0; | |||||
foreach (var doc in arrayDocs) | |||||
{ | |||||
if (doc.IsBsonDocument) | |||||
{ | |||||
updates.AddRange(BuildUpdateDefinition(doc.ToBsonDocument(), key + $".{i}")); | |||||
} | |||||
else | |||||
{ | |||||
updates.Add(Builders<BsonDocument>.Update.Set(f => f[key], element.Value)); | |||||
continue; | |||||
} | |||||
i++; | |||||
} | |||||
} | |||||
//子元素是其他 | |||||
else | |||||
{ | |||||
updates.Add(Builders<BsonDocument>.Update.Set(f => f[key], element.Value)); | |||||
} | |||||
} | |||||
return updates; | |||||
} | |||||
/// <summary> | |||||
/// 更新满足条件的第一条数据, | |||||
/// <code>IMongoCollection.UpdateOne(FilterDefinition{TDocument}, UpdateDefinition{TDocument}, UpdateOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <param name="collection"></param> | |||||
/// <param name="document"></param> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="options"></param> | |||||
public static UpdateResult UpdateOne<TDocument>(this IMongoCollection<TDocument> collection, | |||||
TDocument document, | |||||
Expression<Func<TDocument, bool>> whereExpression, | |||||
UpdateOptions options = null) | |||||
{ | |||||
var bsonDocument = document.ToBsonDocument(); | |||||
bsonDocument.Remove("_id"); | |||||
BsonDocument update = new BsonDocument | |||||
{ | |||||
{"$set", bsonDocument} | |||||
}; | |||||
return collection.UpdateOne(whereExpression, update, options); | |||||
} | |||||
/// <summary> | |||||
/// 更新满足条件的第一条数据, | |||||
/// <code>IMongoCollection.UpdateOne(FilterDefinition{TDocument}, UpdateDefinition{TDocument}, UpdateOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <param name="collection"></param> | |||||
/// <param name="document"></param> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="options"></param> | |||||
public static Task<UpdateResult> UpdateOneAsync<TDocument>(this IMongoCollection<TDocument> collection, | |||||
TDocument document, | |||||
Expression<Func<TDocument, bool>> whereExpression, | |||||
UpdateOptions options = null) | |||||
{ | |||||
var bsonDocument = document.ToBsonDocument(); | |||||
bsonDocument.Remove("_id"); | |||||
BsonDocument update = new BsonDocument | |||||
{ | |||||
{"$set", bsonDocument} | |||||
}; | |||||
return collection.UpdateOneAsync(whereExpression, update, options); | |||||
} | |||||
/// <summary> | |||||
/// 更新满足条件的多条数据, | |||||
/// <code>IMongoCollection.UpdateOne(FilterDefinition{TDocument}, UpdateDefinition{TDocument},UpdateOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <param name="collection"></param> | |||||
/// <param name="document"></param> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="options"></param> | |||||
public static UpdateResult UpdateMany<TDocument>(this IMongoCollection<TDocument> collection, | |||||
TDocument document, | |||||
Expression<Func<TDocument, bool>> whereExpression, | |||||
UpdateOptions options = null) | |||||
{ | |||||
var bsonDocument = document.ToBsonDocument(); | |||||
bsonDocument.Remove("_id"); | |||||
BsonDocument update = new BsonDocument | |||||
{ | |||||
{"$set", bsonDocument} | |||||
}; | |||||
return collection.UpdateMany(whereExpression, update, options); | |||||
} | |||||
/// <summary> | |||||
/// 更新满足条件的多条数据, | |||||
/// <code>IMongoCollection.UpdateOne(FilterDefinition{TDocument}, UpdateDefinition{TDocument},UpdateOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <param name="collection"></param> | |||||
/// <param name="document"></param> | |||||
/// <param name="whereExpression"></param> | |||||
/// <param name="options"></param> | |||||
public static Task<UpdateResult> UpdateManyAsync<TDocument>(this IMongoCollection<TDocument> collection, | |||||
TDocument document, | |||||
Expression<Func<TDocument, bool>> whereExpression, | |||||
UpdateOptions options = null) | |||||
{ | |||||
var bsonDocument = document.ToBsonDocument(); | |||||
bsonDocument.Remove("_id"); | |||||
BsonDocument update = new BsonDocument | |||||
{ | |||||
{"$set", bsonDocument} | |||||
}; | |||||
return collection.UpdateManyAsync(whereExpression, update, options); | |||||
} | |||||
/// <summary> | |||||
/// 根据更新字段表达式组装UpdateDefinitioons | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <param name="param"></param> | |||||
/// <returns></returns> | |||||
private static List<UpdateDefinition<TDocument>> BuildUpdateDefinitioonsByExpression<TDocument>( | |||||
MemberInitExpression param) | |||||
{ | |||||
var fieldList = new List<UpdateDefinition<TDocument>>(); | |||||
foreach (var item in param.Bindings) | |||||
{ | |||||
var propertyName = item.Member.Name; | |||||
if (propertyName == "_id" || propertyName == "Id") | |||||
continue; | |||||
object propertyValue = null; | |||||
if (!(item is MemberAssignment memberAssignment)) | |||||
continue; | |||||
if (memberAssignment.Expression.NodeType == ExpressionType.Constant) | |||||
{ | |||||
if (memberAssignment.Expression is ConstantExpression constantExpression) | |||||
propertyValue = constantExpression.Value; | |||||
} | |||||
else | |||||
{ | |||||
if (memberAssignment.Expression is MethodCallExpression methodCallExpression2) | |||||
{ | |||||
if (methodCallExpression2.Method.Name == "AddToSet") | |||||
{ | |||||
var argument = methodCallExpression2.Arguments[1]; | |||||
if (argument is ConstantExpression constantExpression) | |||||
{ | |||||
fieldList.Add( | |||||
Builders<TDocument>.Update.AddToSet(propertyName, constantExpression.Value)); | |||||
} | |||||
else | |||||
{ | |||||
propertyValue = Expression.Lambda(argument, null).Compile().DynamicInvoke(); | |||||
if (propertyValue is IEnumerable<object> lsArg) | |||||
{ | |||||
fieldList.Add(Builders<TDocument>.Update.AddToSetEach(propertyName, lsArg)); | |||||
} | |||||
else | |||||
{ | |||||
fieldList.Add(Builders<TDocument>.Update.AddToSet(propertyName, propertyValue)); | |||||
} | |||||
} | |||||
continue; | |||||
} | |||||
} | |||||
} | |||||
propertyValue = Expression.Lambda(memberAssignment.Expression, null).Compile().DynamicInvoke(); | |||||
fieldList.Add(Builders<TDocument>.Update.Set(propertyName, propertyValue)); | |||||
} | |||||
return fieldList; | |||||
} | |||||
/// <summary> | |||||
/// 自定义字段更新 更新满足条件的第一条数据,实体键_id不允许更新 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">数据库实体类型</typeparam> | |||||
/// <param name="collection"></param> | |||||
/// <param name="whereExpression">更新条件</param> | |||||
/// <param name="columnsExp">更新字段表达式:x=>new TDocument{ F1=1,F2=2 }</param> | |||||
/// <returns></returns> | |||||
public static UpdateResult UpdateOne<TDocument>(this IMongoCollection<TDocument> collection, | |||||
Expression<Action<TDocument>> columnsExp, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
if (!(columnsExp.Body is MemberInitExpression param)) | |||||
throw new ArgumentException($"{nameof(columnsExp)}错误,更新字段表达式示例: x=>new TDocument{{ F1 = 1,F2 = 2 }}"); | |||||
List<UpdateDefinition<TDocument>> fieldList = BuildUpdateDefinitioonsByExpression<TDocument>(param); | |||||
return collection.UpdateOne(whereExpression, Builders<TDocument>.Update.Combine(fieldList)); | |||||
} | |||||
/// <summary> | |||||
/// 自定义字段更新 更新满足条件的第一条数据,实体键_id不允许更新 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">数据库实体类型</typeparam> | |||||
/// <param name="collection"></param> | |||||
/// <param name="whereExpression">更新条件</param> | |||||
/// <param name="columnsExp">更新字段表达式:x=>new TDocument{ F1=1,F2=2 }</param> | |||||
/// <returns></returns> | |||||
public static Task<UpdateResult> UpdateOneAsync<TDocument>(this IMongoCollection<TDocument> collection, | |||||
Expression<Action<TDocument>> columnsExp, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
if (!(columnsExp.Body is MemberInitExpression param)) | |||||
throw new ArgumentException($"{nameof(columnsExp)}错误,更新字段表达式示例: x=>new TDocument{{ F1 = 1,F2 = 2 }}"); | |||||
List<UpdateDefinition<TDocument>> fieldList = BuildUpdateDefinitioonsByExpression<TDocument>(param); | |||||
return collection.UpdateOneAsync(whereExpression, Builders<TDocument>.Update.Combine(fieldList)); | |||||
} | |||||
/// <summary> | |||||
/// 自定义字段更新 更新满足条件的多条数据,实体键_id不允许更新 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">数据库实体类型</typeparam> | |||||
/// <param name="collection"></param> | |||||
/// <param name="whereExpression">更新条件</param> | |||||
/// <param name="columnsExp">更新字段表达式:x=>new TDocument{ F1=1,F2=2 }</param> | |||||
/// <returns></returns> | |||||
public static UpdateResult UpdateMany<TDocument>(this IMongoCollection<TDocument> collection, | |||||
Expression<Action<TDocument>> columnsExp, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
if (!(columnsExp.Body is MemberInitExpression param)) | |||||
throw new ArgumentException($"{nameof(columnsExp)}错误,更新字段表达式示例: x=>new TDocument{{ F1 = 1,F2 = 2 }}"); | |||||
List<UpdateDefinition<TDocument>> fieldList = BuildUpdateDefinitioonsByExpression<TDocument>(param); | |||||
return collection.UpdateMany(whereExpression, Builders<TDocument>.Update.Combine(fieldList)); | |||||
} | |||||
/// <summary> | |||||
/// 自定义字段更新 更新满足条件的多条数据,实体键_id不允许更新 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">数据库实体类型</typeparam> | |||||
/// <param name="collection"></param> | |||||
/// <param name="whereExpression">更新条件</param> | |||||
/// <param name="columnsExp">更新字段表达式:x=>new TDocument{ F1=1,F2=2 }</param> | |||||
/// <returns></returns> | |||||
public static Task<UpdateResult> UpdateManyAsync<TDocument>(this IMongoCollection<TDocument> collection, | |||||
Expression<Action<TDocument>> columnsExp, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
if (!(columnsExp.Body is MemberInitExpression param)) | |||||
throw new ArgumentException($"{nameof(columnsExp)}错误,更新字段表达式示例: x=>new TDocument{{ F1 = 1,F2 = 2 }}"); | |||||
List<UpdateDefinition<TDocument>> fieldList = BuildUpdateDefinitioonsByExpression<TDocument>(param); | |||||
return collection.UpdateManyAsync(whereExpression, Builders<TDocument>.Update.Combine(fieldList)); | |||||
} | |||||
/// <summary> | |||||
/// 异步覆盖更新满足条件的第一条数据,主键字段名称必须是 Id,等同 | |||||
/// <code>IMongoCollection.ReplaceOne(FilterDefinition{TDocument}, TDocument, ReplaceOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档对象类型</typeparam> | |||||
/// <param name="collection">文档集操作接口</param> | |||||
/// <param name="document">文档对象对象</param> | |||||
/// <returns></returns> | |||||
public static ReplaceOneResult ReplaceOneById<TDocument>(this IMongoCollection<TDocument> collection, | |||||
TDocument document) | |||||
{ | |||||
var id = new ObjectId(typeof(TDocument).GetProperty("Id").GetValue(document).ToString()); | |||||
return collection.ReplaceOne(new BsonDocument("_id", id), document); | |||||
} | |||||
/// <summary> | |||||
/// 异步覆盖更新满足条件的第一条数据,主键字段名称必须是 Id,等同 | |||||
/// <code>IMongoCollection.ReplaceOne(FilterDefinition{TDocument}, TDocument, ReplaceOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档对象类型</typeparam> | |||||
/// <param name="collection">文档集操作接口</param> | |||||
/// <param name="document">文档对象对象</param> | |||||
/// <returns></returns> | |||||
public static Task<ReplaceOneResult> ReplaceOneByIdAsync<TDocument>(this IMongoCollection<TDocument> collection, | |||||
TDocument document) | |||||
{ | |||||
var id = new ObjectId(typeof(TDocument).GetProperty("Id").GetValue(document).ToString()); | |||||
return collection.ReplaceOneAsync(new BsonDocument("_id", id), document); | |||||
} | |||||
/// <summary> | |||||
/// 异步覆盖更新满足条件的第一条数据,主键字段名称必须是 ID,等同 | |||||
/// <code>IMongoCollection.ReplaceOne(FilterDefinition{TDocument}, TDocument, ReplaceOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档对象类型</typeparam> | |||||
/// <param name="collection">文档集操作接口</param> | |||||
/// <param name="document">文档对象对象</param> | |||||
/// <param name="whereExpression">查询添加表达式</param> | |||||
/// <returns></returns> | |||||
public static ReplaceOneResult ReplaceOne<TDocument>(this IMongoCollection<TDocument> collection, | |||||
TDocument document, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
return collection.ReplaceOne(whereExpression, document); | |||||
} | |||||
/// <summary> | |||||
/// 异步覆盖更新满足条件的第一条数据,主键字段名称必须是 ID,等同 | |||||
/// <code>IMongoCollection.ReplaceOne(FilterDefinition{TDocument}, TDocument, ReplaceOptions, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档对象类型</typeparam> | |||||
/// <param name="collection">文档集操作接口</param> | |||||
/// <param name="document">文档对象对象</param> | |||||
/// <param name="whereExpression">查询添加表达式</param> | |||||
/// <returns></returns> | |||||
public static Task<ReplaceOneResult> ReplaceOneAsync<TDocument>(this IMongoCollection<TDocument> collection, | |||||
TDocument document, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
return collection.ReplaceOneAsync(whereExpression, document); | |||||
} | |||||
#endregion | |||||
#region 删除扩展 | |||||
/// <summary> | |||||
/// 删除满足条件的第一条数据,等同于 | |||||
/// <code>IMongoCollection.DeleteOne(FilterDefinition{TDocument}, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档对象类型</typeparam> | |||||
/// <param name="collection">文档集操作接口</param> | |||||
/// <param name="whereExpression">删除条件表达式</param> | |||||
public static DeleteResult DeleteOne<TDocument>(this IMongoCollection<TDocument> collection, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
return collection.DeleteOne(whereExpression, null, default); | |||||
} | |||||
/// <summary> | |||||
/// 批量删除满足条件的多条数据,等同于 | |||||
/// <code>IMongoCollection.DeleteMany(FilterDefinition{TDocument}, CancellationToken)</code> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档对象类型</typeparam> | |||||
/// <param name="collection">文档集操作接口</param> | |||||
/// <param name="whereExpression">删除条件表达式</param> | |||||
public static DeleteResult DeleteMany<TDocument>(this IMongoCollection<TDocument> collection, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
return collection.DeleteMany(whereExpression, null, default); | |||||
} | |||||
#endregion | |||||
#region 查询扩展 | |||||
/// <summary> | |||||
/// AggregateWithDefautSortOption | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <param name="collection"></param> | |||||
/// <param name="optionsAction"></param> | |||||
/// <returns></returns> | |||||
public static IAggregateFluent<TDocument> AggregateWithDefautSortOption<TDocument>( | |||||
this IMongoCollection<TDocument> collection, | |||||
Action<AggregateOptions> optionsAction = null) | |||||
{ | |||||
var options = new AggregateOptions | |||||
{ | |||||
Collation = new Collation(locale: "zh", numericOrdering: true), | |||||
AllowDiskUse = true | |||||
}; | |||||
if (optionsAction != null) | |||||
optionsAction(options); | |||||
return collection.Aggregate(options); | |||||
} | |||||
/// <summary> | |||||
/// 可查询 <see cref="IMongoCollectionExtensions.AsQueryable{TDocument}(IMongoCollection{TDocument}, AggregateOptions)"/> | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <param name="collection"></param> | |||||
/// <returns></returns> | |||||
public static IMongoQueryable<TDocument> Queryable<TDocument>(this IMongoCollection<TDocument> collection) | |||||
{ | |||||
return collection.AsQueryable(DefaultAggregateOptions); | |||||
} | |||||
/// <summary> | |||||
/// 分页查询,统计总共多少条 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档集类型</typeparam> | |||||
/// <param name="queryable">可查询器</param> | |||||
/// <param name="pageIndex">页码,第几页,默认1</param> | |||||
/// <param name="pageSize">每页条数,默认10</param> | |||||
/// <param name="total">总共多少条</param> | |||||
/// <returns></returns> | |||||
public static List<TDocument> Pagination<TDocument>(this IQueryable<TDocument> queryable, int pageIndex, | |||||
int pageSize, | |||||
out int total) | |||||
{ | |||||
pageIndex = pageIndex < 0 ? 1 : pageIndex; | |||||
pageSize = pageSize < 0 ? 10 : pageSize; | |||||
total = queryable.Count(); | |||||
return queryable.Skip((pageIndex - 1) * pageSize).Take(pageSize).ToList(); | |||||
} | |||||
/// <summary> | |||||
/// 分页查询,统计总共多少条,可以根据查询新对象的表达式,返回新对象集合 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档集类型</typeparam> | |||||
/// <typeparam name="TNewResult">新结构类型</typeparam> | |||||
/// <param name="queryable">可查询器</param> | |||||
/// <param name="selector">查询func,查询返回新对象的表达式</param> | |||||
/// <param name="pageIndex">页码,第几页,默认1</param> | |||||
/// <param name="pageSize">每页条数,默认10</param> | |||||
/// <param name="total">总共多少条</param> | |||||
/// <returns></returns> | |||||
public static List<TNewResult> Pagination<TDocument, TNewResult>(this IQueryable<TDocument> queryable, | |||||
Expression<Func<TDocument, TNewResult>> selector, int pageIndex, int pageSize, out int total) | |||||
{ | |||||
pageIndex = pageIndex < 0 ? 1 : pageIndex; | |||||
pageSize = pageSize < 0 ? 10 : pageSize; | |||||
total = queryable.Count(); | |||||
return queryable.Skip((pageIndex - 1) * pageSize).Take(pageSize).Select(selector).ToList(); | |||||
} | |||||
/// <summary> | |||||
/// 分页查询 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档集类型</typeparam> | |||||
/// <param name="queryable">可查询器</param> | |||||
/// <param name="pageIndex">页码,第几页,默认1</param> | |||||
/// <param name="pageSize">每页条数,默认10</param> | |||||
/// <returns></returns> | |||||
public static List<TDocument> Pagination<TDocument>(this IQueryable<TDocument> queryable, int pageIndex, | |||||
int pageSize) | |||||
{ | |||||
pageIndex = pageIndex < 0 ? 1 : pageIndex; | |||||
pageSize = pageSize < 0 ? 10 : pageSize; | |||||
return queryable.Skip((pageIndex - 1) * pageSize).Take(pageSize).ToList(); | |||||
} | |||||
/// <summary> | |||||
/// 分页查询,可以根据查询新对象的表达式,返回新对象集合 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档集类型</typeparam> | |||||
/// <typeparam name="TNewResult">新结构类型</typeparam> | |||||
/// <param name="queryable">可查询器</param> | |||||
/// <param name="selector">查询func,查询返回新对象的表达式</param> | |||||
/// <param name="pageIndex">页码,第几页,默认1</param> | |||||
/// <param name="pageSize">每页条数,默认10</param> | |||||
/// <returns></returns> | |||||
public static List<TNewResult> Pagination<TDocument, TNewResult>(this IMongoQueryable<TDocument> queryable, | |||||
Expression<Func<TDocument, TNewResult>> selector, int pageIndex, int pageSize) | |||||
{ | |||||
pageIndex = pageIndex < 0 ? 1 : pageIndex; | |||||
pageSize = pageSize < 0 ? 10 : pageSize; | |||||
return queryable.Skip((pageIndex - 1) * pageSize).Take(pageSize).Select(selector).ToList(); | |||||
} | |||||
/// <summary> | |||||
/// 当condition为true,才会执行where表达式里面的条件 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档集类型</typeparam> | |||||
/// <param name="queryable">可查询器</param> | |||||
/// <param name="beforeCondition">前置条件</param> | |||||
/// <param name="whereExpression">where表达式</param> | |||||
/// <returns></returns> | |||||
public static IMongoQueryable<TDocument> WhereIF<TDocument>(this IMongoQueryable<TDocument> queryable, | |||||
bool beforeCondition, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
if (beforeCondition) | |||||
return queryable.Where(whereExpression); | |||||
return queryable; | |||||
} | |||||
/// <summary> | |||||
/// 当condition为true,才会执行where表达式里面的条件 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument">文档集类型</typeparam> | |||||
/// <param name="queryable">可查询器</param> | |||||
/// <param name="beforeCondition">前置条件</param> | |||||
/// <param name="whereExpression">where表达式</param> | |||||
/// <returns></returns> | |||||
public static IQueryable<TDocument> WhereIF<TDocument>(this IQueryable<TDocument> queryable, | |||||
bool beforeCondition, | |||||
Expression<Func<TDocument, bool>> whereExpression) | |||||
{ | |||||
if (beforeCondition) | |||||
return queryable.Where(whereExpression); | |||||
return queryable; | |||||
} | |||||
/// <summary> | |||||
/// 根据selectNewResultExp 表达式返回新的查询结果,最终要执行 必须ToList、Single、 Any | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <typeparam name="TProjection"></typeparam> | |||||
/// <typeparam name="TNewResult"></typeparam> | |||||
/// <param name="find"></param> | |||||
/// <param name="selectNewResultExp"></param> | |||||
/// <returns></returns> | |||||
public static IFindFluent<TDocument, TNewResult> As<TDocument, TProjection, TNewResult>( | |||||
this IFindFluent<TDocument, TProjection> find, | |||||
Expression<Func<TDocument, TNewResult>> selectNewResultExp) | |||||
{ | |||||
return find.Project(selectNewResultExp); | |||||
} | |||||
/// <summary> | |||||
/// 根据selectNewResultExp 表达式返回新的查询结果,最终要执行 必须ToList、Single、 Any | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <typeparam name="TProjection"></typeparam> | |||||
/// <typeparam name="TNewResult"></typeparam> | |||||
/// <param name="find"></param> | |||||
/// <param name="selectNewResultExp"></param> | |||||
/// <returns></returns> | |||||
public static IFindFluent<TDocument, TNewResult> Select<TDocument, TProjection, TNewResult>( | |||||
this IFindFluent<TDocument, TProjection> find, | |||||
Expression<Func<TDocument, TNewResult>> selectNewResultExp) | |||||
{ | |||||
return find.Project(selectNewResultExp); | |||||
} | |||||
#endregion | |||||
#region 创建 查询 、索引、更新、排序 条件定义 | |||||
/// <summary> | |||||
/// 创建过滤条件定义 | |||||
/// </summary> | |||||
/// <param name="collection"></param> | |||||
public static FilterDefinitionBuilder<TDocument> BuilderFilter<TDocument>( | |||||
this IMongoCollection<TDocument> collection) | |||||
{ | |||||
return Builders<TDocument>.Filter; | |||||
} | |||||
/// <summary> | |||||
/// 创建索引条件定义 | |||||
/// </summary> | |||||
/// <param name="collection"></param> | |||||
public static IndexKeysDefinitionBuilder<TDocument> BuilderIndexKeys<TDocument>( | |||||
this IMongoCollection<TDocument> collection) | |||||
{ | |||||
return Builders<TDocument>.IndexKeys; | |||||
} | |||||
/// <summary> | |||||
/// 创建更新条件定义 | |||||
/// </summary> | |||||
/// <param name="collection"></param> | |||||
public static UpdateDefinitionBuilder<TDocument> BuilderUpdate<TDocument>( | |||||
this IMongoCollection<TDocument> collection) | |||||
{ | |||||
return Builders<TDocument>.Update; | |||||
} | |||||
/// <summary> | |||||
/// 创建排序条件定义 | |||||
/// </summary> | |||||
/// <param name="collection"></param> | |||||
public static SortDefinitionBuilder<TDocument> BuilderSort<TDocument>( | |||||
this IMongoCollection<TDocument> collection) | |||||
{ | |||||
return Builders<TDocument>.Sort; | |||||
} | |||||
#endregion | |||||
/// <summary> | |||||
/// AddToSet 追加到数组 | |||||
/// </summary> | |||||
/// <typeparam name="T"></typeparam> | |||||
/// <param name="source"></param> | |||||
/// <param name="item"></param> | |||||
/// <returns></returns> | |||||
public static List<T> AddToSet<T>(this List<T> source, T item) | |||||
{ | |||||
return new List<T> {item}; | |||||
} | |||||
/// <summary> | |||||
/// AddToSet 追加到数组 | |||||
/// </summary> | |||||
/// <typeparam name="T"></typeparam> | |||||
/// <param name="source"></param> | |||||
/// <param name="items"></param> | |||||
/// <returns></returns> | |||||
public static List<T> AddToSet<T>(this List<T> source, List<T> items) | |||||
{ | |||||
return items; | |||||
} | |||||
} | |||||
} |
@@ -1,138 +0,0 @@ | |||||
using MongoDB.Driver; | |||||
namespace BPA.Component.MongoClient | |||||
{ | |||||
/// <summary> | |||||
/// MongoDbContext 工厂 | |||||
/// </summary> | |||||
public abstract class MongoDbProvider | |||||
{ | |||||
/// <summary> | |||||
/// 企业和别名的关系 | |||||
/// </summary> | |||||
protected readonly Dictionary<long, MongoDbContext> CorpWithMongoDbContexts = new(); | |||||
/// <summary> | |||||
/// 别名和mongondb实例的对应关系 | |||||
/// </summary> | |||||
protected readonly Dictionary<string, IMongoDatabase> AliasWithMongoDbContexts = new(); | |||||
/// <summary> | |||||
/// 别名和连接配置关系 | |||||
/// </summary> | |||||
public IReadOnlyDictionary<string, MongoDbConfig> AliasConfig { private set; get; } | |||||
/// <summary> | |||||
/// MongonDbFactory | |||||
/// </summary> | |||||
/// <param name="mongoDbConfigs"></param> | |||||
public MongoDbProvider(List<MongoDbConfig> mongoDbConfigs) | |||||
{ | |||||
SetMongoDbConfigs(mongoDbConfigs); | |||||
} | |||||
/// <summary> | |||||
/// 设置数据库连接配置 | |||||
/// </summary> | |||||
/// <param name="mongoDbConfigs"></param> | |||||
public void SetMongoDbConfigs(List<MongoDbConfig> mongoDbConfigs) | |||||
{ | |||||
lock (this) | |||||
{ | |||||
var dic = new Dictionary<string, MongoDbConfig>(); | |||||
foreach (var config in mongoDbConfigs) | |||||
{ | |||||
if (dic.ContainsKey(config.Alias)) | |||||
throw new ArgumentException($"数据库{this.GetType().Name}的配置别名[{config.Alias}]出现重复"); | |||||
dic.Add(config.Alias, config); | |||||
} | |||||
AliasConfig = dic; | |||||
} | |||||
} | |||||
/// <summary> | |||||
/// 根据企业ID获取MongoDb上下文对象 | |||||
/// </summary> | |||||
/// <param name="corpId">企业ID</param> | |||||
/// <returns></returns> | |||||
public virtual MongoDbContext GetDbContext(long corpId) | |||||
{ | |||||
if (CorpWithMongoDbContexts.ContainsKey(corpId)) | |||||
return CorpWithMongoDbContexts[corpId]; | |||||
lock (CorpWithMongoDbContexts) | |||||
{ | |||||
if (CorpWithMongoDbContexts.ContainsKey(corpId)) | |||||
return CorpWithMongoDbContexts[corpId]; | |||||
var dbAlias = GetDbAliasByCropId(corpId); | |||||
if (dbAlias == null) | |||||
throw new ArgumentException($"无法获取到企业[{corpId}]的{this.GetType().Name}数据库别名!"); | |||||
if (!AliasConfig.ContainsKey(dbAlias)) | |||||
throw new ArgumentException($"无法获取到企业[{corpId}]的{this.GetType().Name}数据库别名[{dbAlias}]对应的数据库连接!"); | |||||
var databases = GetMongoDatabase(dbAlias); | |||||
return CorpWithMongoDbContexts[corpId] = new MongoDbContext(corpId, databases.Client, databases); | |||||
} | |||||
} | |||||
/// <summary> | |||||
/// GetMongoDatabase | |||||
/// </summary> | |||||
/// <param name="dbAlias"></param> | |||||
/// <returns></returns> | |||||
public IMongoDatabase GetMongoDatabase(string dbAlias) | |||||
{ | |||||
IMongoDatabase mongoDatabase = null; | |||||
lock (AliasWithMongoDbContexts) | |||||
{ | |||||
if (AliasWithMongoDbContexts.ContainsKey(dbAlias)) | |||||
mongoDatabase = AliasWithMongoDbContexts[dbAlias]; | |||||
else | |||||
{ | |||||
var mongoDbConfig = AliasConfig[dbAlias]; | |||||
var client = new MongoDB.Driver.MongoClient(mongoDbConfig.ConnectionString); | |||||
mongoDatabase = client.GetDatabase(mongoDbConfig.DatabasesName); | |||||
AliasWithMongoDbContexts[dbAlias] = mongoDatabase; | |||||
} | |||||
} | |||||
return mongoDatabase; | |||||
} | |||||
/// <summary> | |||||
/// 获取所有的数据库操作对象 别名+数据库操作对象 | |||||
/// </summary> | |||||
/// <returns></returns> | |||||
public IReadOnlyDictionary<string, IMongoDatabase> GetMongoDatabases() | |||||
{ | |||||
if (AliasConfig.Count != AliasWithMongoDbContexts.Count) | |||||
{ | |||||
foreach (var dbAlias in AliasConfig.Keys) | |||||
{ | |||||
GetMongoDatabase(dbAlias); | |||||
} | |||||
} | |||||
return AliasWithMongoDbContexts; | |||||
} | |||||
/// <summary> | |||||
/// 根据企业Id获取数据库别名,子类必须实现 | |||||
/// </summary> | |||||
/// <returns></returns> | |||||
protected abstract string GetDbAliasByCropId(long corpId); | |||||
/// <summary> | |||||
/// 获取文档集接口 | |||||
/// </summary> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <param name="cropId">企业ID</param> | |||||
/// <param name="settings"></param> | |||||
/// <returns></returns> | |||||
public IMongoCollection<TDocument> GetCollection<TDocument>(long cropId, | |||||
MongoCollectionSettings settings = null) | |||||
{ | |||||
MongoDbContext dbContext = GetDbContext(cropId); | |||||
return dbContext.GetCollection<TDocument>(settings); | |||||
} | |||||
} | |||||
} |
@@ -0,0 +1,99 @@ | |||||
using BPA.Component.MongoClient.Conventions; | |||||
using MongoDB.Bson; | |||||
using MongoDB.Bson.Serialization; | |||||
using MongoDB.Bson.Serialization.Conventions; | |||||
using MongoDB.Bson.Serialization.Serializers; | |||||
using MongoDB.Driver; | |||||
using Newtonsoft.Json.Linq; | |||||
namespace BPA.Component.MongoClient.Repository; | |||||
/// <summary> | |||||
/// MongoDb基础仓储 | |||||
/// </summary> | |||||
public class BaseMongoDbRepository<TMongoDbClient, TDocument> : IBaseMongoDbRepository<TDocument> | |||||
where TMongoDbClient : BaseMongoDbClient<TMongoDbClient> | |||||
where TDocument : class, new() | |||||
{ | |||||
/// <summary> | |||||
/// MongoClient | |||||
/// </summary> | |||||
public MongoDB.Driver.MongoClient _mongoDbClient { get; } | |||||
/// <summary> | |||||
/// _Database | |||||
/// </summary> | |||||
private readonly IMongoDatabase _database; | |||||
/// <summary> | |||||
/// _Collection | |||||
/// </summary> | |||||
private IMongoCollection<TDocument> _collection; | |||||
/// <summary> | |||||
/// 构造函数 | |||||
/// </summary> | |||||
#pragma warning disable CS8618 | |||||
internal BaseMongoDbRepository() | |||||
#pragma warning restore CS8618 | |||||
{ | |||||
} | |||||
/// <summary> | |||||
/// 构造方法 | |||||
/// </summary> | |||||
public BaseMongoDbRepository(BaseMongoDbClient<TMongoDbClient> mongoDbClient) | |||||
{ | |||||
_mongoDbClient = mongoDbClient; | |||||
_database = _mongoDbClient.GetDatabase(mongoDbClient.CurrentDatabaseName); | |||||
var serializer = new DateTimeSerializer(DateTimeKind.Local, BsonType.DateTime); | |||||
BsonSerializer.RegisterSerializer(typeof(DateTime), serializer); | |||||
BsonSerializer.RegisterSerializer(typeof(JObject), new JObjectSerializer()); | |||||
BsonSerializer.RegisterSerializer(typeof(JArray), new JArraySerializer()); | |||||
BsonSerializer.RegisterSerializer(typeof(Dictionary<string, object>), new DictionarySerializerSerializer()); | |||||
BsonSerializer.RegisterSerializer(typeof(decimal), new DecimalSerializer(BsonType.Decimal128)); | |||||
BsonSerializer.RegisterSerializer(typeof(decimal?), new NullableSerializer<decimal>(new DecimalSerializer(BsonType.Decimal128))); | |||||
BsonSerializer.RegisterSerializationProvider(new BPASerializationProvider()); | |||||
ConventionRegistry.Register("IgnoreExtraElements", | |||||
new ConventionPack | |||||
{ | |||||
new IgnoreExtraElementsConvention(true), new BPACamelCaseElementNameConvention(), | |||||
new EnumRepresentationConvention(BsonType.String) | |||||
}, _ => true); | |||||
} | |||||
/// <summary> | |||||
/// 变更集合 | |||||
/// </summary> | |||||
/// <param name="collectionName"></param> | |||||
public virtual void ChangeCollection(string collectionName) | |||||
{ | |||||
_collection = _database.GetCollection<TDocument>(collectionName); | |||||
} | |||||
/// <summary> | |||||
/// 检查当前文档集 | |||||
/// </summary> | |||||
private void Checkcollection() | |||||
{ | |||||
if (_collection == null) | |||||
{ | |||||
throw new ArgumentNullException($"当前要操作的文档集为空,请调用{nameof(ChangeCollection)}方法切换集合文档"); | |||||
} | |||||
} | |||||
/// <summary> | |||||
/// 插入一个 | |||||
/// </summary> | |||||
/// <param name="document"></param> | |||||
/// <typeparam name="TDocument"></typeparam> | |||||
/// <returns></returns> | |||||
public async Task<int> AddAsync<TDocument>(TDocument document) where TDocument : class, new() | |||||
{ | |||||
var coll = _database.GetCollection<TDocument>(document.GetType().Name); | |||||
await coll.InsertOneAsync(document); | |||||
return 1; | |||||
} | |||||
} |
@@ -0,0 +1,12 @@ | |||||
using MongoDB.Driver; | |||||
namespace BPA.Component.MongoClient.Repository | |||||
{ | |||||
/// <summary> | |||||
/// MongoDB仓储接口 | |||||
/// </summary> | |||||
public interface IBaseMongoDbRepository<TDocument> where TDocument : class, new() | |||||
{ | |||||
MongoDB.Driver.MongoClient _mongoDbClient { get; } | |||||
} | |||||
} |
@@ -5,10 +5,19 @@ | |||||
<ImplicitUsings>enable</ImplicitUsings> | <ImplicitUsings>enable</ImplicitUsings> | ||||
<Nullable>enable</Nullable> | <Nullable>enable</Nullable> | ||||
<LangVersion>default</LangVersion> | <LangVersion>default</LangVersion> | ||||
<OutputType>Exe</OutputType> | |||||
</PropertyGroup> | </PropertyGroup> | ||||
<ItemGroup> | <ItemGroup> | ||||
<PackageReference Include="BPA.Component.MongoClient" Version="1.0.1" /> | |||||
<ProjectReference Include="..\..\BPA.Component.ApolloClient\BPA.Component.ApolloClient\BPA.Component.ApolloClient.csproj"/> | |||||
<ProjectReference Include="..\BPA.Component.MongoClient\BPA.Component.MongoClient.csproj"/> | |||||
</ItemGroup> | |||||
<ItemGroup> | |||||
<PackageReference Include="Microsoft.Extensions.Configuration" Version="6.0.0"/> | |||||
<PackageReference Include="Microsoft.Extensions.Configuration.EnvironmentVariables" Version="6.0.0"/> | |||||
<PackageReference Include="Microsoft.Extensions.Logging" Version="6.0.0" /> | |||||
<PackageReference Include="Microsoft.Extensions.Logging.Console" Version="6.0.0" /> | |||||
</ItemGroup> | </ItemGroup> | ||||
</Project> | </Project> |
@@ -1,771 +1,61 @@ | |||||
// using BPA.Component.Extensions; | |||||
// using BPA.Component.MongoClient; | |||||
// using BPA.Component.MongoClientTester.Models; | |||||
// using BPA.Component.MongoClientTester.Repositorys; | |||||
// using MongoDB.Driver; | |||||
// | |||||
// namespace BPA.Component.MongoClientTester | |||||
// { | |||||
// internal class Program | |||||
// { | |||||
// private static readonly MongoDbConfig TestDbConfig = new MongoDbConfig | |||||
// { | |||||
// ConnectionString = "mongodb://root:a5014e2c9c5890d517179be4a5c9f9ac@192.168.0.150:27017/?authSource=admin", | |||||
// DatabasesName = "test", | |||||
// Alias = "crm-test-01" | |||||
// }; | |||||
// | |||||
// private static List<string> _redisCluster = new List<string> | |||||
// { | |||||
// "192.168.0.149:6380,poolsize=50,ssl=false,writeBuffer=10240", | |||||
// "192.168.0.147:6380,poolsize=50,ssl=false,writeBuffer=10240", | |||||
// "192.168.0.150:6380,poolsize=50,ssl=false,writeBuffer=10240" | |||||
// }; | |||||
// | |||||
// private static readonly long corpId = 10000; | |||||
// | |||||
// private static void Main(string[] args) | |||||
// { | |||||
// Console.WriteLine("1=测试Provider,2=测试Repository,3=TestWatch"); | |||||
// var cmd = Console.ReadLine(); | |||||
// switch (cmd) | |||||
// { | |||||
// case "1": | |||||
// TestMongonDbProvider(); | |||||
// break; | |||||
// case "2": | |||||
// TestRepository(); | |||||
// break; | |||||
// default: | |||||
// Console.WriteLine("命令错误"); | |||||
// break; | |||||
// } | |||||
// | |||||
// Console.ReadLine(); | |||||
// } | |||||
// | |||||
// | |||||
// //创建provider | |||||
// private static TestMongoDbProvider _testMongoDbProvider = | |||||
// new TestMongoDbProvider(new List<MongoDbConfig> {TestDbConfig}); | |||||
// | |||||
// static void TestWatchMock() | |||||
// { | |||||
// var corpInfoRepository = new CorpInfoRepository(_testMongoDbProvider); | |||||
// //必须切换企业ID | |||||
// corpInfoRepository.ChangeCorpId(corpId); | |||||
// | |||||
// #region 插入 | |||||
// | |||||
// var insertCorpInfos = new List<CorpInfo>(); | |||||
// for (var i = 0; i < 10000; i++) | |||||
// { | |||||
// insertCorpInfos.Add(new CorpInfo | |||||
// { | |||||
// CorpId = corpId, | |||||
// Id = BPAUniqueIdBulder.NextLong(), | |||||
// Phones = new List<string> {$"1921682012{i}"}, | |||||
// AddressInfos = new List<CorpAddressInfo> | |||||
// { | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, | |||||
// Address = ",''''''''''' %%%%天府大道天府三街", Remark = "一号办公地点" | |||||
// }, | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府五街", | |||||
// Remark = "二号办公地点" | |||||
// }, | |||||
// }, | |||||
// Creator = new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// Name = null, | |||||
// No = $"sun{i}", | |||||
// Tags = new Dictionary<string, object> | |||||
// { | |||||
// {"string", $"string{i}"}, | |||||
// {"int", 10 + i}, | |||||
// {"double", 20.00 + 1}, | |||||
// {"datetime", DateTime.Now.AddMinutes(i)}, | |||||
// {"bool", i % 2}, | |||||
// } | |||||
// }); | |||||
// } | |||||
// | |||||
// Thread.Sleep(1000); | |||||
// //批量插入 | |||||
// corpInfoRepository.InsertMany(insertCorpInfos); | |||||
// | |||||
// #endregion | |||||
// | |||||
// #region 更新 | |||||
// | |||||
// Thread.Sleep(1000); | |||||
// corpInfoRepository.UpdateMany(x => new CorpInfo | |||||
// { | |||||
// Phones = x.Phones.AddToSet("sss ' ,\" \\ \\\\ $ @@@ ") | |||||
// }, x => x.No.StartsWith("sun")); | |||||
// | |||||
// #endregion | |||||
// | |||||
// return; | |||||
// | |||||
// #region 删除 | |||||
// | |||||
// Thread.Sleep(1000); | |||||
// var data = DateTime.Now.AddMinutes(5); | |||||
// corpInfoRepository.DeleteMany(x => x.CreateDate <= data); | |||||
// | |||||
// #endregion | |||||
// } | |||||
// | |||||
// static void TestRepository() | |||||
// { | |||||
// //创建provider | |||||
// var testMongonDbProvider = new TestMongoDbProvider(new List<MongoDbConfig> {TestDbConfig}); | |||||
// ICorpInfoRepository corpInfoRepository = new CorpInfoRepository(testMongonDbProvider); | |||||
// | |||||
// //必须切换企业ID | |||||
// corpInfoRepository.ChangeCorpId(corpId); | |||||
// | |||||
// //清空 测试数据清空下,一般清空是不要用到这个方法 | |||||
// corpInfoRepository.CurrMongoDbContext.ClearCollection<CorpInfo>(); | |||||
// | |||||
// | |||||
// #region 插入 | |||||
// | |||||
// var tags = new Dictionary<string, object> | |||||
// { | |||||
// {"datetime", DateTime.Now}, | |||||
// {"array0-1", new object[] {1, true, 66.2D, EnumEmployeeStatusType.Normal, DateTime.Now, ""}}, | |||||
// {"array00", null}, | |||||
// {"array01", new List<string> {"sss", "bbb"}}, | |||||
// {"array02", new List<string[]> {new string[] {"1", "2"}, new string[] {"3", "4"}}}, | |||||
// { | |||||
// "array03", | |||||
// new List<CorpAddressInfo> | |||||
// { | |||||
// new CorpAddressInfo | |||||
// {Address = "ss", Id = DateTime.Now.Ticks, Latitude = 1, Longitude = 2, Remark = ""} | |||||
// } | |||||
// }, | |||||
// }; | |||||
// // tags = Newtonsoft.Json.JsonConvert.DeserializeObject<Dictionary<string, object>>(tags.ToJson()); | |||||
// //插入单个 | |||||
// corpInfoRepository.InsertOneAsync(new CorpInfo | |||||
// { | |||||
// EnumEmployee = EnumEmployeeStatusType.Normal, | |||||
// CorpId = corpId, | |||||
// Id = BPAUniqueIdBulder.NextLong(), | |||||
// DB = long.MaxValue, | |||||
// AddressInfos = new List<CorpAddressInfo> | |||||
// { | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府五街", | |||||
// Remark = "二号办公地点" | |||||
// }, | |||||
// }, | |||||
// Name = "太阳国1", | |||||
// No = "sun1", | |||||
// Creator = new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// Tags = tags, | |||||
// Phones = new List<string> {"1921682012", "1921682012", "1921682012"} | |||||
// }); | |||||
// | |||||
// corpInfoRepository.InsertOneAsync(new CorpInfo | |||||
// { | |||||
// CorpId = corpId, | |||||
// Id = BPAUniqueIdBulder.NextLong(), | |||||
// AddressInfos = new List<CorpAddressInfo> | |||||
// { | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府五街", | |||||
// Remark = "二号办公地点" | |||||
// }, | |||||
// }, | |||||
// Creator = new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// Name = "太阳国2", | |||||
// No = "sun2", | |||||
// Tags = new Dictionary<string, object> | |||||
// { | |||||
// {"string", "string"}, | |||||
// {"int", 10}, | |||||
// {"double", 20.00}, | |||||
// {"datetime", DateTime.Now}, | |||||
// {"bool", true}, | |||||
// {"array0-1", new object[] {1, true, 66.2D, EnumEmployeeStatusType.Normal, DateTime.Now, ""}}, | |||||
// { | |||||
// "复杂的", | |||||
// new List<CorpAddressInfo> | |||||
// { | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// } | |||||
// } | |||||
// }, | |||||
// Phones = new List<string> {"1921682013", "1921682014", "1921682015"}, | |||||
// Ids = new List<long> {122238324489609220, 124675751317626880, 168259568508141570, 229039077946073100} | |||||
// }); | |||||
// | |||||
// Task.WaitAll(); | |||||
// | |||||
// var all = corpInfoRepository.Queryable().ToList(); | |||||
// | |||||
// return; | |||||
// | |||||
// var insertCorpInfos = new List<CorpInfo>(); | |||||
// for (var i = 3; i < 10; i++) | |||||
// { | |||||
// insertCorpInfos.Add(new CorpInfo | |||||
// { | |||||
// CorpId = corpId, | |||||
// Id = BPAUniqueIdBulder.NextLong(), | |||||
// AddressInfos = new List<CorpAddressInfo> | |||||
// { | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, | |||||
// Address = ",''''''''''' %%%%天府大道天府三街", Remark = "一号办公地点" | |||||
// }, | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府五街", | |||||
// Remark = "二号办公地点" | |||||
// }, | |||||
// }, | |||||
// Creator = new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// Name = null, | |||||
// No = $"sun{i}", | |||||
// Tags = new Dictionary<string, object> | |||||
// { | |||||
// {"string", $"string{i}"}, | |||||
// {"int", 10 + i}, | |||||
// {"double", 20.00 + 1}, | |||||
// {"datetime", DateTime.Now.AddMinutes(i)}, | |||||
// {"bool", i % 2}, | |||||
// } | |||||
// }); | |||||
// } | |||||
// | |||||
// Console.ReadLine(); | |||||
// //批量插入 | |||||
// corpInfoRepository.InsertMany(insertCorpInfos); | |||||
// | |||||
// #endregion | |||||
// | |||||
// var filters = corpInfoRepository.BuilderFilter(); | |||||
// var filterDefinitions = new List<FilterDefinition<CorpInfo>> | |||||
// { | |||||
// filters.Eq("No", "sun1") | |||||
// }; | |||||
// FilterDefinition<CorpInfo> filterDefinition = filters.And(filterDefinitions); | |||||
// var finder = corpInfoRepository.Find(filterDefinition); | |||||
// var result = finder.FirstOrDefault(); | |||||
// Console.WriteLine("使用 Find 进行查询:"); | |||||
// Console.WriteLine(result.ToJson()); | |||||
// | |||||
// | |||||
// #region 查询 Queryable 强烈推荐使用 | |||||
// | |||||
// Console.WriteLine("使用 Queryable 进行查询 :"); | |||||
// var phones = new List<string> {"1921682012", "1921682013", "1921682014"}; | |||||
// var ssss = corpInfoRepository.Queryable().Where(x => x.Phones.Any(x => phones.Contains(x))); | |||||
// var r2 = ssss.ToList(); | |||||
// Console.WriteLine(r2); | |||||
// Console.WriteLine(); | |||||
// | |||||
// var dys = corpInfoRepository.Queryable().Select(x => new A {Name = x.Name}); | |||||
// var r = dys.ToList(); | |||||
// Console.WriteLine(r); | |||||
// Console.WriteLine(); | |||||
// | |||||
// | |||||
// Console.WriteLine("使用 Queryable 进行查询 个别字段:"); | |||||
// var dys2 = corpInfoRepository.Queryable().Where(x => x.Id > 0).Select(x => new {x.Id, x.Creator}) | |||||
// .FirstOrDefault(); | |||||
// Console.WriteLine(dys2.ToJson()); | |||||
// Console.WriteLine(); | |||||
// | |||||
// //使用 Queryable 进行查询 | |||||
// var corpSun1 = corpInfoRepository.Queryable().FirstOrDefault(x => x.No == "sun1"); | |||||
// var corpSun2 = corpInfoRepository.Queryable().FirstOrDefault(x => x.No == "sun2"); | |||||
// Console.WriteLine("使用 Queryable 进行查询:"); | |||||
// Console.WriteLine(corpSun2.ToJson()); | |||||
// | |||||
// | |||||
// //WhereIF | |||||
// var corpSunpNoRefix = "sun"; | |||||
// var corpSuns = corpInfoRepository | |||||
// .Queryable() | |||||
// .Where(x => x.Id > 0) | |||||
// //corpSunpNoRefix.IsNotEmpty()==true 时,才会带上后面的查询添加 | |||||
// .WhereIF(corpSunpNoRefix.IsNotEmpty(), x => x.No.Contains(corpSunpNoRefix)) | |||||
// .ToList(); | |||||
// Console.WriteLine("WhereIF:"); | |||||
// Console.WriteLine(corpSuns.ToJson()); | |||||
// | |||||
// //Queryable 分页查询 带 total | |||||
// var paginationResult1 = corpInfoRepository.Queryable() | |||||
// .Where(x => x.No.Contains(corpSunpNoRefix)) | |||||
// .Pagination(1, 5, out int total); | |||||
// | |||||
// Console.WriteLine("Queryable 分页查询 带 total:"); | |||||
// Console.WriteLine(total); | |||||
// Console.WriteLine(paginationResult1.ToJson()); | |||||
// | |||||
// //Queryable 分页查询 不带 total | |||||
// var paginationResult2 = corpInfoRepository.Queryable() | |||||
// .Where(x => x.No.Contains(corpSunpNoRefix)) | |||||
// .OrderBy(x => x.No) | |||||
// .Pagination(1, 5); | |||||
// Console.WriteLine("Queryable 分页查询 不带 total:"); | |||||
// Console.WriteLine(paginationResult2.ToJson()); | |||||
// | |||||
// | |||||
// //动态字段查询 | |||||
// var queryResult1 = corpInfoRepository.Queryable() | |||||
// .Where(x => (string) x.Tags["string"] == "string") | |||||
// .OrderBy(x => x.No) | |||||
// .Pagination(1, 5); | |||||
// var queryResult2 = corpInfoRepository.Queryable() | |||||
// .Where(x => (DateTime) x.Tags["datetime"] < DateTime.Now) | |||||
// .OrderBy(x => x.No) | |||||
// .Pagination(1, 5); | |||||
// Console.WriteLine("动态字段查询:"); | |||||
// Console.WriteLine(queryResult1.ToJson()); | |||||
// Console.WriteLine(queryResult2.ToJson()); | |||||
// | |||||
// //更新下 方便下面left join 查看效果 | |||||
// corpInfoRepository.UpdateOne(x => new CorpInfo {No = "sun1"}, x => x.No == "sun11"); | |||||
// | |||||
// #endregion | |||||
// | |||||
// #region 更新 | |||||
// | |||||
// //更新符合条件的第一条数据 更新整个对象 | |||||
// corpSun1.Phones.Add("我是新增的"); | |||||
// var updateOneResult = corpInfoRepository.UpdateOne(corpSun1, x => x.No == "sun10"); | |||||
// Console.WriteLine("更新整个对象:"); | |||||
// Console.WriteLine(updateOneResult.ToJson()); | |||||
// | |||||
// var fieldList = Builders<CorpInfo>.Update.AddToSet("ids", 220827615942565900); | |||||
// FilterDefinition<CorpInfo> filter = Builders<CorpInfo>.Filter.Eq("No", "sun2"); | |||||
// corpInfoRepository.UpdateOne(filter, fieldList); | |||||
// | |||||
// corpInfoRepository.UpdateOne(x => new CorpInfo | |||||
// { | |||||
// Ids = x.Ids.AddToSet((long) 220827615942565900) | |||||
// }, x => x.No.StartsWith("sun2")); | |||||
// | |||||
// | |||||
// corpInfoRepository.UpdateOne(x => new CorpInfo | |||||
// { | |||||
// Phones = x.Phones.AddToSet("sss ' ,\" \\ \\\\ $ @@@ ") | |||||
// }, x => x.No.StartsWith("sun2")); | |||||
// corpInfoRepository.UpdateOne(x => new CorpInfo | |||||
// { | |||||
// Phones = x.Phones.AddToSet(new List<string> {"sss", "22222"}) | |||||
// }, x => x.No.StartsWith("sun2")); | |||||
// | |||||
// var sss = corpInfoRepository.UpdateOne(x => new CorpInfo | |||||
// { | |||||
// //Id = corpSun1.Id, | |||||
// CreateDate = DateTime.MinValue, | |||||
// Phones = corpSun1.Phones.AddToSet("AddToSet"), | |||||
// AddressInfos = corpSun1.AddressInfos.AddToSet(new CorpAddressInfo {Id = 0, Address = "AddToSet"}) | |||||
// }, x => x.No.StartsWith("sun2")); | |||||
// | |||||
// //更新 自定义字段 实体键_id不允许更新 | |||||
// corpSun1.Phones.Add("我是新增的222222222222222222"); | |||||
// corpSun1.AddressInfos.Add(new CorpAddressInfo {Address = "新增的3"}); | |||||
// var updateOneResult2 = corpInfoRepository.UpdateOne(x => new CorpInfo | |||||
// { | |||||
// //Id = corpSun1.Id, | |||||
// CreateDate = DateTime.MinValue, | |||||
// Phones = corpSun1.Phones, | |||||
// AddressInfos = corpSun1.AddressInfos | |||||
// }, x => x.No.StartsWith("sun2")); | |||||
// Console.WriteLine("更新 自定义字段:"); | |||||
// Console.WriteLine(updateOneResult2.ToJson()); | |||||
// | |||||
// //更新多个 更新整个对象 | |||||
// corpSun1.Phones.Add("UpdateMany 更新整个对象"); | |||||
// var updateOneResult3 = corpInfoRepository.UpdateMany(corpSun1, x => x.No == "sun1"); | |||||
// Console.WriteLine("更新多个 更新整个对象:"); | |||||
// Console.WriteLine(updateOneResult3.ToJson()); | |||||
// | |||||
// //更新多个 更新整个对象 自定义字段 | |||||
// corpSun1.Phones.Add("UpdateMany 自定义字段"); | |||||
// var updateOneResult4 = corpInfoRepository.UpdateMany(x => new CorpInfo | |||||
// { | |||||
// Phones = corpSun1.Phones, | |||||
// }, x => x.No.StartsWith("sun")); | |||||
// Console.WriteLine("更新多个 自定义字段 :"); | |||||
// Console.WriteLine(updateOneResult4.ToJson()); | |||||
// | |||||
// #endregion | |||||
// | |||||
// | |||||
// #region 删除 | |||||
// | |||||
// //根据条件删除 一个 | |||||
// var deleteResult = corpInfoRepository.DeleteOne(x => x.No == "sun1"); | |||||
// Console.WriteLine("根据条件删除 一个:"); | |||||
// Console.WriteLine(deleteResult.ToJson()); | |||||
// | |||||
// //根据条件删除 多个 | |||||
// var deleteResult2 = corpInfoRepository.DeleteMany(x => x.No.StartsWith("sun1")); | |||||
// Console.WriteLine("根据条件删除 多个:"); | |||||
// Console.WriteLine(deleteResult2.ToJson()); | |||||
// | |||||
// #endregion | |||||
// | |||||
// //清空 测试数据清空下,一般清空是不要用到这个方法 | |||||
// corpInfoRepository.DeleteMany(x => x.Id > 0); | |||||
// //清空 测试数据清空下,一般清空是不要用到这个方法 | |||||
// //corpInfoRepository.CurrMongoDbContext.ClearCollection<CorpInfo>(); | |||||
// } | |||||
// | |||||
// /// <summary> | |||||
// /// 测试Provider | |||||
// /// </summary> | |||||
// /// <param name="args"></param> | |||||
// static void TestMongonDbProvider() | |||||
// { | |||||
// //Console.WriteLine(1.GetHashCode()); | |||||
// //Console.WriteLine(1.GetHashCode()); | |||||
// //Console.WriteLine(1.GetHashCode()); | |||||
// | |||||
// //Console.WriteLine(2.GetHashCode()); | |||||
// //Console.WriteLine(2.GetHashCode()); | |||||
// //Console.WriteLine(2.GetHashCode()); | |||||
// | |||||
// //创建provider | |||||
// var testMongonDbProvider = new TestMongoDbProvider(new List<MongoDbConfig> {TestDbConfig}); | |||||
// //BPATestMongoDbContext 必须要继承 BPAMongoDbContext | |||||
// var testDbContext = testMongonDbProvider.GetDbContext(corpId); | |||||
// | |||||
// //根据企业ID构建文档集名称 | |||||
// var corpInfoCollectionName = testDbContext.BuildCollectionName<CorpInfo>(corpId); | |||||
// Console.WriteLine(corpInfoCollectionName); | |||||
// | |||||
// | |||||
// //获取文档集操作接口对象, | |||||
// var corpInfoCollection = testMongonDbProvider.GetCollection<CorpInfo>(corpId); | |||||
// | |||||
// //清空 测试数据清空下,一般清空是不要用到这个方法 | |||||
// testDbContext.ClearCollection<CorpInfo>(); | |||||
// | |||||
// #region 插入 | |||||
// | |||||
// //插入单个 | |||||
// corpInfoCollection.InsertOne(new CorpInfo | |||||
// { | |||||
// Id = BPAUniqueIdBulder.NextLong(), | |||||
// AddressInfos = new List<CorpAddressInfo> | |||||
// { | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府五街", | |||||
// Remark = "二号办公地点" | |||||
// }, | |||||
// }, | |||||
// Creator = new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// Name = "太阳国1", | |||||
// No = "sun1", | |||||
// Tags = new Dictionary<string, object> | |||||
// { | |||||
// {"string", null}, | |||||
// {"int", null}, | |||||
// {"double", null}, | |||||
// {"datetime", null}, | |||||
// {"bool", null}, | |||||
// }, | |||||
// Phones = new List<string> {"1921682012", "1921682012", "1921682012"} | |||||
// }); | |||||
// corpInfoCollection.InsertOne(new CorpInfo | |||||
// { | |||||
// Id = BPAUniqueIdBulder.NextLong(), | |||||
// AddressInfos = new List<CorpAddressInfo> | |||||
// { | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府五街", | |||||
// Remark = "二号办公地点" | |||||
// }, | |||||
// }, | |||||
// Creator = new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// Name = "太阳国2", | |||||
// No = "sun2", | |||||
// Tags = new Dictionary<string, object> | |||||
// { | |||||
// {"string", "string"}, | |||||
// {"int", 10}, | |||||
// {"double", 20.00}, | |||||
// {"datetime", DateTime.Now}, | |||||
// {"bool", true}, | |||||
// } | |||||
// }); | |||||
// | |||||
// var insertCorpInfos = new List<CorpInfo>(); | |||||
// for (var i = 3; i < 10; i++) | |||||
// { | |||||
// insertCorpInfos.Add(new CorpInfo | |||||
// { | |||||
// Id = BPAUniqueIdBulder.NextLong(), | |||||
// AddressInfos = new List<CorpAddressInfo> | |||||
// { | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府五街", | |||||
// Remark = "二号办公地点" | |||||
// }, | |||||
// }, | |||||
// Creator = new CorpAddressInfo | |||||
// { | |||||
// Id = (long) DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", | |||||
// Remark = "一号办公地点" | |||||
// }, | |||||
// Name = $"太阳国{i}", | |||||
// No = $"sun{i}", | |||||
// Tags = new Dictionary<string, object> | |||||
// { | |||||
// {"string", $"string{i}"}, | |||||
// {"int", 10 + i}, | |||||
// {"double", 20.00 + 1}, | |||||
// {"datetime", DateTime.Now.AddMinutes(i)}, | |||||
// {"bool", i % 2}, | |||||
// } | |||||
// }); | |||||
// } | |||||
// | |||||
// //批量插入 | |||||
// corpInfoCollection.InsertMany(insertCorpInfos); | |||||
// | |||||
// #endregion | |||||
// | |||||
// #region 查询 Queryable 强烈推荐使用 | |||||
// | |||||
// //使用 Queryable 进行查询 | |||||
// | |||||
// var dys = corpInfoCollection.Queryable().Where(x => x.Id > 0).Select(x => new {x.Creator, x.Id}) | |||||
// .FirstOrDefault(); | |||||
// Console.WriteLine(dys.ToJson()); | |||||
// | |||||
// var corpSun1 = corpInfoCollection.Queryable().FirstOrDefault(x => x.No == "sun1"); | |||||
// var corpSun2 = corpInfoCollection.Queryable().FirstOrDefault(x => x.No == "sun2"); | |||||
// Console.WriteLine("使用 Queryable 进行查询:"); | |||||
// Console.WriteLine(corpSun2.ToJson()); | |||||
// | |||||
// | |||||
// //WhereIF | |||||
// var corpSunpNoRefix = "sun"; | |||||
// var corpSuns = corpInfoCollection | |||||
// .Queryable() | |||||
// //corpSunpNoRefix.IsNotEmpty()==true 时,才会带上后面的查询添加 | |||||
// .WhereIF(corpSunpNoRefix.IsNotEmpty(), x => x.No.Contains(corpSunpNoRefix)) | |||||
// .ToList(); | |||||
// Console.WriteLine("WhereIF:"); | |||||
// Console.WriteLine(corpSuns.ToJson()); | |||||
// | |||||
// //Queryable 分页查询 带 total | |||||
// var paginationResult1 = corpInfoCollection.Queryable() | |||||
// .Where(x => x.No.Contains(corpSunpNoRefix)) | |||||
// .Pagination(1, 5, out int total); | |||||
// | |||||
// Console.WriteLine("Queryable 分页查询 带 total:"); | |||||
// Console.WriteLine(total); | |||||
// Console.WriteLine(paginationResult1.ToJson()); | |||||
// | |||||
// //Queryable 分页查询 不带 total | |||||
// var paginationResult2 = corpInfoCollection.Queryable() | |||||
// .Where(x => x.No.Contains(corpSunpNoRefix)) | |||||
// .OrderBy(x => x.No) | |||||
// .Pagination(1, 5); | |||||
// Console.WriteLine("Queryable 分页查询 不带 total:"); | |||||
// Console.WriteLine(paginationResult2.ToJson()); | |||||
// | |||||
// | |||||
// //动态字段查询 | |||||
// var queryResult1 = corpInfoCollection.Queryable() | |||||
// .Where(x => (string) x.Tags["string"] == "string") | |||||
// .OrderBy(x => x.No) | |||||
// .Pagination(1, 5); | |||||
// var queryResult2 = corpInfoCollection.Queryable() | |||||
// .Where(x => (DateTime) x.Tags["datetime"] < DateTime.Now) | |||||
// .OrderBy(x => x.No) | |||||
// .Pagination(1, 5); | |||||
// Console.WriteLine("动态字段查询:"); | |||||
// Console.WriteLine(queryResult1.ToJson()); | |||||
// Console.WriteLine(queryResult2.ToJson()); | |||||
// | |||||
// //更新下 方便下面left join 查看效果 | |||||
// corpInfoCollection.UpdateOne(x => new CorpInfo {No = "sun1"}, x => x.No == "sun11"); | |||||
// | |||||
// // left join | |||||
// var quryable1 = corpInfoCollection.Queryable(); | |||||
// var quryable2 = corpInfoCollection.Queryable(); | |||||
// var quryable5 = corpInfoCollection.Queryable(); | |||||
// var quryable3 = from c1 in quryable1 | |||||
// //left join | |||||
// join c2 in quryable2 | |||||
// on c1.No equals c2.No into temp | |||||
// from tt in temp.DefaultIfEmpty() | |||||
// join c5 in quryable5 | |||||
// on c1.No equals c5.No into temp2 | |||||
// from tt2 in temp2.DefaultIfEmpty() | |||||
// where c1.No == "sun1" | |||||
// select new | |||||
// { | |||||
// C1Id = c1.Id, | |||||
// C1No = c1.No, | |||||
// //C2Id = tt.Id, | |||||
// //C2No = tt.No, | |||||
// //C3Id = tt2.Id, | |||||
// //C3No = tt2.No, | |||||
// //C2Id = tt == null ? ObjectId.Empty : tt.Id, | |||||
// //C2No = tt == null ? string.Empty : tt.No, | |||||
// //C3Id = tt2 == null ? ObjectId.Empty : tt2.Id, | |||||
// //C3No = tt2 == null ? string.Empty : tt2.No | |||||
// }; | |||||
// //var quryable3 = from c1 in quryable1 | |||||
// // //left join | |||||
// // join c2 in quryable2 on c1.No equals c2.No into temp | |||||
// // from tt in temp.DefaultIfEmpty() | |||||
// // select new { c1, tt }; | |||||
// //quryable3 = quryable3.Where(x => x.c1.No == "sun1"); | |||||
// //var quryable4 = quryable3.Select(x => new | |||||
// //{ | |||||
// // C1Id = x.c1.Id, | |||||
// // C1No = x.c1.No, | |||||
// // C2Id = x.tt == null ? ObjectId.Empty : x.tt.Id, | |||||
// // C2No = x.tt == null ? string.Empty : x.tt.No | |||||
// //}); | |||||
// quryable3 = quryable3.Where(x => x.C1No == "sun1"); | |||||
// | |||||
// Console.WriteLine(quryable3.ToString()); | |||||
// var leftJoinReuslt = quryable3.ToList(); | |||||
// Console.WriteLine("left join:"); | |||||
// Console.WriteLine(leftJoinReuslt.ToJson()); | |||||
// | |||||
// #endregion | |||||
// | |||||
// #region 更新 | |||||
// | |||||
// //更新符合条件的第一条数据 更新整个对象 | |||||
// corpSun1.Phones.Add("我是新增的"); | |||||
// var updateOneResult = corpInfoCollection.UpdateOne(corpSun1, x => x.No == "sun10"); | |||||
// Console.WriteLine("更新整个对象:"); | |||||
// Console.WriteLine(updateOneResult.ToJson()); | |||||
// | |||||
// //更新 自定义字段 实体键_id不允许更新 | |||||
// corpSun1.Phones.Add("我是新增的2"); | |||||
// corpSun1.AddressInfos.Each(it => it.Id = (long) DateTime.Now.Ticks); | |||||
// corpSun1.AddressInfos.Add(new CorpAddressInfo {Address = "新增的3"}); | |||||
// var updateOneResult2 = corpInfoCollection.UpdateOne(x => new CorpInfo | |||||
// { | |||||
// //Id = corpSun1.Id, | |||||
// CreateDate = DateTime.Now.AddDays(50), | |||||
// Phones = corpSun1.Phones, | |||||
// AddressInfos = corpSun1.AddressInfos | |||||
// }, x => x.No.StartsWith("sun2")); | |||||
// Console.WriteLine("更新 自定义字段:"); | |||||
// Console.WriteLine(updateOneResult2.ToJson()); | |||||
// | |||||
// //更新多个 更新整个对象 | |||||
// corpSun1.Phones.Add("UpdateMany 更新整个对象"); | |||||
// var updateOneResult3 = corpInfoCollection.UpdateMany(corpSun1, x => x.No == "sun1"); | |||||
// Console.WriteLine("更新多个 更新整个对象:"); | |||||
// Console.WriteLine(updateOneResult3.ToJson()); | |||||
// | |||||
// //更新多个 更新整个对象 自定义字段 | |||||
// corpSun1.Phones.Add("UpdateMany 自定义字段"); | |||||
// var updateOneResult4 = corpInfoCollection.UpdateMany(x => new CorpInfo | |||||
// { | |||||
// Phones = corpSun1.Phones, | |||||
// }, x => x.No == "sun1"); | |||||
// Console.WriteLine("更新多个 自定义字段 :"); | |||||
// Console.WriteLine(updateOneResult4.ToJson()); | |||||
// | |||||
// #endregion | |||||
// | |||||
// | |||||
// #region 删除 | |||||
// | |||||
// //根据条件删除 一个 | |||||
// var deleteResult = corpInfoCollection.DeleteOne(x => x.No == "sun1"); | |||||
// Console.WriteLine("根据条件删除 一个:"); | |||||
// Console.WriteLine(deleteResult.ToJson()); | |||||
// | |||||
// //根据条件删除 多个 | |||||
// var deleteResult2 = corpInfoCollection.DeleteMany(x => x.No.StartsWith("sun1")); | |||||
// Console.WriteLine("根据条件删除 多个:"); | |||||
// Console.WriteLine(deleteResult2.ToJson()); | |||||
// | |||||
// #endregion | |||||
// | |||||
// //清空 测试数据清空下,一般清空是不要用到这个方法 | |||||
// testDbContext.ClearCollection<CorpInfo>(); | |||||
// Console.ReadLine(); | |||||
// } | |||||
// } | |||||
// | |||||
// public class A | |||||
// { | |||||
// public string Name { set; get; } | |||||
// } | |||||
// } | |||||
using BPA.Component.ApolloClient; | |||||
using BPA.Component.DbClientTester; | |||||
using BPA.Component.MongoClientTester.Models; | |||||
using BPA.Component.MongoClientTester.Repositorys; | |||||
using Microsoft.Extensions.Configuration; | |||||
using Microsoft.Extensions.DependencyInjection; | |||||
using Microsoft.Extensions.Logging; | |||||
namespace BPA.Component.MongoClientTester; | |||||
internal class Program | |||||
{ | |||||
private static async Task Main(string[] args) | |||||
{ | |||||
var builder = new ConfigurationBuilder(); | |||||
builder.AddEnvironmentVariables(); | |||||
IConfiguration configuration = builder.Build(); | |||||
configuration.AddApolloConfiguration(); | |||||
var services = new ServiceCollection(); | |||||
services.AddApollo<TestConfig>(); | |||||
services.AddLogging(configure => { configure.AddConsole(); }); | |||||
services.AddScoped<TestMongoDcClient>(); | |||||
services.AddTransient<ICorpInfoRepository, CorpInfoRepository>(); | |||||
var serviceProvider = services.BuildServiceProvider(); | |||||
var testDbClient = serviceProvider.GetService<TestMongoDcClient>(); | |||||
if (testDbClient == null) return; | |||||
var userRepository = serviceProvider.GetService<ICorpInfoRepository>(); | |||||
var tags = new Dictionary<string, object> | |||||
{ | |||||
{"datetime", DateTime.Now}, | |||||
{"array0-1", new object[] {1, true, 66.2D, Enums.Aaa, DateTime.Now, ""}}, | |||||
{"array00", null}, | |||||
{"array01", new List<string> {"sss", "bbb"}}, | |||||
{"array02", new List<string[]> {new[] {"1", "2"}, new[] {"3", "4"}}}, | |||||
{"array03", new List<CorpAddressInfo> {new() {Address = "ss", Id = DateTime.Now.Ticks, Latitude = 1, Longitude = 2, Remark = ""}}}, | |||||
}; | |||||
await userRepository.AddAsync(new CorpInfo | |||||
{ | |||||
DB = long.MaxValue, | |||||
AddressInfos = new List<CorpAddressInfo> | |||||
{ | |||||
new() {Id = DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", Remark = "一号办公地点"}, | |||||
new() {Id = DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府五街", Remark = "二号办公地点"}, | |||||
}, | |||||
Name = "太阳国1", | |||||
No = "sun1", | |||||
Creator = new CorpAddressInfo {Id = DateTime.Now.Ticks, Latitude = 66.52, Longitude = 451.63, Address = "天府大道天府三街", Remark = "一号办公地点"}, | |||||
Tags = tags, | |||||
Phones = new List<string> {"1921682012", "1921682012", "1921682012"} | |||||
}); | |||||
} | |||||
} | |||||
public enum Enums | |||||
{ | |||||
Aaa = 1, | |||||
Bbb = 2 | |||||
} |
@@ -3,9 +3,10 @@ | |||||
"BPA.Component.LogClientTester": { | "BPA.Component.LogClientTester": { | ||||
"commandName": "Project", | "commandName": "Project", | ||||
"environmentVariables": { | "environmentVariables": { | ||||
"APOLLO_META_SERVER_URL": "http://192.168.0.147:7010", | |||||
"APOLLO_COMMON_NAMESPACE": "BPA.test.common", | |||||
"APP_NAME": "BPA.test" | |||||
"ASPNETCORE_ENVIRONMENT": "Development", | |||||
"APOLLO_META_SERVER_URL": "http://10.2.1.21:28080", | |||||
"APOLLO_COMMON_NAMESPACE": "Dev.Common", | |||||
"APP_NAME": "BPA-DEV" | |||||
} | } | ||||
} | } | ||||
} | } |
@@ -1,12 +1,16 @@ | |||||
using BPA.Component.MongoClient; | using BPA.Component.MongoClient; | ||||
using BPA.Component.MongoClient.Repository; | |||||
using BPA.Component.MongoClientTester.Models; | using BPA.Component.MongoClientTester.Models; | ||||
namespace BPA.Component.MongoClientTester.Repositorys | namespace BPA.Component.MongoClientTester.Repositorys | ||||
{ | { | ||||
public class CorpInfoRepository : BaseMGRepository<CorpInfo>, ICorpInfoRepository | |||||
public class CorpInfoRepository : BaseMongoDbRepository<TestMongoDcClient, CorpInfo>, ICorpInfoRepository | |||||
{ | { | ||||
public CorpInfoRepository(TestMongoDbProvider mongoDbProvider) : base(mongoDbProvider) | |||||
public CorpInfoRepository(TestMongoDcClient mongoDbClient) : base(mongoDbClient) | |||||
{ | { | ||||
} | } | ||||
} | } | ||||
} | } |
@@ -1,9 +1,10 @@ | |||||
using BPA.Component.MongoClient; | |||||
using BPA.Component.MongoClient.Repository; | |||||
using BPA.Component.MongoClientTester.Models; | using BPA.Component.MongoClientTester.Models; | ||||
namespace BPA.Component.MongoClientTester.Repositorys | namespace BPA.Component.MongoClientTester.Repositorys | ||||
{ | { | ||||
public interface ICorpInfoRepository : IMGRepository<CorpInfo> | |||||
public interface ICorpInfoRepository : IBaseMongoDbRepository<CorpInfo> | |||||
{ | { | ||||
Task<int> AddAsync<TDocument>(TDocument document) where TDocument : class, new(); | |||||
} | } | ||||
} | } |
@@ -0,0 +1,20 @@ | |||||
using BPA.Component.ApolloClient; | |||||
using BPA.Component.MongoClient; | |||||
using Com.Ctrip.Framework.Apollo; | |||||
using Microsoft.Extensions.Configuration; | |||||
namespace BPA.Component.DbClientTester; | |||||
/// <summary> | |||||
/// test项目配置 | |||||
/// </summary> | |||||
public class TestConfig : ApolloBPAConfig<TestConfig> | |||||
{ | |||||
[AutoWrite] | |||||
public MongoConfig MongoDbForWebApi1Db { get; set; } | |||||
public TestConfig(ApolloConfigurationManager apolloConfigurationManager, IConfiguration configuration) : base(apolloConfigurationManager, configuration) | |||||
{ | |||||
} | |||||
} |
@@ -1,24 +0,0 @@ | |||||
using BPA.Component.MongoClient; | |||||
namespace BPA.Component.MongoClientTester | |||||
{ | |||||
/// <summary> | |||||
/// 测试数据库 TestMongoDbProvider | |||||
/// </summary> | |||||
public class TestMongoDbProvider : MongoDbProvider | |||||
{ | |||||
public TestMongoDbProvider(List<MongoDbConfig> mongoDbConfigs) : base(mongoDbConfigs) | |||||
{ | |||||
} | |||||
/// <summary> | |||||
/// 根据企业ID获取数据库别名 | |||||
/// </summary> | |||||
/// <param name="corpId"></param> | |||||
/// <returns></returns> | |||||
protected override string GetDbAliasByCropId(long corpId) | |||||
{ | |||||
return "test-01"; | |||||
} | |||||
} | |||||
} |
@@ -0,0 +1,13 @@ | |||||
using BPA.Component.DbClientTester; | |||||
using BPA.Component.MongoClient; | |||||
using Microsoft.Extensions.Logging; | |||||
namespace BPA.Component.MongoClientTester; | |||||
public class TestMongoDcClient : BaseMongoDbClient<TestMongoDcClient> | |||||
{ | |||||
public TestMongoDcClient(TestConfig config, ILogger<TestMongoDcClient> logger = null) | |||||
: base(BuildMongoConfig(config.MongoDbForWebApi1Db.ConnectionString, config.MongoDbForWebApi1Db.DatabasesName), logger) | |||||
{ | |||||
} | |||||
} |