I have a LINQ to entity unit test that needs to get employee's timeOut - timeIn for each day they worked in a week and sum them together. The method is fine when pulling sql data, but in the unit test I get the error: "This function can only be invoked from LINQ to Entities."
This seems like a very simple thing, but I've tried a lot of things and can't get the test to pass. Don't want to add a lot of code just for testing because that would defeat the purpose of the test(mentioned in questions similar from years back). I was wondering if there are any newer ways to get this to work without adding huge chunks of code that will complicate the method.
method:
#region CalculateTimeToPay(payrollWeekEnd)
public IQueryable<CalculatedHours> CalculateTimeToPay(DateTime payrollWeekStart, DateTime payrollWeekEnd)
{
var uow = container.Resolve<WWIncomeTaxDataHandlerUnitOfWork>();
var employeeHours = (from time in uow.Accounting.Repository.Find<V_Time>()
where (payrollWeekEnd >= time.PayTimeIn && time.PayTimeIn >= payrollWeekStart)
group time by new { EmployeeID = time.EmployeeID} into empGroup
select new CalculatedHours
{
EmployeeID = empGroup.Key.EmployeeID,
//TimeToPay = (empGroup.Sum(x => (SqlFunctions.DateDiff("second", x.PayTimeIn, x.PayTimeOut)) / 60.0 / 60.0)) ?? 0
//TimeToPay = empGroup.Sum(x => x.PayTimeOut - x.PayTimeIn) //empGroup.Sum(x => (SqlFunctions.DateDiff("second", x.PayTimeIn, x.PayTimeOut)) / 60.0 / 60.0) ?? 0
TimeToPay = (empGroup.Where(x => x.EmployeeID == empGroup.Key.EmployeeID).Sum(x => (SqlFunctions.DateDiff("second", x.PayTimeIn, x.PayTimeOut))/60.0/60.0)) ?? 0
});
//var employeeHours = (from time in uow.Accounting.Repository.Find<V_Time>()
// where (payrollWeekEnd >= time.PayTimeIn && time.PayTimeIn >= payrollWeekStart)
// group time by new { time.EmployeeID } into empGroup
// select new CalculatedHours
// {
// EmployeeID = empGroup.Key.EmployeeID,
// //TimeToPay = (empGroup.Sum(x => (SqlFunctions.DateDiff("second", x.PayTimeIn, x.PayTimeOut)) / 60.0 / 60.0)) ?? 0
// TimeToPay = (empGroup.Sum(x => (SqlFunctions.DateDiff("second", x.PayTimeIn, x.PayTimeOut)) / 60.0 / 60.0)) ?? 0
// //TimeToPay = (empGroup.Where(x => x.EmployeeID == empGroup.Key.EmployeeID).Sum(x => (SqlFunctions.DateDiff("second", x.PayTimeIn, x.PayTimeOut))/60.0/60.0)) ?? 0
// });
return employeeHours;
}
#endregion
test:
#region CalculateTimeToPay_IntegerEmployeeIDAndDateTimeWeekOfDate_IQueryableTimeToPay
[TestMethod]
public void CalculateTimeToPay_IntegerEmployeeIDAndDateTimeWeekOfDate_IQueryableTimeToPay()
{
//Arrange
var service = new WWIncomeTaxDataHandlerService("ProdSQL");
DateTime payrollWeekEnd = Convert.ToDateTime("2017-01-15");
DateTime payrollWeekStart = Convert.ToDateTime("2017-01-09");
var V_Times = new List<V_Time>()
{
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-05 08:00:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-05 16:00:00.000"), EmployeeID = 999 },
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-05 08:30:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-05 16:00:00.000"), EmployeeID = 777 },
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-05 08:45:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-05 16:00:00.000"), EmployeeID = 888 },
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-10 08:00:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-10 16:00:00.000"), EmployeeID = 999 },
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-10 08:30:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-10 16:00:00.000"), EmployeeID = 777 },
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-10 08:45:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-10 16:00:00.000"), EmployeeID = 888 },
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-11 08:00:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-11 16:00:00.000"), EmployeeID = 999 },
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-11 00:00:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-11 07:00:00.000"), EmployeeID = 777 },
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-11 08:00:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-11 16:00:00.000"), EmployeeID = 888 },
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-12 08:00:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-12 16:00:00.000"), EmployeeID = 999 },
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-12 08:00:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-12 16:44:00.000"), EmployeeID = 777 },
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-12 08:00:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-12 16:00:00.000"), EmployeeID = 888 },
new V_Time { PayTimeIn = Convert.ToDateTime("2017-01-14 08:00:00.000"), PayTimeOut = Convert.ToDateTime("2017-01-14 16:07:00.000"), EmployeeID = 777 }
};
var mockRepository = new Mock<IRepository>();
mockRepository.Setup(x => x.Find<V_Time>()).Returns(V_Times.AsQueryable());
var builder = BuildContainer();
builder.Register(x => mockRepository.Object).As<IRepository>();
var container = builder.Build();
var itrs = container.Resolve<WWIncomeTaxDataHandler.Domain.WWIncomeTaxDataHandlerService>();
var expected = new List<CalculatedHours>()
{
new CalculatedHours { EmployeeID = 999, TimeToPay = 24 },
new CalculatedHours { EmployeeID = 777, TimeToPay = 31.35},
new CalculatedHours { EmployeeID = 888, TimeToPay = 23.25}
};
//Act
var actual = itrs.CalculateTimeToPay(payrollWeekStart, payrollWeekEnd).ToList();
//Assert
var compareLogic = new CompareLogic();
var result = compareLogic.Compare(actual, expected);
Assert.IsTrue(result.AreEqual, result.DifferencesString);
}
#endregion