sites_group_overrides-1.x-dev/src/FormDecorator/ConfigFields.php
src/FormDecorator/ConfigFields.php
<?php
declare(strict_types=1);
namespace Drupal\sites_group_overrides\FormDecorator;
use Drupal\Core\Form\FormStateInterface;
use Drupal\group\Entity\GroupTypeInterface;
use Drupal\form_decorator\FormDecoratorBase;
use Drupal\Core\Entity\EntityTypeManagerInterface;
use Drupal\Core\Entity\EntityFieldManagerInterface;
use Drupal\Core\Plugin\ContainerFactoryPluginInterface;
use Drupal\Core\StringTranslation\StringTranslationTrait;
use Drupal\sites_group\SitesGroupServiceInterface;
use Symfony\Component\DependencyInjection\ContainerInterface;
/**
* Plugin implementation of the form_decorator.
*
* @FormDecorator(
* hook = "form_field_config_edit_form_alter"
* )
*/
final class ConfigFields extends FormDecoratorBase implements ContainerFactoryPluginInterface {
use StringTranslationTrait;
/**
* {@inheritdoc}
*/
public static function create(ContainerInterface $container, $configuration, $plugin_id, $plugin_definition) {
return new self($configuration, $plugin_id, $plugin_definition,
$container->get('entity_type.manager'),
$container->get('entity_field.manager'),
$container->get('sites_group.service')
);
}
/**
* {@inheritdoc}
*/
public function __construct(
array $configuration,
$plugin_id,
$plugin_definition,
protected EntityTypeManagerInterface $entityTypeManager,
protected EntityFieldManagerInterface $entityFieldManager,
protected SitesGroupServiceInterface $sitesGroupService
) {
parent::__construct($configuration, $plugin_id, $plugin_definition);
}
/**
* {@inheritdoc}
*/
public function buildForm(array $form, FormStateInterface $form_state, ...$args) {
$form = parent::buildForm($form, $form_state, ...$args);
// Add the sync option to field configs.
$form['sites_group_overrides'] = [
'#title' => $this->t('Sites group override settings'),
'#type' => 'fieldset',
'#tree' => TRUE,
'#weight' => 12,
];
/** @var GroupTypeInterface[] $group_types */
$group_types = $this->sitesGroupService->getGroupTypes();
foreach ($group_types as $group_type) {
foreach ($group_type->getInstalledPlugins() as $plugin) {
$definition = $plugin->getPluginDefinition();
if ($definition->get('entity_type_id') != $this->getEntity()->get('entity_type')) {
continue;
}
$bundle = $definition->get('entity_type_id');
if ($definition->get('entity_bundle')) {
$bundle = $definition->get('entity_bundle');
}
if ($bundle != $this->getEntity()->get('bundle')) {
continue;
}
$relationship_bundle = $this->entityTypeManager->getStorage('group_relationship_type')->getRelationshipTypeId($group_type->id(), $plugin->getPluginId());
// Add the sync option to field configs.
$form['sites_group_overrides'][$relationship_bundle] = [
'#title' => $this->t('Sites group type: %group_type', ['%group_type' => $group_type->label()]),
'#type' => 'details',
'#tree' => TRUE,
'#open' => $this->getEntity()->getThirdPartySetting('sites_group_overrides', $relationship_bundle)['use_overrides'] ?? FALSE,
];
$form['sites_group_overrides'][$relationship_bundle]['use_overrides'] = [
'#title' => $this->t('Make this field overridable per sites group'),
'#type' => 'checkbox',
'#default_value' => $this->getEntity()->getThirdPartySetting('sites_group_overrides', $relationship_bundle)['use_overrides'] ?? FALSE,
];
$form['sites_group_overrides'][$relationship_bundle]['use_existing_field'] = [
'#title' => $this->t('Use existing field as storage'),
'#type' => 'checkbox',
'#default_value' => $this->getEntity()->getThirdPartySetting('sites_group_overrides', $relationship_bundle)['use_existing_field'] ?? FALSE,
'#states' => [
'visible' => [':input[name="sites_group_overrides[' . $relationship_bundle . '][use_overrides]"]' => ['checked' => TRUE]],
],
];
$form['sites_group_overrides'][$relationship_bundle]['target_field_name'] = [
'#title' => $this->t('Select field for override storage'),
'#type' => 'select',
'#options' => array_map(function ($d) {
return t('@l (@mn)', ['@l' => $d->getLabel(), '@mn' => $d->getName()]);
}, $this->entityFieldManager->getFieldDefinitions('group_relationship', $relationship_bundle)),
'#default_value' => $this->getEntity()->getThirdPartySetting('sites_group_overrides', $relationship_bundle)['target_field_name'] ?? $this->getEntity()->get('field_name'),
'#states' => [
'visible' => [':input[name="sites_group_overrides[' . $relationship_bundle . '][use_existing_field]"]' => ['checked' => TRUE]],
],
];
}
}
return $form;
}
/**
* {@inheritdoc}
*/
public function submitForm(array &$form, FormStateInterface $form_state) {
$sync = $form_state->getValue('sites_group_overrides', []);
$result = parent::submitForm($form, $form_state);
foreach ($sync as $bundle => $settings) {
if (!$settings['use_existing_field']) {
$settings['target_field_name'] = $this->getEntity()->get('field_name');
}
$this->getEntity()->setThirdPartySetting('sites_group_overrides', $bundle, $settings);
if ($settings['use_overrides']) {
$this->snycToGroupRelationshipFieldStorage();
$this->snycToGroupRelationshipField($bundle);
}
}
$this->getEntity()->save();
return $result;
}
// @todo Move this to service.
private function snycToGroupRelationshipField(string $bundle) {
$field_configs = $this->entityTypeManager->getStorage('field_config')->loadByProperties([
'field_name' => $this->getEntity()->get('field_name'),
'entity_type' => 'group_relationship',
'bundle' => $bundle,
]);
if (empty($field_configs)) {
$field_config = $this->entityTypeManager->getStorage('field_config')->create([
'field_name' => $this->getEntity()->get('field_name'),
'entity_type' => 'group_relationship',
'type' => $this->getEntity()->getFieldStorageDefinition()->get('type'),
'bundle' => $bundle,
]);
$field_configs = [$field_config];
}
foreach ($field_configs as $field_config) {
$config = $this->getEntity()->toArray();
foreach ($config as $key => $value) {
if (in_array($key, ['uuid', 'field_name', 'entity_type', 'type', 'bundle'])) {
continue;
}
$field_config->set($key, $value);
}
$field_config->save();
}
}
// @todo move this to service.
private function snycToGroupRelationshipFieldStorage() {
$field_storage_configs = $this->entityTypeManager->getStorage('field_storage_config')->loadByProperties([
'field_name' => $this->getEntity()->get('field_name'),
'entity_type' => 'group_relationship',
]);
if (empty($field_storage_configs)) {
$field_storage_config = $this->entityTypeManager->getStorage('field_storage_config')->create([
'field_name' => $this->getEntity()->get('field_name'),
'entity_type' => 'group_relationship',
'type' => $this->getEntity()->getFieldStorageDefinition()->get('type'),
]);
$field_storage_configs = [$field_storage_config];
}
foreach ($field_storage_configs as $field_storage_config) {
$storage_config = $this->getEntity()->getFieldStorageDefinition()->toArray();
foreach ($storage_config as $key => $value) {
if (in_array($key, ['uuid', 'field_name', 'entity_type', 'type'])) {
continue;
}
$field_storage_config->set($key, $value);
}
$field_storage_config->save();
}
}
}
