Làm thế nào để cho phép ký tự đặc biệt trong tên người dùng?


9

Có cách nào để cho phép ký tự đặc biệt trong tên người dùng như "#" và "~" không?

Câu trả lời:


11

Bạn phải ghi đè user_validate_name (tên $) :

Verify the syntax of the given name.

Để làm điều đó, hãy xác định mã xác thực tên người dùng của bạn trong mô-đun tùy chỉnh của bạn

function MODULENAME_form_alter(&$form, &$form_state, $form_id) {
  if ($form_id == 'user_register') {      
    $form['#validate'] = array();
    $form['#validate'][] = 'registration_username_validate';

  }
}

Và bên trong hàm register_username_validate thực hiện logic của bạn để cho phép các ký tự đặc biệt của bạn.

Quan tâm về các vấn đề bảo mật gây ra bằng cách cho phép các ký tự đặc biệt trong tên người dùng và về các vấn đề hiển thị không được vệ sinh tên người dùng có thể gây ra trong các chủ đề.


5
Lưu ý, $form['#validate'] = array();sẽ ghi đè mọi trình xử lý xác thực hiện có, bao gồm cả các trình xử lý có thể được đặt bởi các mô-đun đóng góp / tùy chỉnh khác. Tốt hơn để chọn lọc bỏ qua chức năng xác nhận bị ghi đè.
David Thomas

@rock thanx. Tôi đã kiểm tra cơ sở dữ liệu cũ, tôi chỉ có hai người dùng nên tôi sẽ thông báo cho người dùng về việc thay đổi tên người dùng của họ. Cảm ơn btw giải pháp của bạn là tốt. ;)
Sumit Madan

Cũng đáng lưu ý rằng phương pháp này được ưu tiên hơn nhiều so với việc hack chức năng lõi Drupal bên trong user.module
sheldonkreger 3/03/2015

Cũng có thể sử dụng hàm MODULE_form_user_register_form_alter ()
sheldonkreger

Câu trả lời này là nguy hiểm. Như David Thomas đã đề cập, điều này sẽ thay thế bất kỳ trình xác nhận nào khác, bao gồm cả user_account_form_validatechức năng mặc định xác nhận nhiều hơn chỉ là tên người dùng. Thay thế điều này có thể cho phép tên người dùng trùng lặp! Tôi đã thêm một câu trả lời xung quanh những vấn đề này.
bánh rán

1

Thật không may, không có cách thẳng về phía trước để làm điều này. Theo mặc định user_register_formuser_profile_formđã user_account_form_validateđặt làm trình xác nhận đầu tiên của họ trong $form['#validate']. user_account_form_validate()kiểm tra và xóa tên, email và chữ ký của một tài khoản. Là một phần của việc kiểm tra tên, nó thực hiện cuộc gọi đến user_validate_name(). Đây là chức năng chúng tôi muốn ghi đè, không user_account_form_validate.

Người ta sẽ hy vọng một cái móc hữu ích để ghi đè lên nó, nhưng than ôi. Nếu tôi không quan tâm đến việc xác thực email và chữ ký cũng như kiểm tra xem tên có trùng lặp hay không, tôi chỉ có thể xóa user_account_form_validatekhỏi $form['#validate']. Nhưng điều đó không tốt. Thay vào đó, tôi thêm một trình xác nhận bổ sung hoàn tác công việc user_validate_name()và làm lại mọi thứ mà không cần kiểm tra ký tự đặc biệt.

<?php
function MODULENAME_form_user_register_form_alter(
  array &$form, array &$form_state, $form_id)
{
  MODULENAME_add_name_validator($form);
}

function MODULENAME_form_user_profile_form_alter(
  array &$form, array &$form_state, $form_id)
{
  MODULENAME_add_name_validator($form);
}

function MODULENAME_add_name_validator(array &$form)
{
  $validate =& $form['#validate'];
  # Since `validate_name()` clears out any errors for the "name" field, we
  # want to put it right after the validator we want to partially override.
  $acct_validate_index = array_search('user_account_form_validate', $validate);
  array_splice($validate, ($acct_validate_index + 1), 0,
    ['MODULENAME_validate_name']
  );
}

function MODULENAME_validate_name(array $form, array &$form_state)
{
  # There is no blessed way of overriding the call to `user_validate_name()` in
  # `user_account_form_validate()`.
  $errors =& drupal_static('form_set_error', []);
    # Yes, this gets the errors. `form_get_error()` uses this method so... yeah.
  if (!isset($errors['name']))
    # `user_validate_name()` is a superset of what is checked here. If the name
    # passed that validation, no need to rerun things.
    return;

  # `form_set_error()` also calls `drupal_set_message()` if it finds an
  # error.
  $msg_index = array_search($errors['name'], $_SESSION['messages']['error']);
  if ($msg_index !== false) {
    unset($_SESSION['messages']['error'][$msg_index]);
    if (empty($_SESSION['messages']['error']))
      unset($_SESSION['messages']['error']);
  }
  unset($errors['name']);

  $name = isset($form_state['values']['name'])
          ? $form_state['values']['name'] : null;

  # These checks are taken from `user_validate_name()`, simply excluding the
  # for characters we don't mind being in the names.
  if (!$name)
    $error = t('You must enter a username.');
  else if (substr($name, 0, 1) == ' ')
    $error = t('The username cannot begin with a space.');
  else if (substr($name, -1) == ' ')
    $error = t('The username cannot end with a space.');
  else if (strpos($name, '  ') !== FALSE)
    $error = t('The username cannot contain multiple spaces in a row.');
  else if (preg_match('/[\x{80}-\x{A0}' .   // Non-printable ISO-8859-1 + NBSP
                      '\x{AD}' .            // Soft-hyphen
                      '\x{2000}-\x{200F}' . // Various space characters
                      '\x{2028}-\x{202F}' . // Bidirectional text overrides
                      '\x{205F}-\x{206F}' . // Various text hinting characters
                      '\x{FEFF}' .          // Byte order mark
                      '\x{FF01}-\x{FF60}' . // Full-width latin
                      '\x{FFF9}-\x{FFFD}' . // Replacement characters
                      '\x{0}-\x{1F}]/u',    // NULL byte and control characters
                      $name))
    $error = t('The username contains an illegal character.');
  else if (drupal_strlen($name) > USERNAME_MAX_LENGTH)
    $error = t('The username %name is too long: it must be %max characters '
              .'or less.'
              ,['%name' => $name, '%max' => USERNAME_MAX_LENGTH]);

  if (isset($error))
    form_set_error('name', $error);
}

Vẫn còn một kiểm tra ký tự đặc biệt, tuy nhiên nó chỉ kiểm tra các ký tự sử dụng vô hình hoặc đặc biệt.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.