bim_gdpr-1.0.0-rc3/src/Services/HierarchyStorage.php
src/Services/HierarchyStorage.php
<?php
namespace Drupal\bim_gdpr\Services;
use Drupal\bim_gdpr\BimGdprGroupInterface;
use Drupal\bim_gdpr\BimGdprServiceInterface;
use Drupal\bim_gdpr\Hierarchy\Hierarchy;
use Drupal\bim_gdpr\Hierarchy\HierarchyInterface;
use Drupal\Core\Cache\Cache;
use Drupal\Core\Config\ConfigFactoryInterface;
use Drupal\Core\Entity\EntityInterface;
use Drupal\Core\Entity\EntityTypeManagerInterface;
/**
* Class HierarchyStorage.
*
* Store hierarchy items.
*
* @package Drupal\bim_gdpr\Services
*/
class HierarchyStorage {
/**
* Nom du service.
*
* @const string
*/
const SERVICE_NAME = 'bim_gdpr.hierarchy_storage';
/**
* Cache Tag.
*
* @const string
*/
const CACHE_TAG = 'bim_gdpr';
/**
* Config if.
*
* @const string
*/
const CONFIG_ID = 'bim_gdpr.config';
/**
* Entity Type Manager.
*
* @var \Drupal\Core\Entity\EntityTypeManagerInterface
*/
protected $entityTypeManager;
/**
* THe config factory.
*
* @var \Drupal\Core\Config\ConfigFactoryInterface
*/
protected ConfigFactoryInterface $configFactory;
/**
* ServiceRepository constructor.
*
* @param \Drupal\Core\Entity\EntityTypeManagerInterface $entityTypeManager
* THe entity type manager.
* @param \Drupal\Core\Config\ConfigFactoryInterface $configFactory
* The config factory.
*/
public function __construct(EntityTypeManagerInterface $entityTypeManager, ConfigFactoryInterface $configFactory) {
$this->entityTypeManager = $entityTypeManager;
$this->configFactory = $configFactory;
}
/**
* Return the singleton.
*
* @return static
* The singleton.
*/
public static function me() {
return \Drupal::service(static::SERVICE_NAME);
}
/**
* Return the hierarchy of services.
*
* @return \Drupal\bim_gdpr\Hierarchy\HierarchyInterface
* The hierararchy.
*/
public function getHierarchy(): HierarchyInterface {
$this->cleanStoredHierarchy();
try {
$hierarchy = new Hierarchy($this->configFactory->get(static::CONFIG_ID)
->get('hierarchy') ?: []);
}
catch (\Exception $e) {
$hierarchy = new Hierarchy([]);
}
return $hierarchy;
}
/**
* Return the list of groups.
*
* @return \Drupal\bim_gdpr\BimGdprGroupInterface[]
* The list of groups.
*/
public function getGroups(): array {
return $this->getEntitiesList(BimGdprGroupInterface::ENTITY_TYPE_ID);
}
/**
* Return the list of services.
*
* @return \Drupal\bim_gdpr\BimGdprServiceInterface[]
* The list of services.
*/
public function getServices(): array {
return $this->getEntitiesList(BimGdprServiceInterface::ENTITY_TYPE_ID);
}
/**
* Return a list of entities.
*
* @param string $entityTypeId
* THe entity type id.
*
* @return array
* The list of entities.
*/
protected function getEntitiesList(string $entityTypeId): array {
return $this->entityTypeManager->getStorage($entityTypeId)->loadMultiple();
}
/**
* Register hierarchy configuration.
*
* @param \Drupal\bim_gdpr\Hierarchy\HierarchyInterface $hierarchy
* The hierarchy.
*/
public function saveHierarchy(HierarchyInterface $hierarchy) {
$this->configFactory->getEditable(static::CONFIG_ID)
->set('hierarchy', $hierarchy->getRaw())
->save();
// Clear the cache.
$this->clearCache();
}
/**
* Adds an entity in the hierarchy.
*
* @param \Drupal\Core\Entity\EntityInterface $entity
* The entity.
*/
public function add(EntityInterface $entity) {
$storedHierarchy = $this->getHierarchy();
$rawData = $storedHierarchy->getRaw();
$this->addEntityInHierarchyRawData($entity, $rawData);
$this->saveHierarchy(new Hierarchy($rawData));
}
/**
* Delete entity from storage.
*
* @param \Drupal\Core\Entity\EntityInterface[] $entities
* The entities.
*/
public function delete(array $entities) {
$storedHierarchy = $this->getHierarchy();
$rawData = $storedHierarchy->getRaw();
foreach ($entities as $entity) {
unset($rawData[Hierarchy::getEntityRawId($entity)]);
}
$this->saveHierarchy(new Hierarchy($rawData));
}
/**
* Clean the configuration accordigng to entityes.
*/
public function cleanStoredHierarchy() {
$mustSave = FALSE;
// Delete non existant.
$rawData = $this->configFactory->get(static::CONFIG_ID)
->get('hierarchy') ?: [];
foreach ($rawData as $rawId => $data) {
if (!$this->getEntityFromRawId($rawId)) {
unset($rawData[$rawId]);
$mustSave = TRUE;
}
}
// Add New items.
foreach (array_merge($this->getGroups(), $this->getServices()) as $entity) {
if (!isset($rawData[Hierarchy::getEntityRawId($entity)])) {
$this->addEntityInHierarchyRawData($entity, $rawData);
$mustSave = TRUE;
}
}
if ($mustSave) {
$this->saveHierarchy(new Hierarchy($rawData));
}
}
/**
* Return the entity form raw data id.
*
* @param string $rawId
* THe id.
*
* @return \Drupal\Core\Entity\EntityInterface|null
* The entity.
*
* @throws \Drupal\Component\Plugin\Exception\InvalidPluginDefinitionException
* @throws \Drupal\Component\Plugin\Exception\PluginNotFoundException
*/
public function getEntityFromRawId(string $rawId) {
[$entityTypeId, $id] = explode(HierarchyInterface::PREFIX, $rawId);
return $this->entityTypeManager->getStorage($entityTypeId)->load($id);
}
/**
* Add entity into raw Data.
*
* @param \Drupal\Core\Entity\EntityInterface $entity
* The entity.
* @param array $rawData
* THe raw data.
*/
private function addEntityInHierarchyRawData(EntityInterface $entity, array &$rawData) {
// Define next weight.
if (!empty($rawData)) {
// Place the first group before services.
if ($entity instanceof BimGdprGroupInterface && !Hierarchy::rawDataHasGroup($rawData)) {
$nextWeight = end($rawData)['weight'] - 1;
}
else {
$nextWeight = end($rawData)['weight'] + 1;
}
}
else {
$nextWeight = 0;
}
$rawData[Hierarchy::getEntityRawId($entity)] = [
'type' => [
'entity_type_id' => $entity->getEntityTypeId(),
],
'weight' => $nextWeight,
];
}
/**
* INvlaid the cache.
*/
public function clearCache() {
Cache::invalidateTags([static::CACHE_TAG]);
}
}
