From 089c56b56bd75135d323e3b0d00eb3ae87628d35 Mon Sep 17 00:00:00 2001 From: Dani Palou Date: Wed, 26 Jun 2019 15:19:27 +0200 Subject: [PATCH] MOBILE-3087 calendar: Fix 'lost' events when loading more events When loading more events, it could happen that some events weren't displayed because the timestart was recalculated using the time the request was made. E.g. if I loaded the first events and, 2 minutes later, I loaded more events, there were 2 minutes where we didn't get events. --- src/addon/calendar/pages/list/list.ts | 9 +++++++-- src/addon/calendar/providers/calendar.ts | 19 +++++++++++-------- 2 files changed, 18 insertions(+), 10 deletions(-) diff --git a/src/addon/calendar/pages/list/list.ts b/src/addon/calendar/pages/list/list.ts index 3418f0514..029234a74 100644 --- a/src/addon/calendar/pages/list/list.ts +++ b/src/addon/calendar/pages/list/list.ts @@ -21,6 +21,7 @@ import { AddonCalendarHelperProvider } from '../../providers/helper'; import { AddonCalendarSyncProvider } from '../../providers/calendar-sync'; import { CoreCoursesProvider } from '@core/courses/providers/courses'; import { CoreDomUtilsProvider } from '@providers/utils/dom'; +import { CoreTimeUtilsProvider } from '@providers/utils/time'; import { CoreUtilsProvider } from '@providers/utils/utils'; import { CoreSitesProvider } from '@providers/sites'; import { CoreLocalNotificationsProvider } from '@providers/local-notifications'; @@ -43,6 +44,7 @@ export class AddonCalendarListPage implements OnDestroy { @ViewChild(Content) content: Content; @ViewChild(CoreSplitViewComponent) splitviewCtrl: CoreSplitViewComponent; + protected initialTime = 0; protected daysLoaded = 0; protected emptyEventsTimes = 0; // Variable to identify consecutive calls returning 0 events. protected categoriesRetrieved = false; @@ -87,7 +89,7 @@ export class AddonCalendarListPage implements OnDestroy { localNotificationsProvider: CoreLocalNotificationsProvider, private popoverCtrl: PopoverController, private eventsProvider: CoreEventsProvider, private navCtrl: NavController, private appProvider: CoreAppProvider, private calendarOffline: AddonCalendarOfflineProvider, private calendarSync: AddonCalendarSyncProvider, - network: Network) { + network: Network, private timeUtils: CoreTimeUtilsProvider) { this.siteHomeId = sitesProvider.getCurrentSite().getSiteHomeId(); this.notificationsEnabled = localNotificationsProvider.isAvailable(); @@ -192,6 +194,7 @@ export class AddonCalendarListPage implements OnDestroy { * @return {Promise} Promise resolved when done. */ fetchData(refresh?: boolean, sync?: boolean, showErrors?: boolean): Promise { + this.initialTime = this.timeUtils.timestamp(); this.daysLoaded = 0; this.emptyEventsTimes = 0; this.isOnline = this.appProvider.isOnline(); @@ -269,7 +272,9 @@ export class AddonCalendarListPage implements OnDestroy { fetchEvents(refresh?: boolean): Promise { this.loadMoreError = false; - return this.calendarProvider.getEventsList(this.daysLoaded, AddonCalendarProvider.DAYS_INTERVAL).then((events) => { + return this.calendarProvider.getEventsList(this.initialTime, this.daysLoaded, AddonCalendarProvider.DAYS_INTERVAL) + .then((events) => { + this.daysLoaded += AddonCalendarProvider.DAYS_INTERVAL; if (events.length === 0) { this.emptyEventsTimes++; diff --git a/src/addon/calendar/providers/calendar.ts b/src/addon/calendar/providers/calendar.ts index 0b9af1e6b..c04ebaa2a 100644 --- a/src/addon/calendar/providers/calendar.ts +++ b/src/addon/calendar/providers/calendar.ts @@ -537,16 +537,20 @@ export class AddonCalendarProvider { * Get the events in a certain period. The period is calculated like this: * start time: now + daysToStart * end time: start time + daysInterval - * E.g. using provider.getEventsList(30, 30) is going to get the events starting after 30 days from now + * E.g. using provider.getEventsList(undefined, 30, 30) is going to get the events starting after 30 days from now * and ending before 60 days from now. * - * @param {number} [daysToStart=0] Number of days from now to start getting events. + * @param {number} [initialTime] Timestamp when the first fetch was done. If not defined, current time. + * @param {number} [daysToStart=0] Number of days from now to start getting events. * @param {number} [daysInterval=30] Number of days between timestart and timeend. * @param {string} [siteId] Site to get the events from. If not defined, use current site. * @return {Promise} Promise to be resolved when the participants are retrieved. */ - getEventsList(daysToStart: number = 0, daysInterval: number = AddonCalendarProvider.DAYS_INTERVAL, siteId?: string) - : Promise { + getEventsList(initialTime?: number, daysToStart: number = 0, daysInterval: number = AddonCalendarProvider.DAYS_INTERVAL, + siteId?: string): Promise { + + initialTime = initialTime || this.timeUtils.timestamp(); + return this.sitesProvider.getSite(siteId).then((site) => { siteId = site.getId(); const promises = []; @@ -561,9 +565,8 @@ export class AddonCalendarProvider { })); return Promise.all(promises).then(() => { - const now = this.timeUtils.timestamp(), - start = now + (CoreConstants.SECONDS_DAY * daysToStart), - end = start + (CoreConstants.SECONDS_DAY * daysInterval), + const start = initialTime + (CoreConstants.SECONDS_DAY * daysToStart), + end = start + (CoreConstants.SECONDS_DAY * daysInterval) - 1, data = { options: { userevents: 1, @@ -733,7 +736,7 @@ export class AddonCalendarProvider { return this.isDisabled(siteId).then((disabled) => { if (!disabled) { // Get first events. - return this.getEventsList(undefined, undefined, siteId).then((events) => { + return this.getEventsList(undefined, undefined, undefined, siteId).then((events) => { return this.scheduleEventsNotifications(events, siteId); }); }