コード例 #1
0
ファイル: ProcessGroupHistory.cs プロジェクト: waldo2590/Rock
        /// <summary>
        /// Updates GroupLocationHistorical for any group locations in groups that have data group history enabled
        /// </summary>
        /// <param name="context">The context.</param>
        public void UpdateGroupLocationHistorical(IJobExecutionContext context)
        {
            var rockContext = new RockContext();
            var groupLocationHistoricalService = new GroupLocationHistoricalService(rockContext);
            var groupLocationService           = new GroupLocationService(rockContext);

            var groupLocationsWithHistoryEnabledQuery = groupLocationService.Queryable().Where(a => a.Group.GroupType.EnableGroupHistory == true).AsNoTracking();
            var groupLocationsHistoricalCurrentQuery  = groupLocationHistoricalService.Queryable().Where(a => a.CurrentRowIndicator == true).AsNoTracking();

            // Mark GroupLocationHistorical Rows as History ( CurrentRowIndicator = false, etc ) if any of the tracked field values change
            var groupLocationHistoricalNoLongerCurrentQuery = groupLocationsHistoricalCurrentQuery.Join(
                groupLocationsWithHistoryEnabledQuery,
                glh => glh.GroupLocationId,
                gl => gl.Id, (glh, gl) => new
            {
                GroupLocation           = gl,
                GroupLocationHistorical = glh
            })
                                                              .Where(a =>
                                                                     a.GroupLocation.GroupId != a.GroupLocationHistorical.GroupId ||
                                                                     (a.GroupLocation.GroupLocationTypeValueId != a.GroupLocation.GroupLocationTypeValueId) ||
                                                                     (a.GroupLocation.GroupLocationTypeValueId.HasValue && a.GroupLocation.GroupLocationTypeValue.Value != a.GroupLocationHistorical.GroupLocationTypeName) ||
                                                                     a.GroupLocation.LocationId != a.GroupLocationHistorical.LocationId ||
                                                                     a.GroupLocation.Location.ModifiedDateTime != a.GroupLocationHistorical.LocationModifiedDateTime ||
                                                                     (a.GroupLocation.Schedules.Select(s => new { ScheduleId = s.Id, s.ModifiedDateTime }).Except(a.GroupLocationHistorical.GroupLocationHistoricalSchedules.Select(hs => new { hs.ScheduleId, ModifiedDateTime = hs.ScheduleModifiedDateTime }))).Any()
                                                                     );

            var effectiveExpireDateTime            = RockDateTime.Now;
            int groupLocationsLoggedToHistory      = 0;
            int groupLocationsSaveToHistoryCurrent = 0;

            if (groupLocationHistoricalNoLongerCurrentQuery.Any())
            {
                var groupLocationHistoricalNoLongerCurrent = groupLocationHistoricalNoLongerCurrentQuery.Select(a => a.GroupLocationHistorical).AsNoTracking();

                groupLocationsLoggedToHistory = rockContext.BulkUpdate(groupLocationHistoricalNoLongerCurrent, glh => new GroupLocationHistorical
                {
                    CurrentRowIndicator = false,
                    ExpireDateTime      = effectiveExpireDateTime
                });
            }

            // Insert Group Locations (that have a group with GroupType.EnableGroupHistory) that don't have a CurrentRowIndicator row yet ( or don't have a CurrentRowIndicator because it was stamped with CurrentRowIndicator=false )
            var groupLocationsToAddToHistoricalCurrentsQuery = groupLocationsWithHistoryEnabledQuery.Where(gl => !groupLocationsHistoricalCurrentQuery.Any(glh => glh.GroupLocationId == gl.Id));

            if (groupLocationsToAddToHistoricalCurrentsQuery.Any())
            {
                List <GroupLocationHistorical> groupLocationHistoricalCurrentsToInsert = groupLocationsToAddToHistoricalCurrentsQuery
                                                                                         .Include(a => a.GroupLocationTypeValue)
                                                                                         .Include(a => a.Location).ToList()
                                                                                         .Select(gl => GroupLocationHistorical.CreateCurrentRowFromGroupLocation(gl, effectiveExpireDateTime)).ToList();

                groupLocationsSaveToHistoryCurrent = groupLocationHistoricalCurrentsToInsert.Count();

                // get the current max GroupLocatiionHistorical.Id to help narrow down which ones were inserted
                int groupLocationHistoricalStartId = groupLocationHistoricalService.Queryable().Max(a => ( int? )a.Id) ?? 0;

                rockContext.BulkInsert(groupLocationHistoricalCurrentsToInsert);

                // since we used BulkInsert, we'll need to go back and get the Ids and the associated GroupLocation's Schedules for the GroupLocationHistorical records that we just inserted
                var insertedGroupLocationHistoricalIdsWithSchedules = groupLocationHistoricalService.Queryable()
                                                                      .Where(a => a.Id > groupLocationHistoricalStartId && a.GroupLocation.Schedules.Any()).ToList()
                                                                      .Select(a => new { GroupLocationHistoricalId = a.Id, a.GroupLocation.Schedules });

                List <GroupLocationHistoricalSchedule> groupLocationHistoricalScheduleCurrentsToInsert = new List <GroupLocationHistoricalSchedule>();
                foreach (var insertedGroupLocationHistoricalIdWithSchedules in insertedGroupLocationHistoricalIdsWithSchedules)
                {
                    foreach (Schedule schedule in insertedGroupLocationHistoricalIdWithSchedules.Schedules)
                    {
                        groupLocationHistoricalScheduleCurrentsToInsert.Add(new GroupLocationHistoricalSchedule
                        {
                            GroupLocationHistoricalId = insertedGroupLocationHistoricalIdWithSchedules.GroupLocationHistoricalId,
                            ScheduleId               = schedule.Id,
                            ScheduleName             = schedule.ToString(),
                            ScheduleModifiedDateTime = schedule.ModifiedDateTime
                        });
                    }
                }

                if (groupLocationHistoricalScheduleCurrentsToInsert.Any())
                {
                    rockContext.BulkInsert(groupLocationHistoricalScheduleCurrentsToInsert);
                }
            }

            if (groupLocationsLoggedToHistory > 0)
            {
                _jobStatusMessages.Add($"Logged {groupLocationsLoggedToHistory} {"group location history snapshot".PluralizeIf( groupLocationsLoggedToHistory != 0 )}");
            }

            if (groupLocationsSaveToHistoryCurrent > 0)
            {
                int newGroupLocationsAddedToHistory = groupLocationsSaveToHistoryCurrent - groupLocationsLoggedToHistory;
                if (newGroupLocationsAddedToHistory > 0)
                {
                    _jobStatusMessages.Add($"Added {newGroupLocationsAddedToHistory} new {"group location history snapshot".PluralizeIf( newGroupLocationsAddedToHistory != 0 )}");
                }
            }
        }