I have a project. It is simple License Manager. I have such DbContext (Entity Framework 5):
public class EFDbContext : DbContext
{
public virtual IDbSet<License> Licenses { get; set; }
public virtual IDbSet<Department> Departments { get; set; }
public virtual IDbSet<Its> Itses { get; set; }
}
I created an IUnitOfWork implementation:
public class UnitOfWork : IUnitOfWork
{
private readonly EFDbContext Db;
private readonly LicenseRepository LicenseRepository;
private readonly DepartmentRepository DepartmentRepository;
private readonly ItsRepository ItsRepository;
public UnitOfWork(EFDbContext context)
{
Db = context;
DepartmentRepository = DepartmentRepository ?? (DepartmentRepository = new DepartmentRepository(Db));
ItsRepository = ItsRepository ?? (ItsRepository = new ItsRepository(Db));
LicenseRepository = LicenseRepository ?? (LicenseRepository = new LicenseRepository(Db));
}
public IRepository<License> Licenses
{
get { return LicenseRepository; }
}
public IRepository<Department> Departments
{
get { return DepartmentRepository; }
}
public IRepository<Its> Itses
{
get { return ItsRepository; }
}
}
And I have an IRepository implementation named LicenseRepository:
public class LicenseRepository : IRepository<License>
{
private EFDbContext Db;
public LicenseRepository(EFDbContext context)
{
Db = context;
}
public IQueryable<License> Items
{
get { return Db.Licenses.Include(lic => lic.Department).Include(lic => lic.Its); }
}
private bool CheckIfExist(string codeAct, int id)
{
return (id == 0)
? Db.Licenses.Any(license => license.CodeAct.Equals(codeAct))
: Db.Licenses.Any(license => license.CodeAct.Equals(codeAct) && license.Id != id);
}
private void Defend(License item)
{
Security sec = Security.Instance;
Its its = Db.Itses.FirstOrDefault(i => i.Id == item.ItsId);
item.CodeLic = item.CodeLic.ToUpper()/*.Replace("-", " - ")*/;
string hash = sec.GetHash(item.CodeLic.Replace(" - ", ""), (its == null) ? string.Empty : its.Salt);
item.CodeAct = hash.Insert(5," - ");
}
public IQueryable<License> GetOrderBy<TResult>(string order, IQueryable<License> items, Expression<Func<License, TResult>> key)
{
return (order == null || order.ToUpper() == "ASC") ? items.OrderBy(key) : items.OrderByDescending(key);
}
public void Edit(License item)
{
Defend(item);
if (CheckIfExist(item.CodeAct, item.Id)) throw new DbUpdateException("Error update");
if (item.Id == 0)
{
Db.Licenses.Add(item);
}
else
{
License dbEntry = Db.Licenses.Find(item.Id);
if (dbEntry != null)
{
dbEntry.CodeLic = item.CodeLic;
dbEntry.CodeAct = item.CodeAct;
dbEntry.Peom = item.Peom;
dbEntry.Phone = item.Phone;
dbEntry.Pib = item.Pib;
dbEntry.DepartmentId = item.DepartmentId;
dbEntry.ItsId = item.ItsId;
dbEntry.Dtime = item.Dtime;
}
}
Db.SaveChanges();
}
public License Delete(int id)
{
License dbEntry = Db.Licenses.Find(id);
if (dbEntry != null)
{
Db.Licenses.Remove(dbEntry);
Db.SaveChanges();
}
return dbEntry;
}
}
My LicenseController looks like:
public class LicenseController: Controller
{
private IUnitOfWork Repository;
public LicenseController(IUnitOfWork _repository)
{
Repository = _repository;
}
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Edit(LicenseViewModel model)
{
if (ModelState.IsValid) // валидация данных
{
model.License.DepartmentId = model.License.DepartmentId == 0 ? null : model.License.DepartmentId;
model.License.ItsId = model.License.ItsId == 0 ? null : model.License.ItsId;
if (model.License.Dtime == DateTime.MinValue)
{
model.License.Dtime = DateTime.Now;
}
model.License.CodeLic = string.Join(" - ", model.CodePart1, model.CodePart2, model.CodePart3,
model.CodePart4);
Repository.Licenses.Edit(model.License);
// хранится, пока мы их не прочитаем (ViewBag(не может хранить дольше текущего запроса) и Session(требует явного удаления) нам не подходят)
TempData["message"] = string.Format("Об'єкт \"{0}\" збережений", model.License.CodeLic);
return RedirectToAction("List");
}
// в случае неудачи
model.DropDownDepartment = GetDepartments(model.License.DepartmentId);
model.DropDownIts = GetItses(model.License.ItsId);
return View(model);
}
// another methods ...
}
I want to test if Edit method of Repository calls correctly when I pass correct Entity to it. My Mock class looks like:
private IDbSet<T> GetQueryableMockDbSet<T>(IQueryable<T> sourceList) where T: class
{
Mock<IDbSet<T>> mockSet = new Mock<IDbSet<T>>();
mockSet.As<IQueryable<T>>().Setup(t => t.Provider).Returns(sourceList.Provider);
mockSet.As<IQueryable<T>>().Setup(t => t.Expression).Returns(sourceList.Expression);
mockSet.As<IQueryable<T>>().Setup(t => t.ElementType).Returns(sourceList.ElementType);
mockSet.As<IQueryable<T>>().Setup(t => t.GetEnumerator()).Returns(sourceList.GetEnumerator());
return mockSet.Object;
}
[TestMethod]
public void CanSaveValidLicense()
{
// ARRANGE
// создали пустое имитированное хранилище
var mockContext = new Mock<EFDbContext>();
IUnitOfWork iuow = GetFakeRepository();
mockContext.Setup(context => context.Itses).Returns(GetQueryableMockDbSet(iuow.Itses.Items));
mockContext.Setup(context => context.Departments).Returns(GetQueryableMockDbSet(iuow.Departments.Items));
mockContext.Setup(context => context.Licenses).Returns(GetQueryableMockDbSet(iuow.Licenses.Items));
var mockRepo = new Mock<UnitOfWork>(mockContext.Object);
mockRepo.CallBase = true;
// создаем контроллер
LicenseController target = new LicenseController(mockRepo.Object);
// создаем объект типа License
LicenseViewModel lvm = new LicenseViewModel
{
License = new License
{
CodeAct = "ABCD",
CodeLic = "DCBA",
Peom = "111",
Phone = "777",
Pib = "BDV",
DepartmentId = 1,
ItsId = 1
}
};
// ACT
// пытаемся сохранить новосозданный объект
ActionResult result = target.Edit(lvm);
// ASSERT
// проверяем, что был вызван метод хранилища на сохранение
//mockContext.Verify(context => context.SaveChanges());
//licRep.Verify(repository => repository.Edit(lvm.License), Times.Once());
mockRepo.As<IRepository<License>>().Verify(work => work.Edit(lvm.License), Times.Once());
mockRepo.VerifyAll();
// проверяем, что сохранение прошло успешно - произошло перенаправление на страницу (не остались на текущей)
Assert.IsNotInstanceOfType(result, typeof (ViewResult));
}
I have a headache with Verify method. It throws NotSupportedException or if I try another way it throws another Exception. I'm new in unit-testing. So, can you please help me with this problem.
Aucun commentaire:
Enregistrer un commentaire