Fix duplicated events in other users calendar if its subfolders are active (#5340)

Differential Revision: https://git.kolab.org/D94
This commit is contained in:
Aleksander Machniak 2016-03-02 16:45:30 +01:00
parent e3d70bbad6
commit b01894ee2d
4 changed files with 61 additions and 19 deletions

View file

@ -786,6 +786,22 @@ class calendar extends rcube_plugin
case "subscribe": case "subscribe":
if (!$this->driver->subscribe_calendar($cal)) if (!$this->driver->subscribe_calendar($cal))
$this->rc->output->show_message($this->gettext('errorsaving'), 'error'); $this->rc->output->show_message($this->gettext('errorsaving'), 'error');
else {
$calendars = $this->driver->list_calendars();
$calendar = $calendars[$cal['id']];
// find parent folder and check if it's a "user calendar"
// if it's also activated we need to refresh it (#5340)
while ($calendar['parent']) {
if (isset($calendars[$calendar['parent']]))
$calendar = $calendars[$calendar['parent']];
else
break;
}
if ($calendar['id'] != $cal['id'] && $calendar['active'] && $calendar['group'] == "other user")
$this->rc->output->command('plugin.refresh_source', $calendar['id']);
}
return; return;
case "search": case "search":
$results = array(); $results = array();

View file

@ -2961,6 +2961,15 @@ function rcube_calendar_ui(settings)
return false; return false;
}; };
this.calendar_refresh_source = function(id)
{
// got race-conditions fc.currentFetchID when using refetchEvents,
// so we remove and add the source instead
// fc.fullCalendar('refetchEvents', me.calendars[id]);
fc.fullCalendar('removeEventSource', me.calendars[id]);
fc.fullCalendar('addEventSource', me.calendars[id]);
};
this.calendar_destroy_source = function(id) this.calendar_destroy_source = function(id)
{ {
var delete_ids = []; var delete_ids = [];
@ -4238,6 +4247,7 @@ window.rcmail && rcmail.addEventListener('init', function(evt) {
rcmail.register_command('add-resource', function(){ cal.add_resource2event(); }, false); rcmail.register_command('add-resource', function(){ cal.add_resource2event(); }, false);
// register callback commands // register callback commands
rcmail.addEventListener('plugin.refresh_source', function(data) { cal.calendar_refresh_source(data); });
rcmail.addEventListener('plugin.destroy_source', function(p){ cal.calendar_destroy_source(p.id); }); rcmail.addEventListener('plugin.destroy_source', function(p){ cal.calendar_destroy_source(p.id); });
rcmail.addEventListener('plugin.unlock_saving', function(p){ cal.unlock_saving(); }); rcmail.addEventListener('plugin.unlock_saving', function(p){ cal.unlock_saving(); });
rcmail.addEventListener('plugin.refresh_calendar', function(p){ cal.refresh(p); }); rcmail.addEventListener('plugin.refresh_calendar', function(p){ cal.refresh(p); });

View file

@ -225,11 +225,11 @@ class kolab_user_calendar extends kolab_calendar
} }
} }
// aggregate all calendar folders the user shares (but are not subscribed) // aggregate all calendar folders the user shares (but are not activated)
foreach (kolab_storage::list_user_folders($this->userdata, 'event', false) as $foldername) { foreach (kolab_storage::list_user_folders($this->userdata, 'event', 2) as $foldername) {
$cal = new kolab_calendar($foldername, $this->cal); $cal = new kolab_calendar($foldername, $this->cal);
foreach ($cal->list_events($start, $end, $search, 1) as $event) { foreach ($cal->list_events($start, $end, $search, 1) as $event) {
$this->events[$event['id']] = $event; $this->events[$event['id'] ?: $event['uid']] = $event;
$this->timeindex[$this->time_key($event)] = $event['id']; $this->timeindex[$this->time_key($event)] = $event['id'];
} }
} }

View file

@ -778,11 +778,7 @@ class kolab_storage
if (!$filter) { if (!$filter) {
// Get ALL folders list, standard way // Get ALL folders list, standard way
if ($subscribed) { if ($subscribed) {
$folders = self::$imap->list_folders_subscribed($root, $mbox); $folders = self::_imap_list_subscribed($root, $mbox);
// add temporarily subscribed folders
if (self::$with_tempsubs && is_array($_SESSION['kolab_subscribed_folders'])) {
$folders = array_unique(array_merge($folders, $_SESSION['kolab_subscribed_folders']));
}
} }
else { else {
$folders = self::_imap_list_folders($root, $mbox); $folders = self::_imap_list_folders($root, $mbox);
@ -819,12 +815,7 @@ class kolab_storage
// Get folders list // Get folders list
if ($subscribed) { if ($subscribed) {
$folders = self::$imap->list_folders_subscribed($root, $mbox); $folders = self::_imap_list_subscribed($root, $mbox);
// add temporarily subscribed folders
if (self::$with_tempsubs && is_array($_SESSION['kolab_subscribed_folders'])) {
$folders = array_unique(array_merge($folders, $_SESSION['kolab_subscribed_folders']));
}
} }
else { else {
$folders = self::_imap_list_folders($root, $mbox); $folders = self::_imap_list_folders($root, $mbox);
@ -887,6 +878,21 @@ class kolab_storage
return $folders; return $folders;
} }
/**
* Wrapper for rcube_imap::list_folders_subscribed()
* with support for temporarily subscribed folders
*/
protected static function _imap_list_subscribed($root, $mbox)
{
$folders = self::$imap->list_folders_subscribed($root, $mbox);
// add temporarily subscribed folders
if (self::$with_tempsubs && is_array($_SESSION['kolab_subscribed_folders'])) {
$folders = array_unique(array_merge($folders, $_SESSION['kolab_subscribed_folders']));
}
return $folders;
}
/** /**
* Search for shared or otherwise not listed groupware folders the user has access * Search for shared or otherwise not listed groupware folders the user has access
@ -1490,12 +1496,12 @@ class kolab_storage
* *
* @param array User entry from LDAP * @param array User entry from LDAP
* @param string Data type to list folders for (contact,event,task,journal,file,note,mail,configuration) * @param string Data type to list folders for (contact,event,task,journal,file,note,mail,configuration)
* @param boolean Return subscribed folders only (null to use configured subscription mode) * @param int 1 - subscribed folders only, 0 - all folders, 2 - all non-active
* @param array Will be filled with folder-types data * @param array Will be filled with folder-types data
* *
* @return array List of folders * @return array List of folders
*/ */
public static function list_user_folders($user, $type, $subscribed = null, &$folderdata = array()) public static function list_user_folders($user, $type, $subscribed = 0, &$folderdata = array())
{ {
self::setup(); self::setup();
@ -1508,7 +1514,17 @@ class kolab_storage
$delimiter = self::$imap->get_hierarchy_delimiter(); $delimiter = self::$imap->get_hierarchy_delimiter();
$other_ns = self::namespace_root('other'); $other_ns = self::namespace_root('other');
$folders = self::list_folders($other_ns . $mbox . $delimiter, '*', $type, $subscribed, $folderdata); $prefix = $other_ns . $mbox . $delimiter;
$subscribed = (int) $subscribed;
$subs = $subscribed < 2 ? (bool) $subscribed : false;
$folders = self::list_folders($prefix, '*', $type, $subs, $folderdata);
if ($subscribed === 2 && !empty($folders)) {
$active = self::get_states();
if (!empty($active)) {
$folders = array_diff($folders, $active);
}
}
} }
return $folders; return $folders;