Skip to content
acl.admin.inc 5.74 KiB
Newer Older
 * @file
 * Implementations of administration functions for the acl module.
use Drupal\Component\Utility\Html;
use Drupal\Core\Form\FormStateInterface;
use Drupal\Core\Entity\Element\EntityAutocomplete;
Hans Salvisberg's avatar
Hans Salvisberg committed
 * Implementation of acl_edit_form().
 */
function _acl_edit_form($acl_id, $label = NULL, $new_acl = FALSE) {
  if (!$new_acl) {
    // Ensure the ACL in question even exists.
    if (!($record = $database->query("SELECT name, figure FROM {acl} WHERE acl_id = :acl_id", [
      'acl_id' => $acl_id,
  if (!isset($label)) {
    if (isset($record['name'])) {
      $label = $record['name'];
    }
    elseif (isset($record['figure'])) {
      $label = $record['figure'];
    }
    else {
      $label = $acl_id;
    }
    '#title' => Html::escape($label),
    '#tree' => TRUE,
    '#type' => 'value',
    '#value' => $acl_id,
    '#options' => [],
  ];
  $form['delete_button'] = [
    '#type' => 'button',
    '#value' => t('Remove Checked'),
    '#type' => 'entity_autocomplete',
    '#target_type' => 'user',
    '#title' => t('Add user'),
    '#maxlength' => 60,
    '#size' => 40,
    '#selection_settings' => ['include_anonymous' => FALSE],
    '#type' => 'button',
    '#value' => t('Add User'),
    '#type' => 'hidden',
    '#default_value' => json_encode($accounts),
  $form['user_list_changed'] = [
    '#type' => 'hidden',
    '#value' => FALSE,
  ];

  $form['#after_build'] = ['_acl_edit_form_after_build'];

  return $form;
}

/**
 * Process a form that had our buttons on it.
 */
function _acl_edit_form_after_build($form, FormStateInterface $form_state) {
  // We can't use the form values because it's the entire structure,
  // and we have no clue where our values actually are.
  // That's ok though, because #value still works for us.
  $user_list = acl_edit_form_get_user_list($form);
  $triggering_element = $form_state->getTriggeringElement();

  if (!empty($triggering_element) && $triggering_element['#value'] == $form['delete_button']['#value']) {
    $deletions = $form['deletions']['#value'];
    foreach ($deletions as $uid) {
      unset($user_list[$uid]);
      unset($form['deletions']['#value'][$uid]);
    }
  }
  elseif (!empty($triggering_element['#value']) && $triggering_element['#value'] == $form['add_button']['#value'] && !empty($form['add']['#value'])) {
    if ($match = EntityAutocomplete::extractEntityIdFromAutocompleteInput($value)) {
      $user = @User::load($match);
    }
    if (empty($user)) {
      $form_state->setError($form['add'], t("Invalid user specified."));
      $user_list[$user->id()] = $user->getDisplayName();
    }
  }

  if (count($user_list) != 0) {
    $form['deletions']['#type'] = 'checkboxes';
    $form['deletions']['#title'] = t("Current users");
    $form['deletions']['#options'] = $user_list;
    // Don't carry the value through.
    $form['deletions']['#value'] = [];
    $form['deletions'] = \Drupal::formBuilder()->doBuildForm(!empty($form['#post']) ? $form['#post']['form_id'] : 'acl_form', $form['deletions'], $form_state);
  }
  else {
    $form['delete_button']['#type'] = 'value';
  }
  $form['user_list']['#value'] = json_encode($user_list);
  $original_user_list = acl_edit_form_get_user_list($form, TRUE);
  $form['user_list_changed']['#value'] = !empty(array_diff($original_user_list, $user_list)) || !empty(array_diff($user_list, $original_user_list));
 * Write the results of a form.
 *
Hans Salvisberg's avatar
Hans Salvisberg committed
 * The module that embedded our form must call this function!
 *
 * @param array $form
 *   The ACL edit form part of the form_state array.
 * @param null|int $priority
 *   The priority of the calling module's node access grants.
 */
function acl_save_form($form, $priority = NULL) {
  $users = acl_edit_form_get_user_list($form);
    ->condition('acl_id', $form['acl_id'])
    ->execute();

  $insert = $database->insert('acl_user')->fields(['acl_id', 'uid']);
  foreach ($users as $uid => $name) {
      'acl_id' => $form['acl_id'],
      'uid' => $uid,
  if (isset($priority)) {
        'priority' => $priority,
      ->condition('acl_id', $form['acl_id'])
      ->execute();
/**
 * Decode and return the list of users.
 *
 * @param array $form
 *   The ACL form array or the ACL edit form array part of the form_state.
 * @param bool $get_default
 *   (optional) In the case of a form array, whether to return the
 *   '#default_value' (or the '#value').
 *
 * @return array
 *   An array of $uid => $username.
 */
function acl_edit_form_get_user_list(array $form, $get_default = FALSE) {
  if (is_array($form['user_list'])) {
    return json_decode($form['user_list'][$get_default ? '#default_value' : '#value'], TRUE);
  return json_decode($form['user_list'], TRUE);
/**
 * Check whether the user_list has been changed or not.
 *
 * @param array $form
 *   The ACL form array or the ACL edit form array part of the form_state.
 *
 * @return bool
 *   TRUE if the user_list has been changed.
 */
function acl_edit_form_get_user_list_changed($form) {
  return $form['user_list_changed']['#value'] ?? $form['user_list_changed'];
}