221 lines
7.9 KiB
C#
221 lines
7.9 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.Linq;
|
|
using System.Linq.Expressions;
|
|
using System.Text;
|
|
using System.Threading;
|
|
using System.Threading.Tasks;
|
|
using Microsoft.EntityFrameworkCore;
|
|
using PlixP.Extentions;
|
|
using PlixP.Models;
|
|
using PlixP.Repositories.Contracts;
|
|
|
|
namespace PlixP.Repositories
|
|
{
|
|
public class BaseRepository<T> : IBaseRepository<T>
|
|
where T : Entity
|
|
{
|
|
protected readonly PlixContext DbContext;
|
|
public DbSet<T> Entities { get; }
|
|
public virtual IQueryable<T> Table => Entities.Where(e => e.IsRemoved == false);
|
|
public virtual IQueryable<T> TableNoTracking => Entities.AsNoTracking().Where(e => e.IsRemoved == false);
|
|
|
|
public BaseRepository(PlixContext dbContext)
|
|
{
|
|
DbContext = dbContext;
|
|
Entities = DbContext.Set<T>(); // City => Cities
|
|
}
|
|
|
|
#region Async Method
|
|
public virtual async Task<T> GetByIdAsync(CancellationToken cancellationToken, params object[] ids)
|
|
{
|
|
|
|
var entity = await Entities.FindAsync(ids, cancellationToken);
|
|
DbContext.Entry(entity).State = EntityState.Detached;
|
|
return entity;
|
|
|
|
}
|
|
|
|
public virtual async Task AddAsync(T entity, CancellationToken cancellationToken, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entity, nameof(entity));
|
|
entity.CreationDate = DateTime.Now;
|
|
await Entities.AddAsync(entity, cancellationToken).ConfigureAwait(false);
|
|
if (saveNow)
|
|
await DbContext.SaveChangesAsync(cancellationToken).ConfigureAwait(false);
|
|
}
|
|
|
|
public virtual async Task AddRangeAsync(IEnumerable<T> entities, CancellationToken cancellationToken, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entities, nameof(entities));
|
|
await Entities.AddRangeAsync(entities, cancellationToken).ConfigureAwait(false);
|
|
if (saveNow)
|
|
await DbContext.SaveChangesAsync(cancellationToken).ConfigureAwait(false);
|
|
}
|
|
|
|
public virtual async Task UpdateAsync(T entity, CancellationToken cancellationToken, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entity, nameof(entity));
|
|
DbContext.Entry(entity).State = EntityState.Detached;
|
|
await DbContext.SaveChangesAsync(cancellationToken);
|
|
//DbContext.Entry(entity).State = EntityState.Modified;
|
|
DbContext.Update(entity);
|
|
//DbContext.Entry(entity).CurrentValues.SetValues(entity);
|
|
if (saveNow)
|
|
await DbContext.SaveChangesAsync(cancellationToken);
|
|
}
|
|
|
|
public virtual async Task UpdateRangeAsync(IEnumerable<T> entities, CancellationToken cancellationToken, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entities, nameof(entities));
|
|
Entities.UpdateRange(entities);
|
|
if (saveNow)
|
|
await DbContext.SaveChangesAsync(cancellationToken);
|
|
}
|
|
|
|
public virtual async Task DeleteAsync(T entity, CancellationToken cancellationToken, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entity, nameof(entity));
|
|
entity.IsRemoved = true;
|
|
Entities.Update(entity);
|
|
if (saveNow)
|
|
await DbContext.SaveChangesAsync(cancellationToken);
|
|
}
|
|
|
|
public async Task HardDeleteAsync(T entity, CancellationToken cancellationToken, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entity, nameof(entity));
|
|
Entities.Remove(entity);
|
|
if (saveNow)
|
|
await DbContext.SaveChangesAsync(cancellationToken);
|
|
}
|
|
|
|
public virtual async Task DeleteRangeAsync(IEnumerable<T> entities, CancellationToken cancellationToken, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entities, nameof(entities));
|
|
foreach (var apiEntity in entities)
|
|
{
|
|
apiEntity.IsRemoved = true;
|
|
Entities.Update(apiEntity);
|
|
}
|
|
if (saveNow)
|
|
await DbContext.SaveChangesAsync(cancellationToken);
|
|
}
|
|
#endregion
|
|
|
|
#region Sync Methods
|
|
public virtual T GetById(params object[] ids)
|
|
{
|
|
var ent = Entities.Find(ids);
|
|
Detach(ent);
|
|
return ent;
|
|
}
|
|
|
|
public virtual void Add(T entity, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entity, nameof(entity));
|
|
Entities.Add(entity);
|
|
if (saveNow)
|
|
DbContext.SaveChanges();
|
|
}
|
|
|
|
public virtual void AddRange(IEnumerable<T> entities, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entities, nameof(entities));
|
|
Entities.AddRange(entities);
|
|
if (saveNow)
|
|
DbContext.SaveChanges();
|
|
}
|
|
|
|
public virtual void Update(T entity, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entity, nameof(entity));
|
|
Detach(entity);
|
|
Entities.Update(entity);
|
|
DbContext.SaveChanges();
|
|
}
|
|
|
|
public virtual void UpdateRange(IEnumerable<T> entities, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entities, nameof(entities));
|
|
Entities.UpdateRange(entities);
|
|
if (saveNow)
|
|
DbContext.SaveChanges();
|
|
}
|
|
|
|
public virtual void Delete(T entity, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entity, nameof(entity));
|
|
Entities.Remove(entity);
|
|
if (saveNow)
|
|
DbContext.SaveChanges();
|
|
}
|
|
|
|
public virtual void DeleteRange(IEnumerable<T> entities, bool saveNow = true)
|
|
{
|
|
Assert.NotNull(entities, nameof(entities));
|
|
Entities.RemoveRange(entities);
|
|
if (saveNow)
|
|
DbContext.SaveChanges();
|
|
}
|
|
#endregion
|
|
|
|
#region Attach & Detach
|
|
public virtual void Detach(T entity)
|
|
{
|
|
Assert.NotNull(entity, nameof(entity));
|
|
var entry = DbContext.Entry(entity);
|
|
if (entry != null)
|
|
entry.State = EntityState.Detached;
|
|
}
|
|
|
|
public virtual void Attach(T entity)
|
|
{
|
|
Assert.NotNull(entity, nameof(entity));
|
|
if (DbContext.Entry(entity).State == EntityState.Detached)
|
|
Entities.Attach(entity);
|
|
}
|
|
#endregion
|
|
|
|
#region Explicit Loading
|
|
public virtual async Task LoadCollectionAsync<TProperty>(T entity, Expression<Func<T, IEnumerable<TProperty>>> collectionProperty, CancellationToken cancellationToken)
|
|
where TProperty : class
|
|
{
|
|
Attach(entity);
|
|
|
|
var collection = DbContext.Entry(entity).Collection(collectionProperty);
|
|
if (!collection.IsLoaded)
|
|
await collection.LoadAsync(cancellationToken).ConfigureAwait(false);
|
|
}
|
|
|
|
public virtual void LoadCollection<TProperty>(T entity, Expression<Func<T, IEnumerable<TProperty>>> collectionProperty)
|
|
where TProperty : class
|
|
{
|
|
Attach(entity);
|
|
var collection = DbContext.Entry(entity).Collection(collectionProperty);
|
|
if (!collection.IsLoaded)
|
|
collection.Load();
|
|
}
|
|
|
|
public virtual async Task LoadReferenceAsync<TProperty>(T entity, Expression<Func<T, TProperty>> referenceProperty, CancellationToken cancellationToken)
|
|
where TProperty : class
|
|
{
|
|
Attach(entity);
|
|
var reference = DbContext.Entry(entity).Reference(referenceProperty);
|
|
if (!reference.IsLoaded)
|
|
await reference.LoadAsync(cancellationToken).ConfigureAwait(false);
|
|
}
|
|
|
|
public virtual void LoadReference<TProperty>(T entity, Expression<Func<T, TProperty>> referenceProperty)
|
|
where TProperty : class
|
|
{
|
|
Attach(entity);
|
|
var reference = DbContext.Entry(entity).Reference(referenceProperty);
|
|
if (!reference.IsLoaded)
|
|
reference.Load();
|
|
}
|
|
#endregion
|
|
|
|
}
|
|
}
|