private IEnumerable<TrainMovementResult> CallingBetween(IEnumerable<short> tiplocsFrom, IEnumerable<short> tiplocsTo, DateTime startDate, DateTime endDate, string atocCode, PowerType? powerType)
{
IEnumerable<RunningScheduleTrain> nextDaySchedules = null;
if (startDate.Date != endDate.Date)
{
nextDaySchedules = GetCallingBetweenSchedules(tiplocsFrom, tiplocsTo, endDate.Date, endDate.Date.TimeOfDay, endDate.TimeOfDay, atocCode, powerType);
endDate = startDate.Date.AddDays(1).AddMinutes(-1);
}
else
{
nextDaySchedules = Enumerable.Empty<RunningScheduleTrain>();
}
var allSchedules = GetCallingBetweenSchedules(tiplocsFrom, tiplocsTo, startDate.Date, startDate.TimeOfDay, endDate.TimeOfDay, atocCode, powerType)
.Union(nextDaySchedules)
.ToList();
// need to get live running data between these dates
startDate = startDate.Date;
endDate = endDate.Date.AddDays(1);
var allActualData = GetActualSchedule(allSchedules.SelectMany(s => s.ScheduleIds).Distinct(), startDate, endDate);
IEnumerable<ExtendedCancellation> cancellations = null;
IEnumerable<Reinstatement> reinstatements = null;
IEnumerable<ChangeOfOrigin> changeOfOrigins = null;
if (allActualData.Any())
{
using (DbConnection connection = CreateAndOpenConnection())
{
cancellations = GetCancellations(allActualData.Select(s => s.Id), connection)
.ToList();
reinstatements = GetReinstatements(allActualData.Select(s => s.Id), connection)
.ToList();
changeOfOrigins = GetChangeOfOrigins(allActualData.Select(s => s.Id), connection)
.ToList();
}
}
else
{
cancellations = Enumerable.Empty<ExtendedCancellation>();
reinstatements = Enumerable.Empty<Reinstatement>();
changeOfOrigins = Enumerable.Empty<ChangeOfOrigin>();
}
ICollection<TrainMovementResult> results = new List<TrainMovementResult>(allSchedules.Count());
foreach (var schedule in allSchedules)
{
var actual = allActualData.FirstOrDefault(a => schedule.ScheduleIds.Contains(a.ScheduleId));
var can = actual != null ?
cancellations.Where(c => c.TrainId == actual.Id).ToList() :
Enumerable.Empty<ExtendedCancellation>();
var rein = actual != null ?
reinstatements.Where(c => c.TrainId == actual.Id).ToList() :
Enumerable.Empty<Reinstatement>();
var coo = actual != null ?
changeOfOrigins.Where(c => c.TrainId == actual.Id).ToList() :
Enumerable.Empty<ChangeOfOrigin>();
results.Add(new TrainMovementResult
{
Schedule = schedule,
Actual = actual,
Cancellations = can,
Reinstatements = rein,
ChangeOfOrigins = coo
});
}
return results
.Where(s =>
{
return s.Schedule.Stops != null && (
s.Schedule.Stops.Any(st => tiplocsFrom.Contains(st.Tiploc.TiplocId)) &&
s.Schedule.Stops.Any(st => tiplocsTo.Contains(st.Tiploc.TiplocId)));
})
.OrderBy(s => s.Schedule.DateFor)
.ThenBy(s =>
{
if (s.Schedule.Stops == null || !s.Schedule.Stops.Any())
return default(TimeSpan?);
var tiplocStops = s.Schedule.Stops.Where(stop => tiplocsFrom.Contains(stop.Tiploc.TiplocId));
if (!tiplocStops.Any())
return default(TimeSpan?);
var firstStop = tiplocStops.First();
return firstStop.Departure ?? firstStop.PublicDeparture ?? firstStop.Pass;
});
}