You are here

protected function UserFieldsEventSubscriber::getMatchExpressions in SAML Authentication 8.3

Same name and namespace in other branches
  1. 4.x modules/samlauth_user_fields/src/EventSubscriber/UserFieldsEventSubscriber.php \Drupal\samlauth_user_fields\EventSubscriber\UserFieldsEventSubscriber::getMatchExpressions()

Constructs expressions that should be used for user matching attempts.

Logs a warning if the configuration data is 'corrupt'.

Parameters

array $attributes: The complete set of SAML attributes in the assertion. (The attributes can currently be duplicated, keyed both by their name and friendly name.)

Return value

array[] Sets of field expressions to be used for matching; each set can contain one or multiple expressions and is keyed and sorted by the order given in the configuration. (The key values don't have a particular meaning; only their order does.) Individual expressions are fieldname-value pairs.

1 call to UserFieldsEventSubscriber::getMatchExpressions()
UserFieldsEventSubscriber::onUserLink in modules/samlauth_user_fields/src/EventSubscriber/UserFieldsEventSubscriber.php
Tries to link an existing user based on SAML attribute values.

File

modules/samlauth_user_fields/src/EventSubscriber/UserFieldsEventSubscriber.php, line 171

Class

UserFieldsEventSubscriber
Synchronizes SAML attributes into user fields / links new users during login.

Namespace

Drupal\samlauth_user_fields\EventSubscriber

Code

protected function getMatchExpressions(array $attributes) {
  $config = $this->configFactory
    ->get(static::CONFIG_OBJECT_NAME);
  $mappings = $config
    ->get('field_mappings');
  $match_fields = [];
  if (is_array($mappings)) {
    foreach ($mappings as $mapping) {

      // 'Sub fields' (":") are currently not allowed for linking. We
      // disallow them in the UI, so we hope that no 'sub field' is ever
      // configured here. But if it is... we give the generic warning below.
      // (Why they are disallowed: because I simply haven't checked yet,
      // whether the entity query logic works/can work for them.)
      if (isset($mapping['link_user_order']) && isset($mapping['field_name']) && strpos($mapping['field_name'], ':') === FALSE && isset($mapping['attribute_name'])) {
        $match_id = $mapping['link_user_order'];
        $value = $this
          ->getAttribute($mapping['attribute_name'], $attributes);
        if (!isset($value)) {

          // Skip this match; ignore other mappings that are part of it.
          $match_fields[$match_id] = FALSE;
        }
        if (!isset($match_fields[$match_id])) {
          $match_fields[$match_id] = [
            $mapping['field_name'] => $value,
          ];
        }
        elseif ($match_fields[$match_id]) {
          if (isset($match_fields[$match_id][$mapping['field_name']])) {

            // The same match cannot define two attributes/values for the same
            // user field. Spam logs until the site owner fixes configuration.
            $this->logger
              ->debug("Match attempt %id for linking users has multiple SAML attributes tied to the same user field, which is impossible. We'll ignore attribute %attribute.", [
              '%id' => $match_id,
              '%attribute' => $mapping['attribute_name'],
            ]);
          }
          else {
            $match_fields[$match_id][$mapping['field_name']] = $value;
          }
        }
      }
      else {
        $this->logger
          ->warning('Partially invalid %name configuration value; user linking may be partially skipped.', [
          '%name' => 'field_mappings',
        ]);
      }
    }
  }
  elseif (isset($mappings)) {
    $this->logger
      ->warning('Invalid %name configuration value; skipping user linking.', [
      '%name' => 'field_mappings',
    ]);
  }
  ksort($match_fields);
  return array_filter($match_fields);
}