ispim-1.0.x-dev/src/PreviewImage/PermissionProvider.php
src/PreviewImage/PermissionProvider.php
<?php
declare(strict_types=1);
namespace Drupal\ispim\PreviewImage;
use Drupal\Core\DependencyInjection\ContainerInjectionInterface;
use Drupal\Core\Entity\EntityInterface;
use Drupal\Core\Entity\EntityTypeInterface;
use Drupal\Core\Entity\EntityTypeManagerInterface;
use Drupal\Core\Entity\RevisionableInterface;
use Drupal\Core\StringTranslation\StringTranslationTrait;
use Drupal\user\EntityOwnerInterface;
use Symfony\Component\DependencyInjection\ContainerInterface;
class PermissionProvider implements PermissionProviderInterface, ContainerInjectionInterface {
use StringTranslationTrait;
/**
* @var array<string, string|\Stringable>
*/
protected array $transArgs = [];
protected bool $hasOwner = FALSE;
protected bool $hasRevisions = FALSE;
protected EntityTypeInterface $entityType;
protected string $entityTypeId = '';
public function getEntityTypeId(): string {
return $this->entityTypeId;
}
public function setEntityTypeId(string $entityTypeId): static {
$this->entityTypeId = $entityTypeId;
$this->init();
return $this;
}
/**
* {@inheritdoc}
*
* @return static
*/
public static function create(ContainerInterface $container) {
// @phpstan-ignore-next-line
return new static(
$container->get('entity_type.manager'),
);
}
public function __construct(
protected EntityTypeManagerInterface $entityTypeManager,
) {
}
protected function init(): static {
/* @noinspection PhpUnhandledExceptionInspection */
$this->entityType = $this
->entityTypeManager
->getDefinition($this->getEntityTypeId());
$interfaces = (array) class_implements($this->entityType->getClass());
$this->hasOwner = in_array(EntityOwnerInterface::class, $interfaces);
$this->hasRevisions = in_array(RevisionableInterface::class, $interfaces);
$this->transArgs = [
'@entityType.label' => $this->entityType->getLabel(),
'@entityType.labelPlural' => $this->entityType->getPluralLabel(),
'@bundle.label' => '',
];
return $this;
}
public function getBundlePermission(string $operation, string $bundleId = ''): string {
assert($this->getEntityTypeId() !== '', '::setEntityTypeId() has to be called first');
$module = $this->entityType->getProvider();
if ($operation === 'view' || $bundleId === '') {
$bundleId = '_all';
}
return "$module.{$this->entityTypeId}.$bundleId.$operation";
}
/**
* @return array<string, array<string, mixed>>
*/
public function getPermissions(): array {
assert($this->getEntityTypeId() !== '', '::setEntityTypeId() has to be called first');
return $this->getAdminPermissions() + $this->getBundlePermissionSets();
}
/**
* @return array<string, array<string, mixed>>
*/
protected function getAdminPermissions(): array {
$adminPermission = $this->entityType->getAdminPermission();
if (!$adminPermission) {
return [];
}
settype($adminPermission, 'string');
return [
$adminPermission => [
'title' => $this->t('Administer @entityType.label', $this->transArgs),
],
];
}
/**
* @return array<string, array<string, mixed>>
*/
protected function getBundlePermissionSets(): array {
$perms = [
$this->getBundlePermission('view', '_all') => [
'title' => $this->t('@entityType.label: view any', $this->transArgs),
],
];
$granularity = $this->entityType->getPermissionGranularity();
if ($granularity !== 'bundle') {
$perms += $this->getBundlePermissionsByEntity();
return $perms;
}
$bundleEntityTypeId = $this->entityType->getBundleEntityType();
if ($bundleEntityTypeId) {
/* @noinspection PhpUnhandledExceptionInspection */
$bundles = $this
->entityTypeManager
->getStorage($this->entityType->getBundleEntityType())
->loadMultiple();
foreach ($bundles as $bundle) {
$perms += $this->getBundlePermissionsByBundle($bundle);
}
}
return $perms;
}
/**
* @return array<string, array<string, mixed>>
*/
protected function getBundlePermissionsByEntity(): array {
$module = $this->entityType->getProvider();
$entityTypeId = $this->entityTypeId;
$perms = [
"$module.$entityTypeId._all.create" => [
'title' => (string) $this->t('@entityType.label: create', $this->transArgs),
],
"$module.$entityTypeId._all.edit_any" => [
'title' => $this->t('@entityType.label: edit any', $this->transArgs),
],
"$module.$entityTypeId._all.delete_any" => [
'title' => $this->t('@entityType.label: delete any', $this->transArgs),
],
];
if ($this->hasOwner) {
$perms += [
"$module.$entityTypeId._all.edit_own" => [
'title' => $this->t('@entityType.label: edit own', $this->transArgs),
],
"$module.$entityTypeId._all.delete_own" => [
'title' => $this->t('@entityType.label: delete own', $this->transArgs),
],
];
}
if ($this->hasRevisions) {
$perms += [
"$module.$entityTypeId._all.revision.view" => [
'title' => $this->t('@entityType.label: view revisions', $this->transArgs),
],
"$module.$entityTypeId._all.revision.revert" => [
'title' => $this->t('@entityType.label: revert revisions', $this->transArgs),
],
"$module.$entityTypeId._all.revision.delete" => [
'title' => $this->t('@entityType.label: delete revisions', $this->transArgs),
],
];
}
return $perms;
}
/**
* @return array<string, array<string, mixed>>
*/
protected function getBundlePermissionsByBundle(EntityInterface $bundle): array {
$bundleId = (string) $bundle->id();
$this->transArgs['@bundle.label'] = $bundle->label();
$perms = [
$this->getBundlePermission('create', $bundleId) => [
'title' => $this->t('@entityType.label - @bundle.label: create', $this->transArgs),
],
$this->getBundlePermission('edit.any', $bundleId) => [
'title' => $this->t('@entityType.label - @bundle.label: edit any', $this->transArgs),
],
$this->getBundlePermission('delete.any', $bundleId) => [
'title' => $this->t('@entityType.label - @bundle.label: delete any', $this->transArgs),
],
];
if ($this->hasOwner) {
$perms += [
$this->getBundlePermission('edit.own', $bundleId) => [
'title' => $this->t('@entityType.label - @bundle.label: edit own', $this->transArgs),
],
$this->getBundlePermission('delete.own', $bundleId) => [
'title' => $this->t('@entityType.label - @bundle.label: delete own', $this->transArgs),
],
];
}
if ($this->hasRevisions) {
$perms += [
$this->getBundlePermission('revision.view', $bundleId) => [
'title' => $this->t('@entityType.label - @bundle.label: view revisions', $this->transArgs),
],
$this->getBundlePermission('revision.revert', $bundleId) => [
'title' => $this->t('@entityType.label - @bundle.label: revert revisions', $this->transArgs),
],
$this->getBundlePermission('revision.delete', $bundleId) => [
'title' => $this->t('@entityType.label - @bundle.label: delete revisions', $this->transArgs),
],
];
}
return $perms;
}
}
