You are here

function better_passwords_validate in Better Passwords 8

Same name and namespace in other branches
  1. 2.x better_passwords.module \better_passwords_validate()

Element validate function for password_confirm elements.

Parameters

array $element: The element being validated.

\Drupal\Core\Form\FormStateInterface $form_state: The form_state object returned with the element.

1 string reference to 'better_passwords_validate'
better_passwords_after_build in ./better_passwords.module
After build function for password_confirm elements.

File

./better_passwords.module, line 65
The better passwords module file.

Code

function better_passwords_validate(array $element, FormStateInterface $form_state) {
  $config = \Drupal::config('better_passwords.settings');
  $minLength = $config
    ->get('length');
  $minStrength = $config
    ->get('strength');
  $autoGenerate = $config
    ->get('auto_generate');
  $value = $element['pass1']['#value'];
  if ($value === "") {
    if ($autoGenerate && \Drupal::currentUser()
      ->isAuthenticated() && $form_state
      ->getFormObject()
      ->getFormId() == 'user_register_form') {
      $genpass = user_password(64);
      $form_state
        ->setValueForElement($element, [
        'pass1' => $genpass,
        'pass2' => $genpass,
      ]);
    }
    return TRUE;
  }
  if (strlen($value) < $minLength) {
    $form_state
      ->setError($element, t('Passwords must be at least @num characters.', [
      '@num' => $minLength,
    ]));
    return;
  }
  elseif (!empty($minStrength)) {
    $userdata = [
      $form_state
        ->get('name'),
      $form_state
        ->get('mail'),
    ];
    $z = new Zxcvbn();
    $strength = $z
      ->passwordStrength($value, $userdata);
    if ($strength['score'] < $minStrength) {
      $matches = [];
      foreach ($strength['sequence'] as $obj) {
        if (!empty($obj->pattern)) {
          $str = substr($value, $obj->begin, $obj->end + 1 - $obj->begin);
          switch ($obj->pattern) {
            case 'date':
              $matches[] = t('%str is a date', [
                '%str' => $str,
              ]);
              break;
            case 'dictionary':
              $matches[] = t('%str matches @dict dictionary (#@num)', [
                '%str' => $str,
                '@dict' => $obj->dictionaryName,
                '@num' => $obj->rank,
              ]);
              break;
            case 'digit':
              $matches[] = t('%str is numeric', [
                '%str' => $str,
              ]);
              break;
            case 'repeat':
              $matches[] = t('%str is repetitive', [
                '%str' => $str,
              ]);
              break;
            case 'sequence':
              $matches[] = t('%str is sequential', [
                '%str' => $str,
              ]);
              break;
            case 'spatial':
              $matches[] = t('%str is adjacent on the keyboard', [
                '%str' => $str,
              ]);
              break;
            case 'year':
              $matches[] = t('%str is a year', [
                '%str' => $str,
              ]);
              break;
          }
        }
      }
      $error = new FormattableMarkup(t('Please choose a stronger password. Current strength: @score. Minimum: @min.', [
        '@score' => $strength['score'],
        '@min' => $minStrength,
      ]) . '<ul><li>' . implode('</li><li>', $matches) . '</li></ul>', []);
      $form_state
        ->setErrorByName('pass1', $error);
    }
    else {
      \Drupal::messenger()
        ->addMessage(t('Password strength: @score. Minimum: @min.', [
        '@score' => $strength['score'],
        '@min' => $minStrength,
      ]));
    }
  }
}