From f09e927d13ba0beb41121691fe531cbf76a0f37b Mon Sep 17 00:00:00 2001 From: Paweł Sroka Date: Sun, 4 Nov 2012 11:25:42 +0100 Subject: Added caching of all subtypes with single query --- engine/lib/entities.php | 112 ++++++++++++++++++++++++++++++------------------ 1 file changed, 70 insertions(+), 42 deletions(-) (limited to 'engine/lib') diff --git a/engine/lib/entities.php b/engine/lib/entities.php index a14160e14..3642856bf 100644 --- a/engine/lib/entities.php +++ b/engine/lib/entities.php @@ -17,7 +17,7 @@ global $ENTITY_CACHE; $ENTITY_CACHE = array(); /** - * Cache subtypes and related class names once loaded. + * Cache subtypes and related class names. * * @global array $SUBTYPE_CACHE * @access private @@ -156,18 +156,15 @@ function get_subtype_id($type, $subtype) { if ($subtype == "") { return FALSE; } + + if (!$SUBTYPE_CACHE) { + populate_subtype_cache(); + } - // @todo use the cache before hitting database - $result = get_data_row("SELECT * from {$CONFIG->dbprefix}entity_subtypes - where type='$type' and subtype='$subtype'"); - - if ($result) { - if (!$SUBTYPE_CACHE) { - $SUBTYPE_CACHE = array(); - } - - $SUBTYPE_CACHE[$result->id] = $result; - return $result->id; + // use the cache before hitting database + $result = retrieve_cached_subtype($type, $subtype); + if ($result!==null) { + return $result->id; } return FALSE; @@ -192,21 +189,47 @@ function get_subtype_from_id($subtype_id) { return false; } + if (!$SUBTYPE_CACHE) { + populate_subtype_cache(); + } + if (isset($SUBTYPE_CACHE[$subtype_id])) { return $SUBTYPE_CACHE[$subtype_id]->subtype; } - $result = get_data_row("SELECT * from {$CONFIG->dbprefix}entity_subtypes where id=$subtype_id"); - if ($result) { - if (!$SUBTYPE_CACHE) { - $SUBTYPE_CACHE = array(); - } + return false; +} - $SUBTYPE_CACHE[$subtype_id] = $result; - return $result->subtype; +/** + * Retrieve subtype from the cache. + * + * @return stdClass|null + * @access private + */ +function retrieve_cached_subtype($type, $subtype) { + global $SUBTYPE_CACHE; + + foreach ($SUBTYPE_CACHE as $id => $obj) { + if ($obj->type==$type && $obj->subtype==$subtype) { + return $obj; + } } + return null; +} - return false; +/** + * Fetch all suptypes from DB to local cache. + * @access private + */ +function populate_subtype_cache() { + global $CONFIG, $SUBTYPE_CACHE; + + $results = get_data("SELECT * from {$CONFIG->dbprefix}entity_subtypes"); + + $SUBTYPE_CACHE = array(); + foreach ($results as $result) { + $SUBTYPE_CACHE[$result->id] = $result; + } } /** @@ -230,16 +253,13 @@ function get_subtype_class($type, $subtype) { $type = sanitise_string($type); $subtype = sanitise_string($subtype); - // @todo use the cache before going to the database - $result = get_data_row("SELECT * from {$CONFIG->dbprefix}entity_subtypes - where type='$type' and subtype='$subtype'"); - - if ($result) { - if (!$SUBTYPE_CACHE) { - $SUBTYPE_CACHE = array(); - } - - $SUBTYPE_CACHE[$result->id] = $result; + if (!$SUBTYPE_CACHE) { + populate_subtype_cache(); + } + + // use the cache before going to the database + $result = retrieve_cached_subtype($type, $subtype); + if ($result!==null) { return $result->class; } @@ -265,20 +285,14 @@ function get_subtype_class_from_id($subtype_id) { return false; } + if (!$SUBTYPE_CACHE) { + populate_subtype_cache(); + } + if (isset($SUBTYPE_CACHE[$subtype_id])) { return $SUBTYPE_CACHE[$subtype_id]->class; } - $result = get_data_row("SELECT * from {$CONFIG->dbprefix}entity_subtypes where id=$subtype_id"); - - if ($result) { - if (!$SUBTYPE_CACHE) { - $SUBTYPE_CACHE = array(); - } - $SUBTYPE_CACHE[$subtype_id] = $result; - return $result->class; - } - return NULL; } @@ -305,7 +319,7 @@ function get_subtype_class_from_id($subtype_id) { * @see get_entity() */ function add_subtype($type, $subtype, $class = "") { - global $CONFIG; + global $CONFIG, $SUBTYPE_CACHE; $type = sanitise_string($type); $subtype = sanitise_string($subtype); $class = sanitise_string($class); @@ -318,8 +332,18 @@ function add_subtype($type, $subtype, $class = "") { $id = get_subtype_id($type, $subtype); if ($id == 0) { - return insert_data("insert into {$CONFIG->dbprefix}entity_subtypes" + $result = insert_data("insert into {$CONFIG->dbprefix}entity_subtypes" . " (type, subtype, class) values ('$type','$subtype','$class')"); + + // add entry to cache + $obj = new stdClass(); + $obj->id = $result; + $obj->type = $type; + $obj->subtype = $subtype; + $obj->class = $class; + $SUBTYPE_CACHE[$obj->id] = $obj; + + return $result; } return $id; @@ -367,6 +391,10 @@ function update_subtype($type, $subtype, $class = '') { $type = sanitise_string($type); $subtype = sanitise_string($subtype); + if (!$SUBTYPE_CACHE) { + populate_subtype_cache(); + } + $result = update_data("UPDATE {$CONFIG->dbprefix}entity_subtypes SET type = '$type', subtype = '$subtype', class = '$class' WHERE id = $id -- cgit v1.2.3 From 867d094d56df02ed93806f0c2c72890ecf762e41 Mon Sep 17 00:00:00 2001 From: Steve Clay Date: Wed, 28 Nov 2012 00:27:53 -0500 Subject: Subtype functions cleanup --- engine/lib/entities.php | 178 ++++++++++++++++++++++++------------------------ 1 file changed, 90 insertions(+), 88 deletions(-) (limited to 'engine/lib') diff --git a/engine/lib/entities.php b/engine/lib/entities.php index 3642856bf..a1c1c2997 100644 --- a/engine/lib/entities.php +++ b/engine/lib/entities.php @@ -19,11 +19,11 @@ $ENTITY_CACHE = array(); /** * Cache subtypes and related class names. * - * @global array $SUBTYPE_CACHE + * @global array|null $SUBTYPE_CACHE array once populated from DB, initially null * @access private */ global $SUBTYPE_CACHE; -$SUBTYPE_CACHE = NULL; +$SUBTYPE_CACHE = null; /** * Invalidate this class's entry in the cache. @@ -87,8 +87,6 @@ function cache_entity(ElggEntity $entity) { function retrieve_cached_entity($guid) { global $ENTITY_CACHE; - $guid = (int)$guid; - if (isset($ENTITY_CACHE[$guid])) { if ($ENTITY_CACHE[$guid]->isFullyLoaded()) { return $ENTITY_CACHE[$guid]; @@ -148,26 +146,23 @@ function retrieve_cached_entity_row($guid) { * @access private */ function get_subtype_id($type, $subtype) { - global $CONFIG, $SUBTYPE_CACHE; + global $SUBTYPE_CACHE; - $type = sanitise_string($type); - $subtype = sanitise_string($subtype); - - if ($subtype == "") { - return FALSE; + if (!$subtype) { + return false; } - - if (!$SUBTYPE_CACHE) { - populate_subtype_cache(); + + if ($SUBTYPE_CACHE === null) { + _elgg_populate_subtype_cache(); } - // use the cache before hitting database - $result = retrieve_cached_subtype($type, $subtype); - if ($result!==null) { - return $result->id; + // use the cache before hitting database + $result = _elgg_retrieve_cached_subtype($type, $subtype); + if ($result !== null) { + return $result->id; } - return FALSE; + return false; } /** @@ -175,24 +170,22 @@ function get_subtype_id($type, $subtype) { * * @param int $subtype_id Subtype ID * - * @return string Subtype name + * @return string|false Subtype name, false if subtype not found * @link http://docs.elgg.org/DataModel/Entities/Subtypes * @see get_subtype_from_id() * @access private */ function get_subtype_from_id($subtype_id) { - global $CONFIG, $SUBTYPE_CACHE; - - $subtype_id = (int)$subtype_id; + global $SUBTYPE_CACHE; if (!$subtype_id) { return false; } - if (!$SUBTYPE_CACHE) { - populate_subtype_cache(); - } - + if ($SUBTYPE_CACHE === null) { + _elgg_populate_subtype_cache(); + } + if (isset($SUBTYPE_CACHE[$subtype_id])) { return $SUBTYPE_CACHE[$subtype_id]->subtype; } @@ -200,35 +193,43 @@ function get_subtype_from_id($subtype_id) { return false; } -/** - * Retrieve subtype from the cache. - * - * @return stdClass|null - * @access private - */ -function retrieve_cached_subtype($type, $subtype) { - global $SUBTYPE_CACHE; - - foreach ($SUBTYPE_CACHE as $id => $obj) { - if ($obj->type==$type && $obj->subtype==$subtype) { +/** + * Retrieve subtype from the cache. + * + * @param string $type + * @param string $subtype + * @return stdClass|null + * + * @access private + */ +function _elgg_retrieve_cached_subtype($type, $subtype) { + global $SUBTYPE_CACHE; + + if ($SUBTYPE_CACHE === null) { + _elgg_populate_subtype_cache(); + } + + foreach ($SUBTYPE_CACHE as $obj) { + if ($obj->type === $type && $obj->subtype === $subtype) { return $obj; } } - return null; + return null; } /** * Fetch all suptypes from DB to local cache. + * * @access private */ -function populate_subtype_cache() { +function _elgg_populate_subtype_cache() { global $CONFIG, $SUBTYPE_CACHE; - $results = get_data("SELECT * from {$CONFIG->dbprefix}entity_subtypes"); + $results = get_data("SELECT * FROM {$CONFIG->dbprefix}entity_subtypes"); $SUBTYPE_CACHE = array(); - foreach ($results as $result) { - $SUBTYPE_CACHE[$result->id] = $result; + foreach ($results as $row) { + $SUBTYPE_CACHE[$row->id] = $row; } } @@ -248,22 +249,19 @@ function populate_subtype_cache() { * @access private */ function get_subtype_class($type, $subtype) { - global $CONFIG, $SUBTYPE_CACHE; + global $SUBTYPE_CACHE; - $type = sanitise_string($type); - $subtype = sanitise_string($subtype); - - if (!$SUBTYPE_CACHE) { - populate_subtype_cache(); - } + if ($SUBTYPE_CACHE === null) { + _elgg_populate_subtype_cache(); + } // use the cache before going to the database - $result = retrieve_cached_subtype($type, $subtype); - if ($result!==null) { - return $result->class; + $obj = _elgg_retrieve_cached_subtype($type, $subtype); + if ($obj) { + return $obj->class; } - return NULL; + return null; } /** @@ -277,23 +275,21 @@ function get_subtype_class($type, $subtype) { * @access private */ function get_subtype_class_from_id($subtype_id) { - global $CONFIG, $SUBTYPE_CACHE; - - $subtype_id = (int)$subtype_id; + global $SUBTYPE_CACHE; if (!$subtype_id) { - return false; + return null; } - if (!$SUBTYPE_CACHE) { - populate_subtype_cache(); - } + if ($SUBTYPE_CACHE === null) { + _elgg_populate_subtype_cache(); + } if (isset($SUBTYPE_CACHE[$subtype_id])) { return $SUBTYPE_CACHE[$subtype_id]->class; } - return NULL; + return null; } /** @@ -320,30 +316,31 @@ function get_subtype_class_from_id($subtype_id) { */ function add_subtype($type, $subtype, $class = "") { global $CONFIG, $SUBTYPE_CACHE; - $type = sanitise_string($type); - $subtype = sanitise_string($subtype); - $class = sanitise_string($class); - // Short circuit if no subtype is given - if ($subtype == "") { + if (!$subtype) { return 0; } $id = get_subtype_id($type, $subtype); - if ($id == 0) { - $result = insert_data("insert into {$CONFIG->dbprefix}entity_subtypes" - . " (type, subtype, class) values ('$type','$subtype','$class')"); + if (!$id) { + // In cache we store non-SQL-escaped strings because that's what's returned by query + $cache_obj = (object) array( + 'type' => $type, + 'subtype' => $subtype, + 'class' => $class, + ); + + $type = sanitise_string($type); + $subtype = sanitise_string($subtype); + $class = sanitise_string($class); + + $id = insert_data("INSERT INTO {$CONFIG->dbprefix}entity_subtypes" + . " (type, subtype, class) VALUES ('$type', '$subtype', '$class')"); // add entry to cache - $obj = new stdClass(); - $obj->id = $result; - $obj->type = $type; - $obj->subtype = $subtype; - $obj->class = $class; - $SUBTYPE_CACHE[$obj->id] = $obj; - - return $result; + $cache_obj->id = $id; + $SUBTYPE_CACHE[$id] = $cache_obj; } return $id; @@ -385,26 +382,31 @@ function remove_subtype($type, $subtype) { function update_subtype($type, $subtype, $class = '') { global $CONFIG, $SUBTYPE_CACHE; - if (!$id = get_subtype_id($type, $subtype)) { - return FALSE; + $id = get_subtype_id($type, $subtype); + if (!$id) { + return false; } + + if ($SUBTYPE_CACHE === null) { + _elgg_populate_subtype_cache(); + } + + $unescaped_class = $class; + $type = sanitise_string($type); $subtype = sanitise_string($subtype); - - if (!$SUBTYPE_CACHE) { - populate_subtype_cache(); - } + $class = sanitise_string($class); - $result = update_data("UPDATE {$CONFIG->dbprefix}entity_subtypes + $success = update_data("UPDATE {$CONFIG->dbprefix}entity_subtypes SET type = '$type', subtype = '$subtype', class = '$class' WHERE id = $id "); - if ($result && isset($SUBTYPE_CACHE[$id])) { - $SUBTYPE_CACHE[$id]->class = $class; + if ($success && isset($SUBTYPE_CACHE[$id])) { + $SUBTYPE_CACHE[$id]->class = $unescaped_class; } - return $result; + return $success; } /** @@ -1800,7 +1802,7 @@ function oddentity_to_elggentity(ODDEntity $element) { if (!$tmp) { // Construct new class with owner from session $classname = get_subtype_class($class, $subclass); - if ($classname != "") { + if ($classname) { if (class_exists($classname)) { $tmp = new $classname(); -- cgit v1.2.3