Use mapper classes for relational data

Signed-off-by: Julius Härtl <jus@bitgrid.net>
This commit is contained in:
Julius Härtl
2017-03-27 20:10:18 +02:00
parent 1e9c86e158
commit 02eecb3a3f
12 changed files with 106 additions and 67 deletions

View File

@@ -52,6 +52,7 @@ class Board extends RelationalEntity implements JsonSerializable {
if ($this->shared === -1) {
unset($json['shared']);
}
$json['owner'] = $this->resolveOwner();
return $json;
}

View File

@@ -24,19 +24,31 @@
namespace OCA\Deck\Db;
use OCP\IDBConnection;
use OCP\IUserManager;
use OCP\IGroupManager;
class BoardMapper extends DeckMapper implements IPermissionMapper {
private $labelMapper;
private $aclMapper;
private $stackMapper;
private $userManager;
private $groupManager;
public function __construct(IDBConnection $db, LabelMapper $labelMapper, AclMapper $aclMapper, StackMapper $stackMapper) {
public function __construct(
IDBConnection $db,
LabelMapper $labelMapper,
AclMapper $aclMapper,
StackMapper $stackMapper,
IUserManager $userManager,
IGroupManager $groupManager
) {
parent::__construct($db, 'deck_boards', '\OCA\Deck\Db\Board');
$this->labelMapper = $labelMapper;
$this->aclMapper = $aclMapper;
$this->stackMapper = $stackMapper;
$this->userManager = $userManager;
$this->groupManager = $groupManager;
}
@@ -149,5 +161,29 @@ class BoardMapper extends DeckMapper implements IPermissionMapper {
return $id;
}
public function mapAcl(Acl &$acl) {
$userManager = $this->userManager;
$groupManager = $this->groupManager;
$acl->resolveRelation('participant', function($participant) use (&$acl, &$userManager, &$groupManager) {
if($acl->getType() === Acl::PERMISSION_TYPE_USER) {
return new User($userManager->get($acl->getParticipant($participant)));
}
if($acl->getType() === Acl::PERMISSION_TYPE_GROUP) {
return new Group($groupManager->get($acl->getParticipant($participant)));
}
throw new \Exception('Unknown permission type for mapping Acl');
});
}
/**
* @param Board $board
*/
public function mapOwner(Board &$board) {
$userManager = $this->userManager;
$board->resolveRelation('owner', function($owner) use (&$userManager) {
return new User($userManager->get($owner));
});
}
}

View File

@@ -48,6 +48,7 @@ class Card extends RelationalEntity implements JsonSerializable {
$this->addType('createdAt', 'integer');
$this->addType('archived', 'boolean');
$this->addRelation('labels');
$this->addResolvable('owner');
}
}

View File

@@ -25,15 +25,17 @@ namespace OCA\Deck\Db;
use OCP\AppFramework\Db\Entity;
use OCP\IDBConnection;
use OCP\IUserManager;
class CardMapper extends DeckMapper implements IPermissionMapper {
private $labelMapper;
public function __construct(IDBConnection $db, LabelMapper $labelMapper) {
public function __construct(IDBConnection $db, LabelMapper $labelMapper, IUserManager $userManager) {
parent::__construct($db, 'deck_cards', '\OCA\Deck\Db\Card');
$this->labelMapper = $labelMapper;
$this->userManager = $userManager;
}
public function insert(Entity $entity) {
@@ -57,6 +59,7 @@ class CardMapper extends DeckMapper implements IPermissionMapper {
$card = $this->findEntity($sql, [$id]);
$labels = $this->labelMapper->findAssignedLabelsForCard($card->id);
$card->setLabels($labels);
$this->mapOwner($card);
return $card;
}
@@ -125,5 +128,12 @@ class CardMapper extends DeckMapper implements IPermissionMapper {
return $row['id'];
}
public function mapOwner(Card &$card) {
$userManager = $this->userManager;
$card->resolveRelation('owner', function($owner) use (&$userManager) {
return new User($userManager->get($owner));
});
}
}

View File

@@ -23,7 +23,9 @@
namespace OCA\Deck\Db;
class RelationalEntity extends \OCP\AppFramework\Db\Entity implements \JsonSerializable {
use OCP\AppFramework\Db\Entity;
class RelationalEntity extends Entity implements \JsonSerializable {
private $_relations = array();
private $_resolvedProperties = [];
@@ -73,9 +75,15 @@ class RelationalEntity extends \OCP\AppFramework\Db\Entity implements \JsonSeria
}
}
}
foreach ($this->_resolvedProperties as $property => $value) {
if($value !== null) {
$json[$property] = $value;
}
}
return $json;
}
/*
/*
* Resolve relational data from external methods
*
* example usage:
@@ -83,7 +91,7 @@ class RelationalEntity extends \OCP\AppFramework\Db\Entity implements \JsonSeria
* in Board::__construct()
* $this->addResolvable('owner')
*
* in BoardService
* in BoardMapper
* $board->resolveRelation('owner', function($owner) use (&$userManager) {
* return new \OCA\Deck\Db\User($userManager->get($owner));
* });
@@ -91,8 +99,6 @@ class RelationalEntity extends \OCP\AppFramework\Db\Entity implements \JsonSeria
* resolved values can be obtained by calling resolveProperty
* e.g. $board->resolveOwner()
*
* TODO: Maybe move from callable to a custom Resolver class that can be reused and use DI?
*
* @param string $property name of the property
* @param callable $resolver anonymous function to resolve relational
* data defined by $property as unique identifier
@@ -126,7 +132,8 @@ class RelationalEntity extends \OCP\AppFramework\Db\Entity implements \JsonSeria
if(!is_scalar($args[0])) {
$args[0] = $args[0]['primaryKey'];
}
return parent::setter($attr, $args);
parent::setter($attr, $args);
return null;
}
return parent::__call($methodName, $args);
}