Merge pull request #7363 from owncloud/optimize-startup-queries

Optimize some queries that are always executed when loading base.php
This commit is contained in:
Morris Jobke 2014-05-19 01:21:37 +02:00
commit 804020bb6d
3 changed files with 133 additions and 13 deletions

View File

@ -40,19 +40,38 @@ class Manager extends PublicEmitter {
/** /**
* @var \OC\Group\Group[] * @var \OC\Group\Group[]
*/ */
private $cachedGroups; private $cachedGroups = array();
/**
* @var \OC\Group\Group[]
*/
private $cachedUserGroups = array();
/** /**
* @param \OC\User\Manager $userManager * @param \OC\User\Manager $userManager
*/ */
public function __construct($userManager) { public function __construct($userManager) {
$this->userManager = $userManager; $this->userManager = $userManager;
$cache = & $this->cachedGroups; $cachedGroups = & $this->cachedGroups;
$this->listen('\OC\Group', 'postDelete', function ($group) use (&$cache) { $cachedUserGroups = & $this->cachedUserGroups;
$this->listen('\OC\Group', 'postDelete', function ($group) use (&$cachedGroups, &$cachedUserGroups) {
/** /**
* @var \OC\Group\Group $group * @var \OC\Group\Group $group
*/ */
unset($cache[$group->getGID()]); unset($cachedGroups[$group->getGID()]);
$cachedUserGroups = array();
});
$this->listen('\OC\Group', 'postAddUser', function ($group) use (&$cachedUserGroups) {
/**
* @var \OC\Group\Group $group
*/
$cachedUserGroups = array();
});
$this->listen('\OC\Group', 'postRemoveUser', function ($group) use (&$cachedUserGroups) {
/**
* @var \OC\Group\Group $group
*/
$cachedUserGroups = array();
}); });
} }
@ -135,7 +154,7 @@ class Manager extends PublicEmitter {
foreach ($this->backends as $backend) { foreach ($this->backends as $backend) {
$groupIds = $backend->getGroups($search, $limit, $offset); $groupIds = $backend->getGroups($search, $limit, $offset);
foreach ($groupIds as $groupId) { foreach ($groupIds as $groupId) {
$groups[$groupId] = $this->getGroupObject($groupId); $groups[$groupId] = $this->get($groupId);
} }
if (!is_null($limit) and $limit <= 0) { if (!is_null($limit) and $limit <= 0) {
return array_values($groups); return array_values($groups);
@ -149,14 +168,19 @@ class Manager extends PublicEmitter {
* @return \OC\Group\Group[] * @return \OC\Group\Group[]
*/ */
public function getUserGroups($user) { public function getUserGroups($user) {
$uid = $user->getUID();
if (isset($this->cachedUserGroups[$uid])) {
return $this->cachedUserGroups[$uid];
}
$groups = array(); $groups = array();
foreach ($this->backends as $backend) { foreach ($this->backends as $backend) {
$groupIds = $backend->getUserGroups($user->getUID()); $groupIds = $backend->getUserGroups($uid);
foreach ($groupIds as $groupId) { foreach ($groupIds as $groupId) {
$groups[$groupId] = $this->getGroupObject($groupId); $groups[$groupId] = $this->get($groupId);
} }
} }
return array_values($groups); $this->cachedUserGroups[$uid] = array_values($groups);
return $this->cachedUserGroups[$uid];
} }
/** /**

View File

@ -55,11 +55,6 @@ class User {
*/ */
public function __construct($uid, $backend, $emitter = null, $config = null) { public function __construct($uid, $backend, $emitter = null, $config = null) {
$this->uid = $uid; $this->uid = $uid;
if ($backend and $backend->implementsActions(OC_USER_BACKEND_GET_DISPLAYNAME)) {
$this->displayName = $backend->getDisplayName($uid);
} else {
$this->displayName = $uid;
}
$this->backend = $backend; $this->backend = $backend;
$this->emitter = $emitter; $this->emitter = $emitter;
$this->config = $config; $this->config = $config;
@ -86,6 +81,13 @@ class User {
* @return string * @return string
*/ */
public function getDisplayName() { public function getDisplayName() {
if (!isset($this->displayName)) {
if ($this->backend and $this->backend->implementsActions(OC_USER_BACKEND_GET_DISPLAYNAME)) {
$this->displayName = $this->backend->getDisplayName($this->uid);
} else {
$this->displayName = $this->uid;
}
}
return $this->displayName; return $this->displayName;
} }

View File

@ -398,4 +398,98 @@ class Manager extends \PHPUnit_Framework_TestCase {
$this->assertEquals(1, count($users)); $this->assertEquals(1, count($users));
$this->assertTrue(isset($users['user33'])); $this->assertTrue(isset($users['user33']));
} }
public function testGetUserGroupsWithAddUser() {
/**
* @var \PHPUnit_Framework_MockObject_MockObject | \OC_Group_Backend $backend
*/
$backend = $this->getMock('\OC_Group_Database');
$expectedGroups = array();
$backend->expects($this->any())
->method('getUserGroups')
->with('user1')
->will($this->returnCallback(function () use (&$expectedGroups) {
return $expectedGroups;
}));
$backend->expects($this->any())
->method('groupExists')
->with('group1')
->will($this->returnValue(true));
$backend->expects($this->once())
->method('implementsActions')
->will($this->returnValue(true));
/**
* @var \OC\User\Manager $userManager
*/
$userManager = $this->getMock('\OC\User\Manager');
$manager = new \OC\Group\Manager($userManager);
$manager->addBackend($backend);
// prime cache
$user1 = new User('user1', null);
$groups = $manager->getUserGroups($user1);
$this->assertEquals(array(), $groups);
// add user
$group = $manager->get('group1');
$group->addUser($user1);
$expectedGroups = array('group1');
// check result
$groups = $manager->getUserGroups($user1);
$this->assertEquals(1, count($groups));
$group1 = $groups[0];
$this->assertEquals('group1', $group1->getGID());
}
public function testGetUserGroupsWithRemoveUser() {
/**
* @var \PHPUnit_Framework_MockObject_MockObject | \OC_Group_Backend $backend
*/
$backend = $this->getMock('\OC_Group_Database');
$expectedGroups = array('group1');
$backend->expects($this->any())
->method('getUserGroups')
->with('user1')
->will($this->returnCallback(function () use (&$expectedGroups) {
return $expectedGroups;
}));
$backend->expects($this->any())
->method('groupExists')
->with('group1')
->will($this->returnValue(true));
$backend->expects($this->once())
->method('implementsActions')
->will($this->returnValue(true));
$backend->expects($this->once())
->method('inGroup')
->will($this->returnValue(true));
$backend->expects($this->once())
->method('removeFromGroup')
->will($this->returnValue(true));
/**
* @var \OC\User\Manager $userManager
*/
$userManager = $this->getMock('\OC\User\Manager');
$manager = new \OC\Group\Manager($userManager);
$manager->addBackend($backend);
// prime cache
$user1 = new User('user1', null);
$groups = $manager->getUserGroups($user1);
$this->assertEquals(1, count($groups));
$group1 = $groups[0];
$this->assertEquals('group1', $group1->getGID());
// remove user
$group = $manager->get('group1');
$group->removeUser($user1);
$expectedGroups = array();
// check result
$groups = $manager->getUserGroups($user1);
$this->assertEquals(array(), $groups);
}
} }