Merge pull request #2087 from dpalou/MOBILE-3068
MOBILE-3068 calendar: Autofetch day&month when event changedmain
commit
86ac4dad06
|
@ -285,14 +285,16 @@ export class AddonCalendarCalendarComponent implements OnInit, OnChanges, OnDest
|
||||||
/**
|
/**
|
||||||
* Refresh events.
|
* Refresh events.
|
||||||
*
|
*
|
||||||
* @param {boolean} [sync] Whether it should try to synchronize offline events.
|
* @param {boolean} [afterChange] Whether the refresh is done after an event has changed or has been synced.
|
||||||
* @param {boolean} [showErrors] Whether to show sync errors to the user.
|
|
||||||
* @return {Promise<any>} Promise resolved when done.
|
* @return {Promise<any>} Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
refreshData(sync?: boolean, showErrors?: boolean): Promise<any> {
|
refreshData(afterChange?: boolean): Promise<any> {
|
||||||
const promises = [];
|
const promises = [];
|
||||||
|
|
||||||
promises.push(this.calendarProvider.invalidateMonthlyEvents(this.year, this.month));
|
// Don't invalidate monthly events after a change, it has already been handled.
|
||||||
|
if (!afterChange) {
|
||||||
|
promises.push(this.calendarProvider.invalidateMonthlyEvents(this.year, this.month));
|
||||||
|
}
|
||||||
promises.push(this.coursesProvider.invalidateCategories(0, true));
|
promises.push(this.coursesProvider.invalidateCategories(0, true));
|
||||||
promises.push(this.calendarProvider.invalidateTimeFormat());
|
promises.push(this.calendarProvider.invalidateTimeFormat());
|
||||||
|
|
||||||
|
|
|
@ -225,14 +225,16 @@ export class AddonCalendarUpcomingEventsComponent implements OnInit, OnChanges,
|
||||||
/**
|
/**
|
||||||
* Refresh events.
|
* Refresh events.
|
||||||
*
|
*
|
||||||
* @param {boolean} [sync] Whether it should try to synchronize offline events.
|
* @param {boolean} [afterChange] Whether the refresh is done after an event has changed or has been synced.
|
||||||
* @param {boolean} [showErrors] Whether to show sync errors to the user.
|
|
||||||
* @return {Promise<any>} Promise resolved when done.
|
* @return {Promise<any>} Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
refreshData(sync?: boolean, showErrors?: boolean): Promise<any> {
|
refreshData(afterChange?: boolean): Promise<any> {
|
||||||
const promises = [];
|
const promises = [];
|
||||||
|
|
||||||
promises.push(this.calendarProvider.invalidateAllUpcomingEvents());
|
// Don't invalidate upcoming events after a change, it has already been handled.
|
||||||
|
if (!afterChange) {
|
||||||
|
promises.push(this.calendarProvider.invalidateAllUpcomingEvents());
|
||||||
|
}
|
||||||
promises.push(this.coursesProvider.invalidateCategories(0, true));
|
promises.push(this.coursesProvider.invalidateCategories(0, true));
|
||||||
promises.push(this.calendarProvider.invalidateLookAhead());
|
promises.push(this.calendarProvider.invalidateLookAhead());
|
||||||
promises.push(this.calendarProvider.invalidateTimeFormat());
|
promises.push(this.calendarProvider.invalidateTimeFormat());
|
||||||
|
|
|
@ -113,35 +113,35 @@ export class AddonCalendarDayPage implements OnInit, OnDestroy {
|
||||||
this.newEventObserver = eventsProvider.on(AddonCalendarProvider.NEW_EVENT_EVENT, (data) => {
|
this.newEventObserver = eventsProvider.on(AddonCalendarProvider.NEW_EVENT_EVENT, (data) => {
|
||||||
if (data && data.event) {
|
if (data && data.event) {
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.refreshData(true, false);
|
this.refreshData(true, false, true);
|
||||||
}
|
}
|
||||||
}, this.currentSiteId);
|
}, this.currentSiteId);
|
||||||
|
|
||||||
// Listen for new event discarded event. When it does, reload the data.
|
// Listen for new event discarded event. When it does, reload the data.
|
||||||
this.discardedObserver = eventsProvider.on(AddonCalendarProvider.NEW_EVENT_DISCARDED_EVENT, () => {
|
this.discardedObserver = eventsProvider.on(AddonCalendarProvider.NEW_EVENT_DISCARDED_EVENT, () => {
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.refreshData(true, false);
|
this.refreshData(true, false, true);
|
||||||
}, this.currentSiteId);
|
}, this.currentSiteId);
|
||||||
|
|
||||||
// Listen for events edited. When an event is edited, reload the data.
|
// Listen for events edited. When an event is edited, reload the data.
|
||||||
this.editEventObserver = eventsProvider.on(AddonCalendarProvider.EDIT_EVENT_EVENT, (data) => {
|
this.editEventObserver = eventsProvider.on(AddonCalendarProvider.EDIT_EVENT_EVENT, (data) => {
|
||||||
if (data && data.event) {
|
if (data && data.event) {
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.refreshData(true, false);
|
this.refreshData(true, false, true);
|
||||||
}
|
}
|
||||||
}, this.currentSiteId);
|
}, this.currentSiteId);
|
||||||
|
|
||||||
// Refresh data if calendar events are synchronized automatically.
|
// Refresh data if calendar events are synchronized automatically.
|
||||||
this.syncObserver = eventsProvider.on(AddonCalendarSyncProvider.AUTO_SYNCED, (data) => {
|
this.syncObserver = eventsProvider.on(AddonCalendarSyncProvider.AUTO_SYNCED, (data) => {
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.refreshData();
|
this.refreshData(false, false, true);
|
||||||
}, this.currentSiteId);
|
}, this.currentSiteId);
|
||||||
|
|
||||||
// Refresh data if calendar events are synchronized manually but not by this page.
|
// Refresh data if calendar events are synchronized manually but not by this page.
|
||||||
this.manualSyncObserver = eventsProvider.on(AddonCalendarSyncProvider.MANUAL_SYNCED, (data) => {
|
this.manualSyncObserver = eventsProvider.on(AddonCalendarSyncProvider.MANUAL_SYNCED, (data) => {
|
||||||
if (data && (data.source != 'day' || data.year != this.year || data.month != this.month || data.day != this.day)) {
|
if (data && (data.source != 'day' || data.year != this.year || data.month != this.month || data.day != this.day)) {
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.refreshData();
|
this.refreshData(false, false, true);
|
||||||
}
|
}
|
||||||
}, this.currentSiteId);
|
}, this.currentSiteId);
|
||||||
|
|
||||||
|
@ -153,7 +153,7 @@ export class AddonCalendarDayPage implements OnInit, OnDestroy {
|
||||||
this.deletedEvents.push(data.eventId);
|
this.deletedEvents.push(data.eventId);
|
||||||
} else {
|
} else {
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.refreshData();
|
this.refreshData(false, false, true);
|
||||||
}
|
}
|
||||||
}, this.currentSiteId);
|
}, this.currentSiteId);
|
||||||
|
|
||||||
|
@ -425,15 +425,19 @@ export class AddonCalendarDayPage implements OnInit, OnDestroy {
|
||||||
*
|
*
|
||||||
* @param {boolean} [sync] Whether it should try to synchronize offline events.
|
* @param {boolean} [sync] Whether it should try to synchronize offline events.
|
||||||
* @param {boolean} [showErrors] Whether to show sync errors to the user.
|
* @param {boolean} [showErrors] Whether to show sync errors to the user.
|
||||||
|
* @param {boolean} [afterChange] Whether the refresh is done after an event has changed or has been synced.
|
||||||
* @return {Promise<any>} Promise resolved when done.
|
* @return {Promise<any>} Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
refreshData(sync?: boolean, showErrors?: boolean): Promise<any> {
|
refreshData(sync?: boolean, showErrors?: boolean, afterChange?: boolean): Promise<any> {
|
||||||
this.syncIcon = 'spinner';
|
this.syncIcon = 'spinner';
|
||||||
|
|
||||||
const promises = [];
|
const promises = [];
|
||||||
|
|
||||||
|
// Don't invalidate day events after a change, it has already been handled.
|
||||||
|
if (!afterChange) {
|
||||||
|
promises.push(this.calendarProvider.invalidateDayEvents(this.year, this.month, this.day));
|
||||||
|
}
|
||||||
promises.push(this.calendarProvider.invalidateAllowedEventTypes());
|
promises.push(this.calendarProvider.invalidateAllowedEventTypes());
|
||||||
promises.push(this.calendarProvider.invalidateDayEvents(this.year, this.month, this.day));
|
|
||||||
promises.push(this.coursesProvider.invalidateCategories(0, true));
|
promises.push(this.coursesProvider.invalidateCategories(0, true));
|
||||||
promises.push(this.calendarProvider.invalidateTimeFormat());
|
promises.push(this.calendarProvider.invalidateTimeFormat());
|
||||||
|
|
||||||
|
|
|
@ -499,7 +499,7 @@ export class AddonCalendarEditEventPage implements OnInit, OnDestroy {
|
||||||
const numberOfRepetitions = formData.repeat ? formData.repeats :
|
const numberOfRepetitions = formData.repeat ? formData.repeats :
|
||||||
(data.repeateditall && this.event.othereventscount ? this.event.othereventscount + 1 : 1);
|
(data.repeateditall && this.event.othereventscount ? this.event.othereventscount + 1 : 1);
|
||||||
|
|
||||||
this.calendarHelper.invalidateRepeatedEventsOnCalendarForEvent(result.event, numberOfRepetitions).catch(() => {
|
return this.calendarHelper.refreshAfterChangeEvent(result.event, numberOfRepetitions).catch(() => {
|
||||||
// Ignore errors.
|
// Ignore errors.
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
|
@ -449,8 +449,8 @@ export class AddonCalendarEventPage implements OnDestroy {
|
||||||
|
|
||||||
if (sent) {
|
if (sent) {
|
||||||
// Event deleted, invalidate right days & months.
|
// Event deleted, invalidate right days & months.
|
||||||
promise = this.calendarHelper.invalidateRepeatedEventsOnCalendarForEvent(this.event,
|
promise = this.calendarHelper.refreshAfterChangeEvent(this.event, deleteAll ? this.event.eventcount : 1)
|
||||||
deleteAll ? this.event.eventcount : 1).catch(() => {
|
.catch(() => {
|
||||||
// Ignore errors.
|
// Ignore errors.
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -95,42 +95,42 @@ export class AddonCalendarIndexPage implements OnInit, OnDestroy {
|
||||||
this.newEventObserver = eventsProvider.on(AddonCalendarProvider.NEW_EVENT_EVENT, (data) => {
|
this.newEventObserver = eventsProvider.on(AddonCalendarProvider.NEW_EVENT_EVENT, (data) => {
|
||||||
if (data && data.event) {
|
if (data && data.event) {
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.refreshData(true, false);
|
this.refreshData(true, false, true);
|
||||||
}
|
}
|
||||||
}, this.currentSiteId);
|
}, this.currentSiteId);
|
||||||
|
|
||||||
// Listen for new event discarded event. When it does, reload the data.
|
// Listen for new event discarded event. When it does, reload the data.
|
||||||
this.discardedObserver = eventsProvider.on(AddonCalendarProvider.NEW_EVENT_DISCARDED_EVENT, () => {
|
this.discardedObserver = eventsProvider.on(AddonCalendarProvider.NEW_EVENT_DISCARDED_EVENT, () => {
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.refreshData(true, false);
|
this.refreshData(true, false, true);
|
||||||
}, this.currentSiteId);
|
}, this.currentSiteId);
|
||||||
|
|
||||||
// Listen for events edited. When an event is edited, reload the data.
|
// Listen for events edited. When an event is edited, reload the data.
|
||||||
this.editEventObserver = eventsProvider.on(AddonCalendarProvider.EDIT_EVENT_EVENT, (data) => {
|
this.editEventObserver = eventsProvider.on(AddonCalendarProvider.EDIT_EVENT_EVENT, (data) => {
|
||||||
if (data && data.event) {
|
if (data && data.event) {
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.refreshData(true, false);
|
this.refreshData(true, false, true);
|
||||||
}
|
}
|
||||||
}, this.currentSiteId);
|
}, this.currentSiteId);
|
||||||
|
|
||||||
// Refresh data if calendar events are synchronized automatically.
|
// Refresh data if calendar events are synchronized automatically.
|
||||||
this.syncObserver = eventsProvider.on(AddonCalendarSyncProvider.AUTO_SYNCED, (data) => {
|
this.syncObserver = eventsProvider.on(AddonCalendarSyncProvider.AUTO_SYNCED, (data) => {
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.refreshData();
|
this.refreshData(false, false, true);
|
||||||
}, this.currentSiteId);
|
}, this.currentSiteId);
|
||||||
|
|
||||||
// Refresh data if calendar events are synchronized manually but not by this page.
|
// Refresh data if calendar events are synchronized manually but not by this page.
|
||||||
this.manualSyncObserver = eventsProvider.on(AddonCalendarSyncProvider.MANUAL_SYNCED, (data) => {
|
this.manualSyncObserver = eventsProvider.on(AddonCalendarSyncProvider.MANUAL_SYNCED, (data) => {
|
||||||
if (data && data.source != 'index') {
|
if (data && data.source != 'index') {
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.refreshData();
|
this.refreshData(false, false, true);
|
||||||
}
|
}
|
||||||
}, this.currentSiteId);
|
}, this.currentSiteId);
|
||||||
|
|
||||||
// Update the events when an event is deleted.
|
// Update the events when an event is deleted.
|
||||||
this.deleteEventObserver = eventsProvider.on(AddonCalendarProvider.DELETED_EVENT_EVENT, (data) => {
|
this.deleteEventObserver = eventsProvider.on(AddonCalendarProvider.DELETED_EVENT_EVENT, (data) => {
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.refreshData();
|
this.refreshData(false, false, true);
|
||||||
}, this.currentSiteId);
|
}, this.currentSiteId);
|
||||||
|
|
||||||
// Update the "hasOffline" property if an event deleted in offline is restored.
|
// Update the "hasOffline" property if an event deleted in offline is restored.
|
||||||
|
@ -251,9 +251,10 @@ export class AddonCalendarIndexPage implements OnInit, OnDestroy {
|
||||||
*
|
*
|
||||||
* @param {boolean} [sync] Whether it should try to synchronize offline events.
|
* @param {boolean} [sync] Whether it should try to synchronize offline events.
|
||||||
* @param {boolean} [showErrors] Whether to show sync errors to the user.
|
* @param {boolean} [showErrors] Whether to show sync errors to the user.
|
||||||
|
* @param {boolean} [afterChange] Whether the refresh is done after an event has changed or has been synced.
|
||||||
* @return {Promise<any>} Promise resolved when done.
|
* @return {Promise<any>} Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
refreshData(sync?: boolean, showErrors?: boolean): Promise<any> {
|
refreshData(sync?: boolean, showErrors?: boolean, afterChange?: boolean): Promise<any> {
|
||||||
this.syncIcon = 'spinner';
|
this.syncIcon = 'spinner';
|
||||||
|
|
||||||
const promises = [];
|
const promises = [];
|
||||||
|
@ -262,9 +263,9 @@ export class AddonCalendarIndexPage implements OnInit, OnDestroy {
|
||||||
|
|
||||||
// Refresh the sub-component.
|
// Refresh the sub-component.
|
||||||
if (this.showCalendar && this.calendarComponent) {
|
if (this.showCalendar && this.calendarComponent) {
|
||||||
promises.push(this.calendarComponent.refreshData());
|
promises.push(this.calendarComponent.refreshData(afterChange));
|
||||||
} else if (!this.showCalendar && this.upcomingEventsComponent) {
|
} else if (!this.showCalendar && this.upcomingEventsComponent) {
|
||||||
promises.push(this.upcomingEventsComponent.refreshData());
|
promises.push(this.upcomingEventsComponent.refreshData(afterChange));
|
||||||
}
|
}
|
||||||
|
|
||||||
return Promise.all(promises).finally(() => {
|
return Promise.all(promises).finally(() => {
|
||||||
|
|
|
@ -159,7 +159,7 @@ export class AddonCalendarSyncProvider extends CoreSyncBaseProvider {
|
||||||
// Data has been sent to server. Now invalidate the WS calls.
|
// Data has been sent to server. Now invalidate the WS calls.
|
||||||
const promises = [
|
const promises = [
|
||||||
this.calendarProvider.invalidateEventsList(siteId),
|
this.calendarProvider.invalidateEventsList(siteId),
|
||||||
this.calendarHelper.invalidateRepeatedEventsOnCalendar(result.toinvalidate, siteId)
|
this.calendarHelper.refreshAfterChangeEvents(result.toinvalidate, siteId)
|
||||||
];
|
];
|
||||||
|
|
||||||
return Promise.all(promises).catch(() => {
|
return Promise.all(promises).catch(() => {
|
||||||
|
|
|
@ -15,7 +15,7 @@
|
||||||
import { Injectable } from '@angular/core';
|
import { Injectable } from '@angular/core';
|
||||||
import { CoreLoggerProvider } from '@providers/logger';
|
import { CoreLoggerProvider } from '@providers/logger';
|
||||||
import { CoreSitesProvider, CoreSiteSchema } from '@providers/sites';
|
import { CoreSitesProvider, CoreSiteSchema } from '@providers/sites';
|
||||||
import { CoreSite } from '@classes/site';
|
import { CoreSite, CoreSiteWSPreSets } from '@classes/site';
|
||||||
import { CoreCoursesProvider } from '@core/courses/providers/courses';
|
import { CoreCoursesProvider } from '@core/courses/providers/courses';
|
||||||
import { CoreAppProvider } from '@providers/app';
|
import { CoreAppProvider } from '@providers/app';
|
||||||
import { CoreTextUtilsProvider } from '@providers/utils/text';
|
import { CoreTextUtilsProvider } from '@providers/utils/text';
|
||||||
|
@ -971,10 +971,12 @@ export class AddonCalendarProvider {
|
||||||
* @param {number} day Day to get.
|
* @param {number} day Day to get.
|
||||||
* @param {number} [courseId] Course to get.
|
* @param {number} [courseId] Course to get.
|
||||||
* @param {number} [categoryId] Category to get.
|
* @param {number} [categoryId] Category to get.
|
||||||
|
* @param {boolean} [ignoreCache] True if it should ignore cached data (it will always fail in offline or server down).
|
||||||
* @param {string} [siteId] Site ID. If not defined, current site.
|
* @param {string} [siteId] Site ID. If not defined, current site.
|
||||||
* @return {Promise<any>} Promise resolved with the response.
|
* @return {Promise<any>} Promise resolved with the response.
|
||||||
*/
|
*/
|
||||||
getDayEvents(year: number, month: number, day: number, courseId?: number, categoryId?: number, siteId?: string): Promise<any> {
|
getDayEvents(year: number, month: number, day: number, courseId?: number, categoryId?: number, ignoreCache?: boolean,
|
||||||
|
siteId?: string): Promise<any> {
|
||||||
|
|
||||||
return this.sitesProvider.getSite(siteId).then((site) => {
|
return this.sitesProvider.getSite(siteId).then((site) => {
|
||||||
|
|
||||||
|
@ -991,11 +993,16 @@ export class AddonCalendarProvider {
|
||||||
data.categoryid = categoryId;
|
data.categoryid = categoryId;
|
||||||
}
|
}
|
||||||
|
|
||||||
const preSets = {
|
const preSets: CoreSiteWSPreSets = {
|
||||||
cacheKey: this.getDayEventsCacheKey(year, month, day, courseId, categoryId),
|
cacheKey: this.getDayEventsCacheKey(year, month, day, courseId, categoryId),
|
||||||
updateFrequency: CoreSite.FREQUENCY_SOMETIMES
|
updateFrequency: CoreSite.FREQUENCY_SOMETIMES
|
||||||
};
|
};
|
||||||
|
|
||||||
|
if (ignoreCache) {
|
||||||
|
preSets.getFromCache = false;
|
||||||
|
preSets.emergencyCache = false;
|
||||||
|
}
|
||||||
|
|
||||||
return site.read('core_calendar_get_calendar_day_view', data, preSets).then((response) => {
|
return site.read('core_calendar_get_calendar_day_view', data, preSets).then((response) => {
|
||||||
this.storeEventsInLocalDB(response.events, siteId);
|
this.storeEventsInLocalDB(response.events, siteId);
|
||||||
|
|
||||||
|
@ -1159,7 +1166,6 @@ export class AddonCalendarProvider {
|
||||||
return site.getDb().getRecords(AddonCalendarProvider.EVENTS_TABLE, {repeatid: repeatId});
|
return site.getDb().getRecords(AddonCalendarProvider.EVENTS_TABLE, {repeatid: repeatId});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get monthly calendar events.
|
* Get monthly calendar events.
|
||||||
*
|
*
|
||||||
|
@ -1167,10 +1173,12 @@ export class AddonCalendarProvider {
|
||||||
* @param {number} month Month to get.
|
* @param {number} month Month to get.
|
||||||
* @param {number} [courseId] Course to get.
|
* @param {number} [courseId] Course to get.
|
||||||
* @param {number} [categoryId] Category to get.
|
* @param {number} [categoryId] Category to get.
|
||||||
|
* @param {boolean} [ignoreCache] True if it should ignore cached data (it will always fail in offline or server down).
|
||||||
* @param {string} [siteId] Site ID. If not defined, current site.
|
* @param {string} [siteId] Site ID. If not defined, current site.
|
||||||
* @return {Promise<any>} Promise resolved with the response.
|
* @return {Promise<any>} Promise resolved with the response.
|
||||||
*/
|
*/
|
||||||
getMonthlyEvents(year: number, month: number, courseId?: number, categoryId?: number, siteId?: string): Promise<any> {
|
getMonthlyEvents(year: number, month: number, courseId?: number, categoryId?: number, ignoreCache?: boolean, siteId?: string)
|
||||||
|
: Promise<any> {
|
||||||
|
|
||||||
return this.sitesProvider.getSite(siteId).then((site) => {
|
return this.sitesProvider.getSite(siteId).then((site) => {
|
||||||
|
|
||||||
|
@ -1180,7 +1188,7 @@ export class AddonCalendarProvider {
|
||||||
};
|
};
|
||||||
|
|
||||||
// This parameter requires Moodle 3.5.
|
// This parameter requires Moodle 3.5.
|
||||||
if ( site.isVersionGreaterEqualThan('3.5')) {
|
if (site.isVersionGreaterEqualThan('3.5')) {
|
||||||
// Set mini to 1 to prevent returning the course selector HTML.
|
// Set mini to 1 to prevent returning the course selector HTML.
|
||||||
data.mini = 1;
|
data.mini = 1;
|
||||||
}
|
}
|
||||||
|
@ -1192,11 +1200,16 @@ export class AddonCalendarProvider {
|
||||||
data.categoryid = categoryId;
|
data.categoryid = categoryId;
|
||||||
}
|
}
|
||||||
|
|
||||||
const preSets = {
|
const preSets: CoreSiteWSPreSets = {
|
||||||
cacheKey: this.getMonthlyEventsCacheKey(year, month, courseId, categoryId),
|
cacheKey: this.getMonthlyEventsCacheKey(year, month, courseId, categoryId),
|
||||||
updateFrequency: CoreSite.FREQUENCY_SOMETIMES
|
updateFrequency: CoreSite.FREQUENCY_SOMETIMES
|
||||||
};
|
};
|
||||||
|
|
||||||
|
if (ignoreCache) {
|
||||||
|
preSets.getFromCache = false;
|
||||||
|
preSets.emergencyCache = false;
|
||||||
|
}
|
||||||
|
|
||||||
return site.read('core_calendar_get_calendar_monthly_view', data, preSets).then((response) => {
|
return site.read('core_calendar_get_calendar_monthly_view', data, preSets).then((response) => {
|
||||||
response.weeks.forEach((week) => {
|
response.weeks.forEach((week) => {
|
||||||
week.days.forEach((day) => {
|
week.days.forEach((day) => {
|
||||||
|
@ -1253,10 +1266,11 @@ export class AddonCalendarProvider {
|
||||||
*
|
*
|
||||||
* @param {number} [courseId] Course to get.
|
* @param {number} [courseId] Course to get.
|
||||||
* @param {number} [categoryId] Category to get.
|
* @param {number} [categoryId] Category to get.
|
||||||
|
* @param {boolean} [ignoreCache] True if it should ignore cached data (it will always fail in offline or server down).
|
||||||
* @param {string} [siteId] Site ID. If not defined, current site.
|
* @param {string} [siteId] Site ID. If not defined, current site.
|
||||||
* @return {Promise<any>} Promise resolved with the response.
|
* @return {Promise<any>} Promise resolved with the response.
|
||||||
*/
|
*/
|
||||||
getUpcomingEvents(courseId?: number, categoryId?: number, siteId?: string): Promise<any> {
|
getUpcomingEvents(courseId?: number, categoryId?: number, ignoreCache?: boolean, siteId?: string): Promise<any> {
|
||||||
|
|
||||||
return this.sitesProvider.getSite(siteId).then((site) => {
|
return this.sitesProvider.getSite(siteId).then((site) => {
|
||||||
|
|
||||||
|
@ -1269,11 +1283,16 @@ export class AddonCalendarProvider {
|
||||||
data.categoryid = categoryId;
|
data.categoryid = categoryId;
|
||||||
}
|
}
|
||||||
|
|
||||||
const preSets = {
|
const preSets: CoreSiteWSPreSets = {
|
||||||
cacheKey: this.getUpcomingEventsCacheKey(courseId, categoryId),
|
cacheKey: this.getUpcomingEventsCacheKey(courseId, categoryId),
|
||||||
updateFrequency: CoreSite.FREQUENCY_SOMETIMES
|
updateFrequency: CoreSite.FREQUENCY_SOMETIMES
|
||||||
};
|
};
|
||||||
|
|
||||||
|
if (ignoreCache) {
|
||||||
|
preSets.getFromCache = false;
|
||||||
|
preSets.emergencyCache = false;
|
||||||
|
}
|
||||||
|
|
||||||
return site.read('core_calendar_get_calendar_upcoming_view', data, preSets).then((response) => {
|
return site.read('core_calendar_get_calendar_upcoming_view', data, preSets).then((response) => {
|
||||||
this.storeEventsInLocalDB(response.events, siteId);
|
this.storeEventsInLocalDB(response.events, siteId);
|
||||||
|
|
||||||
|
|
|
@ -342,29 +342,36 @@ export class AddonCalendarHelperProvider {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Invalidate all calls from calendar WS calls.
|
* Refresh the month & day for several created/edited/deleted events, and invalidate the months & days
|
||||||
|
* for their repeated events if needed.
|
||||||
*
|
*
|
||||||
* @param {{event: any, repeated: number}[]} events Events that have been touched and number of times each event is repeated.
|
* @param {{event: any, repeated: number}[]} events Events that have been touched and number of times each event is repeated.
|
||||||
* @param {string} [siteId] Site ID. If not defined, current site.
|
* @param {string} [siteId] Site ID. If not defined, current site.
|
||||||
* @return {Promise<any>} Resolved when done.
|
* @return {Promise<any>} Resolved when done.
|
||||||
*/
|
*/
|
||||||
invalidateRepeatedEventsOnCalendar(events: {event: any, repeated: number}[], siteId?: string): Promise<any> {
|
refreshAfterChangeEvents(events: {event: any, repeated: number}[], siteId?: string): Promise<any> {
|
||||||
return this.sitesProvider.getSite(siteId).then((site) => {
|
return this.sitesProvider.getSite(siteId).then((site) => {
|
||||||
const timestarts = [];
|
const fetchTimestarts = [],
|
||||||
|
invalidateTimestarts = [];
|
||||||
|
|
||||||
|
// Always fetch upcoming events.
|
||||||
|
const upcomingPromise = this.calendarProvider.getUpcomingEvents(undefined, undefined, true, site.id).catch(() => {
|
||||||
|
// Ignore errors.
|
||||||
|
});
|
||||||
|
|
||||||
// Invalidate the events and get the timestarts so we can invalidate months & days.
|
// Invalidate the events and get the timestarts so we can invalidate months & days.
|
||||||
return this.utils.allPromises(events.map((eventData) => {
|
return this.utils.allPromises([upcomingPromise].concat(events.map((eventData) => {
|
||||||
|
|
||||||
if (eventData.repeated > 1) {
|
if (eventData.repeated > 1) {
|
||||||
if (eventData.event.repeatid) {
|
if (eventData.event.repeatid) {
|
||||||
// Being edited or deleted.
|
// Being edited or deleted.
|
||||||
// We need to calculate the days to invalidate because the event date could have changed.
|
// We need to calculate the days to invalidate because the event date could have changed.
|
||||||
// We don't know if the repeated events are before or after this one, invalidate them all.
|
// We don't know if the repeated events are before or after this one, invalidate them all.
|
||||||
timestarts.push(eventData.event.timestart);
|
fetchTimestarts.push(eventData.event.timestart);
|
||||||
|
|
||||||
for (let i = 1; i < eventData.repeated; i++) {
|
for (let i = 1; i < eventData.repeated; i++) {
|
||||||
timestarts.push(eventData.event.timestart + CoreConstants.SECONDS_DAY * 7 * i);
|
invalidateTimestarts.push(eventData.event.timestart + CoreConstants.SECONDS_DAY * 7 * i);
|
||||||
timestarts.push(eventData.event.timestart - CoreConstants.SECONDS_DAY * 7 * i);
|
invalidateTimestarts.push(eventData.event.timestart - CoreConstants.SECONDS_DAY * 7 * i);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get the repeated events to invalidate them.
|
// Get the repeated events to invalidate them.
|
||||||
|
@ -378,48 +385,66 @@ export class AddonCalendarHelperProvider {
|
||||||
} else {
|
} else {
|
||||||
// Being added.
|
// Being added.
|
||||||
let time = eventData.event.timestart;
|
let time = eventData.event.timestart;
|
||||||
while (eventData.repeated > 0) {
|
fetchTimestarts.push(time);
|
||||||
timestarts.push(time);
|
|
||||||
|
while (eventData.repeated > 1) {
|
||||||
time += CoreConstants.SECONDS_DAY * 7;
|
time += CoreConstants.SECONDS_DAY * 7;
|
||||||
eventData.repeated--;
|
eventData.repeated--;
|
||||||
|
invalidateTimestarts.push(time);
|
||||||
}
|
}
|
||||||
|
|
||||||
return Promise.resolve();
|
return Promise.resolve();
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// Not repeated.
|
// Not repeated.
|
||||||
timestarts.push(eventData.event.timestart);
|
fetchTimestarts.push(eventData.event.timestart);
|
||||||
|
|
||||||
return this.calendarProvider.invalidateEvent(eventData.event.id);
|
return this.calendarProvider.invalidateEvent(eventData.event.id);
|
||||||
}
|
}
|
||||||
|
|
||||||
})).finally(() => {
|
}))).finally(() => {
|
||||||
const invalidatedMonths = {},
|
const treatedMonths = {},
|
||||||
invalidatedDays = {};
|
treatedDays = {};
|
||||||
|
|
||||||
return this.utils.allPromises([
|
return this.utils.allPromises([
|
||||||
this.calendarProvider.invalidateAllUpcomingEvents(),
|
this.calendarProvider.invalidateAllUpcomingEvents(),
|
||||||
|
|
||||||
// Invalidate months and days.
|
// Fetch or invalidate months and days.
|
||||||
this.utils.allPromises(timestarts.map((time) => {
|
this.utils.allPromises(fetchTimestarts.concat(invalidateTimestarts).map((time, index) => {
|
||||||
const promises = [],
|
const promises = [],
|
||||||
day = moment(new Date(time * 1000)),
|
day = moment(new Date(time * 1000)),
|
||||||
monthId = this.getMonthId(day.year(), day.month() + 1),
|
monthId = this.getMonthId(day.year(), day.month() + 1),
|
||||||
dayId = monthId + '#' + day.date();
|
dayId = monthId + '#' + day.date();
|
||||||
|
|
||||||
if (!invalidatedMonths[monthId]) {
|
if (!treatedMonths[monthId]) {
|
||||||
// Month not invalidated already, do it now.
|
// Month not treated already, do it now.
|
||||||
invalidatedMonths[monthId] = monthId;
|
treatedMonths[monthId] = monthId;
|
||||||
|
|
||||||
promises.push(this.calendarProvider.invalidateMonthlyEvents(day.year(), day.month() + 1, site.id));
|
if (index < fetchTimestarts.length) {
|
||||||
|
promises.push(this.calendarProvider.getMonthlyEvents(day.year(), day.month() + 1, undefined,
|
||||||
|
undefined, true, site.id).catch(() => {
|
||||||
|
|
||||||
|
// Ignore errors.
|
||||||
|
}));
|
||||||
|
} else {
|
||||||
|
promises.push(this.calendarProvider.invalidateMonthlyEvents(day.year(), day.month() + 1, site.id));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!invalidatedDays[dayId]) {
|
if (!treatedDays[dayId]) {
|
||||||
// Day not invalidated already, do it now.
|
// Day not invalidated already, do it now.
|
||||||
invalidatedDays[dayId] = dayId;
|
treatedDays[dayId] = dayId;
|
||||||
|
|
||||||
promises.push(this.calendarProvider.invalidateDayEvents(day.year(), day.month() + 1, day.date(),
|
if (index < fetchTimestarts.length) {
|
||||||
site.id));
|
promises.push(this.calendarProvider.getDayEvents(day.year(), day.month() + 1, day.date(),
|
||||||
|
undefined, undefined, true, site.id).catch(() => {
|
||||||
|
|
||||||
|
// Ignore errors.
|
||||||
|
}));
|
||||||
|
} else {
|
||||||
|
promises.push(this.calendarProvider.invalidateDayEvents(day.year(), day.month() + 1, day.date(),
|
||||||
|
site.id));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return this.utils.allPromises(promises);
|
return this.utils.allPromises(promises);
|
||||||
|
@ -430,14 +455,15 @@ export class AddonCalendarHelperProvider {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Invalidate all calls from calendar WS calls.
|
* Refresh the month & day for a created/edited/deleted event, and invalidate the months & days
|
||||||
|
* for their repeated events if needed.
|
||||||
*
|
*
|
||||||
* @param {any} event Event that has been touched.
|
* @param {any} event Event that has been touched.
|
||||||
* @param {number} repeated Number of times the event is repeated.
|
* @param {number} repeated Number of times the event is repeated.
|
||||||
* @param {string} [siteId] Site ID. If not defined, current site.
|
* @param {string} [siteId] Site ID. If not defined, current site.
|
||||||
* @return {Promise<any>} Resolved when done.
|
* @return {Promise<any>} Resolved when done.
|
||||||
*/
|
*/
|
||||||
invalidateRepeatedEventsOnCalendarForEvent(event: any, repeated: number, siteId?: string): Promise<any> {
|
refreshAfterChangeEvent(event: any, repeated: number, siteId?: string): Promise<any> {
|
||||||
return this.invalidateRepeatedEventsOnCalendar([{event: event, repeated: repeated}], siteId);
|
return this.refreshAfterChangeEvents([{event: event, repeated: repeated}], siteId);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue