示例#1
0
 /// <summary>
 /// Categorizes the <paramref name="result"/> of scheduling recordings,
 /// returned through <paramref name="scheduleSuccesses"/> and <paramref name="scheduleConflicts"/>.
 /// </summary>
 /// <param name="result">The results of attempting to schedule recordings.</param>
 /// <param name="scheduleSuccesses">Returns the recordings that were successfully scheduled.</param>
 /// <param name="scheduleConflicts">Returns the recordings that were unsuccessfully scheduled.</param>
 public static void GetSuccessesAndConflicts(Dictionary <ScheduleRecording, ScheduledRecordingResult> result,
                                             out List <Guid> scheduleSuccesses,
                                             out Dictionary <ScheduleRecording, ScheduledRecordingInfo[]> scheduleConflicts)
 {
     scheduleSuccesses = new List <Guid>();
     scheduleConflicts = new Dictionary <ScheduleRecording, ScheduledRecordingInfo[]>();
     foreach (ScheduleRecording sr in result.Keys)
     {
         ScheduledRecordingResult scheduleResult = result[sr];
         if (!scheduleResult.ConflictsExist)
         {
             foreach (Guid id in scheduleResult.SessionIDs)
             {
                 scheduleSuccesses.Add(id);
             }
         }
         else
         {
             scheduleConflicts.Add(sr, scheduleResult.ConflictingSessions);
         }
     }
 }
示例#2
0
        /// <summary>
        /// Takes the recording client and authentication, and attempts to schedule sessions provided in <paramref name="schedule"/>.
        /// </summary>
        /// <param name="rrMgr">The client in which holds the information about the recorders available.</param>
        /// <param name="rrAuth">The authentication information for which to access the information from <paramref name="rrMgr"/>.</param>
        /// <param name="schedule">The recording schedule.</param>
        /// <param name="sender">The BackgroundWorker to make this method asynchronous.</param>
        /// <returns>The results of the scheduling attempt.</returns>
        public static Dictionary <ScheduleRecording, ScheduledRecordingResult> ScheduleRecordings(
            IRemoteRecorderManagement rrMgr,
            Utilities.RemoteRecorderManagement42.AuthenticationInfo rrAuth,
            List <ScheduleRecording> schedule,
            BackgroundWorker sender)
        {
            Dictionary <ScheduleRecording, ScheduledRecordingResult> result = new Dictionary <ScheduleRecording, ScheduledRecordingResult>();

            for (int i = 0; i < schedule.Count; i++)
            {
                if (sender != null)
                {
                    sender.ReportProgress(i + 1);
                }
                else
                {
                    Console.WriteLine("Scheduling recording " + (i + 1) + "/" + schedule.Count + "...");
                }
                ScheduleRecording scheduleRecording = schedule[i];
                try
                {
                    // Currently only concerned with 1 RR for each session
                    RecorderSettings rs = new RecorderSettings()
                    {
                        RecorderId = scheduleRecording.RecorderID
                    };
                    RecurringRecording recurring = null;
                    // need to check to make sure start date is on cadence and adjust as needed if recurring.
                    if ((scheduleRecording as RecurringRecording) != null)
                    {
                        scheduleRecording.StartDate = AdjustDateOntoCadence(
                            scheduleRecording.StartDate,
                            ((RecurringRecording)scheduleRecording).Cadence);
                        // since we need to schedule the first occurrence, this is for accurate success/conflict counting
                        recurring = new RecurringRecording((RecurringRecording)scheduleRecording);
                    }
                    ScheduledRecordingResult scheduledResult = rrMgr.ScheduleRecording(
                        rrAuth,
                        scheduleRecording.SessionName,
                        scheduleRecording.FolderID,
                        scheduleRecording.IsBroadcast || Properties.Settings.Default.ScheduleBroadcasts,
                        scheduleRecording.StartDate,
                        scheduleRecording.StartDate + scheduleRecording.Duration,
                        new RecorderSettings[] { rs });
                    result.Add(scheduleRecording, scheduledResult);
                    if ((scheduleRecording as RecurringRecording) != null && !result[scheduleRecording].ConflictsExist)
                    {
                        // need to transform recurring.Cadence to a DayOfWeek[]
                        DayOfWeek[] days = CadenceToArray(recurring.Cadence);
                        // update the dictionary since this is recurring recording.
                        scheduledResult = rrMgr.ScheduleRecurringRecording(rrAuth,
                                                                           result[scheduleRecording].SessionIDs[0],
                                                                           days,
                                                                           recurring.EndDate);
                        result.Add(recurring, scheduledResult);
                    }
                }
                catch
                {
                    // Since something went wrong with scheduling, still log it in result to report it later.
                    result.Add(scheduleRecording, new ScheduledRecordingResult()
                    {
                        ConflictsExist = true
                    });
                }
            }
            return(result);
        }
示例#3
0
        /// <summary>
        /// Makes a SOAP api call to schedule a recording
        /// </summary>
        private void ScheduleRecordings()
        {
            log.Debug("Sync started at: " + DateTime.Now.ToString());
            try
            {
                Schedule schedule = null;

                do
                {
                    using (SyllabusPlusDBContext db = new SyllabusPlusDBContext())
                    {
                        if (this.configSettings.OrderSyncById)
                        {
                            schedule =
                                db.SchedulesTable.Select(s => s)
                                .Where(s => (s.NumberOfAttempts <MAX_ATTEMPTS &&
                                                                 (!s.LastPanoptoSync.HasValue ||
                                                                  !s.PanoptoSyncSuccess.HasValue || s.PanoptoSyncSuccess == false) &&
                                                                 s.LastUpdate> s.LastPanoptoSync.Value))
                                .OrderBy(s => s.ID).FirstOrDefault();
                        }
                        else
                        {
                            schedule =
                                db.SchedulesTable.Select(s => s)
                                .Where(s => (s.NumberOfAttempts <MAX_ATTEMPTS &&
                                                                 (!s.LastPanoptoSync.HasValue ||
                                                                  !s.PanoptoSyncSuccess.HasValue || s.PanoptoSyncSuccess == false) &&
                                                                 s.LastUpdate> s.LastPanoptoSync.Value))
                                .OrderBy(s => s.LastUpdate).FirstOrDefault();
                        }

                        try
                        {
                            if (schedule != null)
                            {
                                log.Debug(
                                    String.Format("Attempting to sync a session. Name: {0}, Last update: {1}, Last Panopto sync: {2}, Panopto sync success: {3}, Number of attempts: {4}",
                                                  schedule.SessionName,
                                                  schedule.LastUpdate,
                                                  (schedule.LastPanoptoSync != null) ? (DateTime?)schedule.LastPanoptoSync.Value : null,
                                                  schedule.PanoptoSyncSuccess,
                                                  schedule.NumberOfAttempts));
                                if (!schedule.CancelSchedule.HasValue)
                                {
                                    ScheduledRecordingResult result = null;

                                    using (RemoteRecorderManagementWrapper remoteRecorderManagementWrapper
                                               = new RemoteRecorderManagementWrapper(
                                                     this.configSettings.PanoptoSite,
                                                     this.configSettings.PanoptoUserName,
                                                     this.configSettings.PanoptoPassword))
                                        using (SessionManagementWrapper sessionManagementWrapper
                                                   = new SessionManagementWrapper(
                                                         this.configSettings.PanoptoSite,
                                                         this.configSettings.PanoptoUserName,
                                                         this.configSettings.PanoptoPassword))
                                            using (UserManagementWrapper userManagementWrapper
                                                       = new UserManagementWrapper(
                                                             this.configSettings.PanoptoSite,
                                                             this.configSettings.PanoptoUserName,
                                                             this.configSettings.PanoptoPassword))


                                            {
                                                // Schedule session id will determine if need to create or update/delete the corresponding schedule
                                                if (schedule.ScheduledSessionId == null || schedule.ScheduledSessionId == Guid.Empty)
                                                {
                                                    log.Debug(schedule.SessionName + " is not associated with a session on the Panopto database. Attempting to schedule.");
                                                    result = VerifyFolderAndScheduleRecording(sessionManagementWrapper, schedule, remoteRecorderManagementWrapper);
                                                }
                                                else
                                                {
                                                    log.Debug(schedule.SessionName + " is already associated with a session on the Panopto database. Attempting to update schedule.");
                                                    Session scheduledSession = sessionManagementWrapper.GetSessionById((Guid)schedule.ScheduledSessionId);

                                                    // Check if either the primary or secondary remote recorder changed. If so, delete the old session and create a new session.
                                                    if (schedule.PrimaryRemoteRecorderId != scheduledSession.RemoteRecorderIds[0] ||
                                                        (scheduledSession.RemoteRecorderIds.Length > 1 && schedule.SecondaryRemoteRecorderId != scheduledSession.RemoteRecorderIds[1]))
                                                    {
                                                        log.Debug(schedule.SessionName + " has a different remote recorder. Moving the recording by deleting the existing scheduled session and creating a new scheduled session.");
                                                        sessionManagementWrapper.DeleteSessions((Guid)schedule.ScheduledSessionId);
                                                        // Reset the ScheduledSessionId in the DB just in case rescheduling the session fails the first time.
                                                        schedule.ScheduledSessionId = null;
                                                        result = VerifyFolderAndScheduleRecording(sessionManagementWrapper, schedule, remoteRecorderManagementWrapper);
                                                    }
                                                    else
                                                    {
                                                        // Check if name was updated in DB. If so, update the session name on the server.
                                                        if (scheduledSession.Name != schedule.SessionName)
                                                        {
                                                            log.Debug(String.Format("Updating the session name from {0} to {1}.", scheduledSession.Name, schedule.SessionName));
                                                            sessionManagementWrapper.UpdateSessionName((Guid)schedule.ScheduledSessionId, schedule.SessionName);
                                                        }
                                                        // Check if start time was updated in DB. If so, update the start time on the server. Could fail if there is a conflict.
                                                        if (scheduledSession.StartTime != schedule.StartTime)
                                                        {
                                                            log.Debug("Updating the scheduled session's start time.");
                                                            result = remoteRecorderManagementWrapper.UpdateRecordingTime(schedule);
                                                        }

                                                        if (scheduledSession.Duration != Convert.ToDouble(schedule.Duration) * 60)
                                                        {
                                                            log.Debug("Updating the scheduled duration.");
                                                            log.Debug($"Old duration in seconds {scheduledSession.Duration}, New duration in seconds {Convert.ToDouble(schedule.Duration) * 60}");
                                                            result = remoteRecorderManagementWrapper.UpdateRecordingTime(schedule);
                                                        }

                                                        if (schedule.PresenterUsername != userManagementWrapper.GetUserNameByID(scheduledSession.CreatorId))
                                                        {
                                                            log.Debug("Updating the session owner.");
                                                            if (schedule.PresenterUsername == null)

                                                            {
                                                                bool Username = CheckUsernameAndUpdateOwner(userManagementWrapper, sessionManagementWrapper, this.configSettings.PanoptoUserName, (Guid)schedule.ScheduledSessionId);
                                                                if (Username == true)
                                                                {
                                                                    log.Debug(schedule.SessionName + " has had owner updated to " + this.configSettings.PanoptoUserName);
                                                                }
                                                                else
                                                                {
                                                                    schedule.ErrorResponse = "Owner update failed. Username:"******"could not be located";
                                                                }
                                                            }

                                                            else
                                                            {
                                                                bool Username = CheckUsernameAndUpdateOwner(userManagementWrapper, sessionManagementWrapper, schedule.PresenterUsername, (Guid)schedule.ScheduledSessionId);
                                                                if (Username == true)
                                                                {
                                                                    log.Debug(schedule.SessionName + " has had owner updated to " + schedule.PresenterUsername);
                                                                }
                                                                else
                                                                {
                                                                    schedule.ErrorResponse = "Owner update failed. Username:"******"could not be located";
                                                                }
                                                            }
                                                        }


                                                        if (schedule.FolderId != scheduledSession.FolderId)
                                                        {
                                                            log.Debug($"Updating the folder session {schedule.SessionName} is scheduled to by deleting existing schedule and re-scheduling. Old folder {scheduledSession.FolderId}, New Folder {schedule.FolderId}");
                                                            sessionManagementWrapper.DeleteSessions((Guid)schedule.ScheduledSessionId);
                                                            // Reset the ScheduledSessionId in the DB just in case rescheduling the session fails the first time.
                                                            schedule.ScheduledSessionId = null;
                                                            result = VerifyFolderAndScheduleRecording(sessionManagementWrapper, schedule, remoteRecorderManagementWrapper);
                                                        }
                                                    }
                                                }
                                            }

                                    // If just updating the session name, the ScheduleRecordingResult object will be null.
                                    schedule.PanoptoSyncSuccess = result != null ? !result.ConflictsExist : true;
                                    using (UserManagementWrapper userManagementWrapper
                                               = new UserManagementWrapper(
                                                     this.configSettings.PanoptoSite,
                                                     this.configSettings.PanoptoUserName,
                                                     this.configSettings.PanoptoPassword))

                                        using (SessionManagementWrapper sessionManagementWrapper
                                                   = new SessionManagementWrapper(
                                                         this.configSettings.PanoptoSite,
                                                         this.configSettings.PanoptoUserName,
                                                         this.configSettings.PanoptoPassword))

                                            if ((bool)schedule.PanoptoSyncSuccess)
                                            {
                                                log.Debug(schedule.SessionName + " sync succeeded.");
                                                // Should only be 1 valid Session ID. ScheduleRecordingResult could be null if just updating the session name.
                                                if (result != null)
                                                {
                                                    schedule.ScheduledSessionId = result.SessionIDs.FirstOrDefault();
                                                    if (schedule.PresenterUsername != null)
                                                    {
                                                        bool Username = CheckUsernameAndUpdateOwner(userManagementWrapper, sessionManagementWrapper, schedule.PresenterUsername, schedule.ScheduledSessionId.Value);
                                                        if (Username == true)
                                                        {
                                                            log.Debug(schedule.SessionName + " has had owner updated to " + schedule.PresenterUsername);
                                                        }
                                                        else
                                                        {
                                                            schedule.ErrorResponse = "Owner update failed. Username:"******"could not be located";
                                                        }
                                                    }
                                                }
                                                schedule.NumberOfAttempts = 0;


                                                if (schedule.LastUpdate > DateTime.UtcNow)
                                                {
                                                    // In the rare case that the LastUpdateTime was in the future, set it to now, to ensure we don't repeat sync
                                                    schedule.LastUpdate = DateTime.UtcNow;
                                                }
                                            }
                                            else
                                            {
                                                schedule.ErrorResponse = this.xmlScheduledRecordingHelper.SerializeXMLToString(result);
                                                schedule.NumberOfAttempts++;
                                                if (schedule.NumberOfAttempts >= MAX_ATTEMPTS)
                                                {
                                                    log.Error(schedule.SessionName + " failed to sync.");
                                                }
                                            }
                                }

                                // Cancel Schedule has been requested and not succeeded
                                else if (schedule.CancelSchedule == false)
                                {
                                    log.Debug("Cancelling " + schedule.SessionName);
                                    using (SessionManagementWrapper sessionManagementWrapper
                                               = new SessionManagementWrapper(
                                                     this.configSettings.PanoptoSite,
                                                     this.configSettings.PanoptoUserName,
                                                     this.configSettings.PanoptoPassword))
                                    {
                                        sessionManagementWrapper.DeleteSessions((Guid)schedule.ScheduledSessionId);
                                        schedule.CancelSchedule     = true;
                                        schedule.PanoptoSyncSuccess = true;
                                        schedule.NumberOfAttempts   = 0;
                                        schedule.ErrorResponse      = null;
                                    }
                                }

                                schedule.LastPanoptoSync = DateTime.UtcNow;
                            }
                        }
                        catch (Exception ex)
                        {
                            log.Error("Error syncing schedule " + ex.ToString(), ex);
                            schedule.ErrorResponse      = ex.Message;
                            schedule.PanoptoSyncSuccess = false;
                            schedule.NumberOfAttempts++;
                        }

                        try
                        {
                            if (schedule != null)
                            {
                                log.Debug(
                                    String.Format("Attempting to save schedule back to database. Name: {0}, Last update: {1}, Last Panopto sync: {2}, Panopto sync success: {3}, Number of attempts: {4}",
                                                  schedule.SessionName,
                                                  schedule.LastUpdate,
                                                  (schedule.LastPanoptoSync != null) ? (DateTime?)schedule.LastPanoptoSync.Value : null,
                                                  schedule.PanoptoSyncSuccess,
                                                  schedule.NumberOfAttempts));

                                // Save after every iteration to prevent scheduling not being insync with Panopto Server
                                db.SaveChanges();
                            }
                        }
                        catch (Exception ex)
                        {
                            log.Error("Error saving to database " + ex.ToString(), ex);
                        }
                    }
                } while (schedule != null);
            }
            catch (Exception ex)
            {
                log.Error(ex.Message, ex);
            }
        }