using System; using System.Collections.Generic; using System.Data; using System.Linq.Expressions; using Luticate2.Utils.Dbo.Result; using Microsoft.EntityFrameworkCore; using Microsoft.Extensions.DependencyInjection; namespace Luticate2.Utils.DataAccess { public abstract class LuEfDataAccess : LuDataAccess where TModel : class where TDbContext : DbContext { private readonly IServiceProvider _serviceProvider; protected LuEfTransactionScope TransactionScope => _serviceProvider.GetService(); protected LuEfDataAccess(IServiceProvider serviceProvider) { _serviceProvider = serviceProvider; } protected abstract DbSet GetTable(TDbContext db); protected virtual LuResult HandleError(Exception e) { return null; } public virtual LuResult Execute(Func, LuResult> func) { try { var transactedDb = TransactionScope.GetTransactedDbContext(); if (transactedDb == null) { using (var db = _serviceProvider.GetService()) { return func(db, GetTable(db)); } } return func(transactedDb, GetTable(transactedDb)); } catch (Exception e) { var err = HandleError(e); if (null != err) { return err; } return LuResult.Error(LuStatus.DbError, e); } } public static Expression> GetExpression(params KeyValuePair[] keys) { var param = Expression.Parameter(typeof(TModel), "x"); Expression totalExp = null; foreach (var pair in keys) { var equalExp = Expression.Equal(Expression.Property(param, pair.Key), Expression.Constant(pair.Value)); totalExp = totalExp == null ? equalExp : Expression.And(equalExp, totalExp); } return Expression.Lambda>(totalExp, param); } public bool BeginTransaction(TDbContext context, IsolationLevel? level = null) { return TransactionScope.BeginTransaction(context, level); } public void CommitTransaction(bool transact) { if (transact) { TransactionScope.CommitTransaction(); } } public void RollbackTransaction(bool transact) { if (transact) { TransactionScope.RollbackTransaction(); } } } }