using System; using System.Collections.Generic; using System.Data.Entity; using System.Linq; using System.Linq.Expressions; using iiie.Logs.DataAccess; using iiie.Logs.DBO; using System.Linq.Dynamic; namespace iiie.WebApiUtils.BusinessManager { /// /// Helper for SQL Server data access /// public abstract class SqlServerManager where TDbObject : class where TEntities : DbContext, new() where TThis : SqlServerManager, new() { private class DbObjectId { public long id { get; set; } } /// /// Return the table to be used /// /// The database /// The table instance public abstract DbSet GetTable(TEntities db); public abstract TDbo DbToDbo(TDbObject obj); public abstract TDbObject DboToDb(TDbo obj); /// /// Return the database table to use /// /// The database instance /// The table public static DbSet GetTableStatic(TEntities db) { var type = new TThis(); return type.GetTable(db); } /// /// Helper to convert DB object to DBO /// /// The result to convert /// The DBO object public static OpResult DbToDboStatic(OpResult res) { if (!res) return OpResult.Error(res); var obj = new TThis(); return OpResult.Ok(obj.DbToDbo(res.Data)); } /// /// Helper to convert DBO object to DB /// /// The result to convert /// The DB object public static OpResult DboToDbStatic(OpResult res) { if (!res) return OpResult.Error(res); var obj = new TThis(); return OpResult.Ok(obj.DboToDb(res.Data)); } /// /// Helper to convert DB object to DBO /// /// The result to convert /// The DBO object public static TDbo DbToDboStatic(TDbObject res) { var obj = new TThis(); return obj.DbToDbo(res); } /// /// Helper to convert DBO object to DB /// /// The result to convert /// The DB object public static TDbObject DboToDbStatic(TDbo res) { var obj = new TThis(); return obj.DboToDb(res); } /// /// Execute SQL quries in try catch /// /// The queries to be performed /// The result or an error public static OpResult Execute(Func, OpResult> func) { try { using (var db = new TEntities()) { var table = GetTableStatic(db); return func(db, table); } } catch (Exception e) { return Logger.Error(ResultStatus.DBError, e); } } /// /// Get a single DB object matching the predicate /// /// The predicate /// The object that match, or null public static OpResult GetSingle(Expression> predicate) { return Execute((db, table) => { var o = table.FirstOrDefault(predicate); if (o == null) { return OpResult.Error(ResultStatus.NotFound, typeof(TThis).Name + ": Value not found", ""); } return OpResult.Ok(o); }); } /// /// Get a single DBO matching the predicate /// /// The predicate /// The object that match, or null public static OpResult GetSingleDbo(Expression> predicate) { return DbToDboStatic(GetSingle(predicate)); } /// /// Get all DB object matching the predicate /// /// The predicate /// All matching objects public static OpResult> GetMultiple(Expression> predicate) { return Execute((db, table) => OpResult>.Ok(table.Where(predicate).ToList())); } /// /// Get all DBO matching the predicate /// /// The DBO type /// The predicate /// All matching objects public static OpResult> GetMultipleDbo(Expression> predicate) { var res = GetMultiple(predicate); if (!res) return OpResult>.Error(res); var dbo = res.Data.Select(DbToDboStatic); return OpResult>.Ok(dbo); } /// /// Add an entry in the database /// /// The object to be added /// Always true or an OpResult error public static OpResult Add(TDbObject obj) { return Execute((db, table) => { table.Add(obj); db.SaveChanges(); return OpResult.Ok(true); }); } /// /// Add an entry in the database /// /// /// Always true or an OpResult error public static OpResult AddDbo(TDbo obj) { return Add(DboToDbStatic(obj)); } /// /// Get an object by its id /// /// The id of the object /// The object public static OpResult GetById(long id) { var param = Expression.Parameter(typeof(TDbObject), "x"); var exp = Expression.Lambda>( Expression.Equal( Expression.Property(param, "id"), Expression.Constant(id) ), param); return GetSingle(exp); } /// /// Get an object by its id /// /// The id of the object /// The object public static OpResult GetByIdDbo(long id) { return DbToDboStatic(GetById(id)); } } }