Performance: Consolidate metadata requests (#3989)
This changes number of cache requests from 4 to 2 for each groupware folder.
This commit is contained in:
parent
a9b09a16ac
commit
2172f4340c
9 changed files with 119 additions and 56 deletions
|
@ -162,8 +162,8 @@ class kolab_driver extends calendar_driver
|
|||
// special handling for user or virtual folders
|
||||
if ($cal instanceof kolab_storage_folder_user) {
|
||||
$calendars[$cal->id] = array(
|
||||
'id' => $cal->id,
|
||||
'name' => kolab_storage::object_name($fullname),
|
||||
'id' => $cal->id,
|
||||
'name' => $fullname,
|
||||
'listname' => $listname,
|
||||
'editname' => $cal->get_foldername(),
|
||||
'color' => $cal->get_color(),
|
||||
|
|
|
@ -166,7 +166,6 @@ class rcube_kolab_contacts extends rcube_addressbook
|
|||
$this->action = rcube::get_instance()->action;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Getter for the address book name to be displayed
|
||||
*
|
||||
|
@ -174,8 +173,7 @@ class rcube_kolab_contacts extends rcube_addressbook
|
|||
*/
|
||||
public function get_name()
|
||||
{
|
||||
$folder = kolab_storage::object_name($this->imap_folder, $this->namespace);
|
||||
return $folder;
|
||||
return $this->storagefolder->get_name();
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -186,7 +184,6 @@ class rcube_kolab_contacts extends rcube_addressbook
|
|||
return $this->storagefolder->get_foldername();
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Getter for the IMAP folder name
|
||||
*
|
||||
|
@ -197,7 +194,6 @@ class rcube_kolab_contacts extends rcube_addressbook
|
|||
return $this->imap_folder;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Getter for the name of the namespace to which the IMAP folder belongs
|
||||
*
|
||||
|
|
|
@ -239,7 +239,7 @@ class kolab_notes extends rcube_plugin
|
|||
else if ($folder->virtual) {
|
||||
$lists[$list_id] = array(
|
||||
'id' => $list_id,
|
||||
'name' => kolab_storage::object_name($fullname),
|
||||
'name' => $fullname,
|
||||
'listname' => $listname,
|
||||
'virtual' => true,
|
||||
'editable' => false,
|
||||
|
@ -1045,7 +1045,7 @@ class kolab_notes extends rcube_plugin
|
|||
$newfolder = kolab_storage::folder_update($list);
|
||||
|
||||
if ($newfolder === false) {
|
||||
$save_error = $this->gettext(kolab_storage::$last_error);
|
||||
$save_error = $this->gettext(kolab_storage::$last_error);
|
||||
}
|
||||
else {
|
||||
$success = true;
|
||||
|
@ -1056,7 +1056,7 @@ class kolab_notes extends rcube_plugin
|
|||
// compose the new display name
|
||||
$delim = $this->rc->get_storage()->get_hierarchy_delimiter();
|
||||
$path_imap = explode($delim, $newfolder);
|
||||
$list['name'] = kolab_storage::object_name($newfolder);
|
||||
$list['name'] = kolab_storage::object_name($newfolder);
|
||||
$list['editname'] = rcube_charset::convert(array_pop($path_imap), 'UTF7-IMAP');
|
||||
$list['listname'] = str_repeat(' ', count($path_imap)) . '» ' . $list['editname'];
|
||||
}
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
|
||||
class kolab_storage
|
||||
{
|
||||
const CTYPE_KEY = '/shared/vendor/kolab/folder-type';
|
||||
const CTYPE_KEY = '/shared/vendor/kolab/folder-type';
|
||||
const CTYPE_KEY_PRIVATE = '/private/vendor/kolab/folder-type';
|
||||
const COLOR_KEY_SHARED = '/shared/vendor/kolab/color';
|
||||
const COLOR_KEY_PRIVATE = '/private/vendor/kolab/color';
|
||||
|
@ -551,6 +551,7 @@ class kolab_storage
|
|||
|
||||
/**
|
||||
* Getter for human-readable name of Kolab object (folder)
|
||||
* with kolab_custom_display_names support.
|
||||
* See http://wiki.kolab.org/UI-Concepts/Folder-Listing for reference
|
||||
*
|
||||
* @param string $folder IMAP folder name (UTF7-IMAP)
|
||||
|
@ -560,13 +561,43 @@ class kolab_storage
|
|||
*/
|
||||
public static function object_name($folder, &$folder_ns=null)
|
||||
{
|
||||
self::setup();
|
||||
|
||||
// find custom display name in folder METADATA
|
||||
if ($name = self::custom_displayname($folder)) {
|
||||
return $name;
|
||||
}
|
||||
|
||||
return self::object_prettyname($folder, $folder_ns);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get custom display name (saved in metadata) for the given folder
|
||||
*/
|
||||
public static function custom_displayname($folder)
|
||||
{
|
||||
// find custom display name in folder METADATA
|
||||
if (self::$config->get('kolab_custom_display_names', true) && self::setup()) {
|
||||
$metadata = self::$imap->get_metadata($folder, array(self::NAME_KEY_PRIVATE, self::NAME_KEY_SHARED));
|
||||
if (($name = $metadata[$folder][self::NAME_KEY_PRIVATE]) || ($name = $metadata[$folder][self::NAME_KEY_SHARED])) {
|
||||
return $name;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Getter for human-readable name of Kolab object (folder)
|
||||
* See http://wiki.kolab.org/UI-Concepts/Folder-Listing for reference
|
||||
*
|
||||
* @param string $folder IMAP folder name (UTF7-IMAP)
|
||||
* @param string $folder_ns Will be set to namespace name of the folder
|
||||
*
|
||||
* @return string Name of the folder-object
|
||||
*/
|
||||
public static function object_prettyname($folder, &$folder_ns=null)
|
||||
{
|
||||
self::setup();
|
||||
|
||||
$found = false;
|
||||
$namespace = self::$imap->get_namespace();
|
||||
|
||||
|
@ -634,22 +665,6 @@ class kolab_storage
|
|||
return $folder;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get custom display name (saved in metadata) for the given folder
|
||||
*/
|
||||
public static function custom_displayname($folder)
|
||||
{
|
||||
// find custom display name in folder METADATA
|
||||
if (self::$config->get('kolab_custom_display_names', true)) {
|
||||
$metadata = self::$imap->get_metadata($folder, array(self::NAME_KEY_PRIVATE, self::NAME_KEY_SHARED));
|
||||
if (($name = $metadata[$folder][self::NAME_KEY_PRIVATE]) || ($name = $metadata[$folder][self::NAME_KEY_SHARED])) {
|
||||
return $name;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper method to generate a truncated folder name to display.
|
||||
* Note: $origname is a string returned by self::object_name()
|
||||
|
@ -745,7 +760,7 @@ class kolab_storage
|
|||
}
|
||||
}
|
||||
|
||||
$names[$name] = self::object_name($name);
|
||||
$names[$name] = $folder->get_name();
|
||||
}
|
||||
|
||||
// Build SELECT field of parent folder
|
||||
|
@ -960,7 +975,7 @@ class kolab_storage
|
|||
foreach ($folders as $folder) {
|
||||
$folders[$folder->name] = $folder;
|
||||
$ns = $folder->get_namespace();
|
||||
$nsnames[$ns][$folder->name] = strtolower(html_entity_decode(self::object_name($folder->name, $ns), ENT_COMPAT, RCUBE_CHARSET)) . $pad; // decode »
|
||||
$nsnames[$ns][$folder->name] = strtolower(html_entity_decode($folder->get_name(), ENT_COMPAT, RCUBE_CHARSET)) . $pad; // decode »
|
||||
}
|
||||
|
||||
// $folders is a result of get_folders() we can assume folders were already sorted
|
||||
|
@ -1017,7 +1032,7 @@ class kolab_storage
|
|||
$refs[$parent] = new kolab_storage_folder_user($parent, $parent_parent);
|
||||
}
|
||||
else {
|
||||
$name = kolab_storage::object_name($parent, $folder->get_namespace());
|
||||
$name = kolab_storage::object_name($parent);
|
||||
$refs[$parent] = new kolab_storage_folder_virtual($parent, $name, $folder->get_namespace(), $parent_parent);
|
||||
}
|
||||
$parents[] = $refs[$parent];
|
||||
|
@ -1599,5 +1614,30 @@ class kolab_storage
|
|||
$db = rcmail::get_instance()->get_dbh();
|
||||
$prefix = 'imap://' . urlencode($args['username']) . '@' . $args['host'] . '/%';
|
||||
$db->query("DELETE FROM " . $db->table_name('kolab_folders', true) . " WHERE `resource` LIKE ?", $prefix);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Get folder METADATA for all supported keys
|
||||
* Do this in one go for better caching performance
|
||||
*/
|
||||
public static function folder_metadata($folder)
|
||||
{
|
||||
if (self::setup()) {
|
||||
$keys = array(
|
||||
self::NAME_KEY_PRIVATE,
|
||||
self::NAME_KEY_SHARED,
|
||||
self::CTYPE_KEY,
|
||||
self::CTYPE_KEY_PRIVATE,
|
||||
self::COLOR_KEY_PRIVATE,
|
||||
self::COLOR_KEY_SHARED,
|
||||
self::UID_KEY_SHARED,
|
||||
self::UID_KEY_CYRUS,
|
||||
);
|
||||
|
||||
$metadata = self::$imap->get_metadata($folder, $keys);
|
||||
|
||||
return $metadata[$folder];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -64,15 +64,16 @@ class kolab_storage_folder extends kolab_storage_folder_api
|
|||
*/
|
||||
public function set_folder($name, $type = null, $type_annotation = null)
|
||||
{
|
||||
$this->name = $name;
|
||||
|
||||
if (empty($type_annotation)) {
|
||||
$type_annotation = kolab_storage::folder_type($name);
|
||||
$type_annotation = $this->get_type();
|
||||
}
|
||||
|
||||
$oldtype = $this->type;
|
||||
list($this->type, $suffix) = explode('.', $type_annotation);
|
||||
$this->default = $suffix == 'default';
|
||||
$this->subtype = $this->default ? '' : $suffix;
|
||||
$this->name = $name;
|
||||
$this->id = kolab_storage::folder_id($name);
|
||||
$this->valid = !empty($this->type) && $this->type != 'mail' && (!$type || $this->type == $type);
|
||||
|
||||
|
@ -155,7 +156,7 @@ class kolab_storage_folder extends kolab_storage_folder_api
|
|||
{
|
||||
// UID is defined in folder METADATA
|
||||
$metakeys = array(kolab_storage::UID_KEY_SHARED, kolab_storage::UID_KEY_CYRUS);
|
||||
$metadata = $this->get_metadata($metakeys);
|
||||
$metadata = $this->get_metadata();
|
||||
|
||||
if ($metadata !== null) {
|
||||
foreach ($metakeys as $key) {
|
||||
|
@ -1168,6 +1169,4 @@ class kolab_storage_folder extends kolab_storage_folder_api
|
|||
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
|
|
@ -57,7 +57,7 @@ abstract class kolab_storage_folder_api
|
|||
* @var array
|
||||
*/
|
||||
public $children = array();
|
||||
|
||||
|
||||
/**
|
||||
* Name of the parent folder
|
||||
* @var string
|
||||
|
@ -69,6 +69,7 @@ abstract class kolab_storage_folder_api
|
|||
protected $info;
|
||||
protected $idata;
|
||||
protected $namespace;
|
||||
protected $metadata;
|
||||
|
||||
|
||||
/**
|
||||
|
@ -135,10 +136,10 @@ abstract class kolab_storage_folder_api
|
|||
{
|
||||
if (!isset($this->namespace))
|
||||
$this->namespace = $this->imap->folder_namespace($this->name);
|
||||
|
||||
return $this->namespace;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Get the display name value of this folder
|
||||
*
|
||||
|
@ -146,9 +147,22 @@ abstract class kolab_storage_folder_api
|
|||
*/
|
||||
public function get_name()
|
||||
{
|
||||
return kolab_storage::object_name($this->name, $this->get_namespace());
|
||||
}
|
||||
$rcmail = rcube::get_instance();
|
||||
|
||||
// find custom display name in folder METADATA
|
||||
if ($rcmail->config->get('kolab_custom_display_names', true)) {
|
||||
$metadata = $this->get_metadata();
|
||||
|
||||
if ($name = $metadata[kolab_storage::NAME_KEY_PRIVATE]) {
|
||||
return $name;
|
||||
}
|
||||
if ($name = $metadata[kolab_storage::NAME_KEY_SHARED]) {
|
||||
return $name;
|
||||
}
|
||||
}
|
||||
|
||||
return kolab_storage::object_prettyname($this->name);
|
||||
}
|
||||
|
||||
/**
|
||||
* Getter for the top-end folder name (not the entire path)
|
||||
|
@ -221,7 +235,7 @@ abstract class kolab_storage_folder_api
|
|||
public function get_color($default = null)
|
||||
{
|
||||
// color is defined in folder METADATA
|
||||
$metadata = $this->get_metadata(array(kolab_storage::COLOR_KEY_PRIVATE, kolab_storage::COLOR_KEY_SHARED));
|
||||
$metadata = $this->get_metadata();
|
||||
if (($color = $metadata[kolab_storage::COLOR_KEY_PRIVATE]) || ($color = $metadata[kolab_storage::COLOR_KEY_SHARED])) {
|
||||
return $color;
|
||||
}
|
||||
|
@ -229,19 +243,20 @@ abstract class kolab_storage_folder_api
|
|||
return $default;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Returns IMAP metadata/annotations (GETMETADATA/GETANNOTATION)
|
||||
* supported by kolab_storage
|
||||
*
|
||||
* @param array List of metadata keys to read
|
||||
* @return array Metadata entry-value hash array on success, NULL on error
|
||||
*/
|
||||
public function get_metadata($keys)
|
||||
public function get_metadata()
|
||||
{
|
||||
$metadata = rcube::get_instance()->get_storage()->get_metadata($this->name, (array)$keys);
|
||||
return $metadata[$this->name];
|
||||
}
|
||||
if ($this->metadata === null) {
|
||||
$this->metadata = kolab_storage::folder_metadata($this->name);
|
||||
}
|
||||
|
||||
return $this->metadata;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets IMAP metadata/annotations (SETMETADATA/SETANNOTATION)
|
||||
|
@ -251,10 +266,10 @@ abstract class kolab_storage_folder_api
|
|||
*/
|
||||
public function set_metadata($entries)
|
||||
{
|
||||
$this->metadata = null;
|
||||
return $this->imap->set_metadata($this->name, $entries);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
|
@ -277,6 +292,21 @@ abstract class kolab_storage_folder_api
|
|||
return $this->idata;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns (full) type of IMAP folder
|
||||
*
|
||||
* @return string Folder type
|
||||
*/
|
||||
public function get_type()
|
||||
{
|
||||
$metadata = $this->get_metadata();
|
||||
|
||||
if (!empty($metadata)) {
|
||||
return kolab_storage::folder_select_metadata($metadata);
|
||||
}
|
||||
|
||||
return $this->type;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get IMAP ACL information for this folder
|
||||
|
@ -358,4 +388,3 @@ abstract class kolab_storage_folder_api
|
|||
return $this->name;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -72,7 +72,7 @@ class kolab_storage_folder_user extends kolab_storage_folder_virtual
|
|||
*/
|
||||
public function get_title()
|
||||
{
|
||||
return trim($this->ldaprec['displayname'] . '; ' . $this->ldaprec['mail'], '; ');
|
||||
return trim($this->ldaprec['displayname'] . '; ' . $this->ldaprec['mail'], '; ');
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -131,5 +131,4 @@ class kolab_storage_folder_user extends kolab_storage_folder_virtual
|
|||
|
||||
return $success;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
|
|
@ -56,4 +56,4 @@ class kolab_storage_folder_virtual extends kolab_storage_folder_api
|
|||
{
|
||||
return $default;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -214,7 +214,7 @@ class tasklist_kolab_driver extends tasklist_driver
|
|||
if ($folder instanceof kolab_storage_folder_user) {
|
||||
$lists[$list_id] = array(
|
||||
'id' => $list_id,
|
||||
'name' => $folder->get_name(),
|
||||
'name' => $fullname,
|
||||
'listname' => $listname,
|
||||
'title' => $folder->get_title(),
|
||||
'virtual' => true,
|
||||
|
@ -228,7 +228,7 @@ class tasklist_kolab_driver extends tasklist_driver
|
|||
else if ($folder->virtual) {
|
||||
$lists[$list_id] = array(
|
||||
'id' => $list_id,
|
||||
'name' => kolab_storage::object_name($fullname),
|
||||
'name' => $fullname,
|
||||
'listname' => $listname,
|
||||
'virtual' => true,
|
||||
'editable' => false,
|
||||
|
|
Loading…
Add table
Reference in a new issue