View source
<?php
define('GENPASS_DEFAULT', 0);
define('GENPASS_OPTIONAL', 1);
define('GENPASS_RESTRICTED', 2);
define('GENPASS_DISPLAY_NONE', 0);
define('GENPASS_DISPLAY_ADMIN', 1);
define('GENPASS_DISPLAY_USER', 2);
define('GENPASS_DISPLAY_BOTH', 3);
function _genpass_default_entropy() {
return 'abcdefghjkmnpqrstuvwxyzABCDEFGHJKLMNPQRSTUVWXYZ23456789!#$%&()*+,-./:;<=>?@[]^_{|}~';
}
function genpass_generate() {
return module_invoke(genpass_algorithm_module(), 'password');
}
function genpass_password() {
$pass = '';
$length = variable_get('genpass_length', 8);
$allowable_characters = variable_get('genpass_entropy', _genpass_default_entropy());
$len = strlen($allowable_characters) - 1;
for ($i = 0; $i < $length; $i++) {
$pass .= $allowable_characters[mt_rand(0, $len)];
}
return $pass;
}
function &_genpass_get_form_item(&$form, $field) {
if (isset($form['account'][$field])) {
return $form['account'][$field];
}
else {
return $form[$field];
}
}
function genpass_form_alter(&$form, $form_state, $form_id) {
switch ($form_id) {
case 'user_admin_settings':
$form['registration']['genpass_mode'] = array(
'#type' => 'radios',
'#title' => t('Password handling'),
'#default_value' => variable_get('genpass_mode', GENPASS_DEFAULT),
'#options' => array(
GENPASS_DEFAULT => t('Users must enter a password on registration (default Drupal behaviour).'),
GENPASS_OPTIONAL => t('Users may enter a password on registration. If not, a random password will be generated.'),
GENPASS_RESTRICTED => t('Users cannot choose a password on registration. It will be generated.'),
),
'#description' => t('Choose a password handling mode for new users. Note that if "Require e-mail verification when a visitor creates an account" is selected above, then the third option always applies for the regular user registration form. Also note that for manual user creation by an administrator, the second option always applies.'),
);
$form['registration']['genpass_length'] = array(
'#type' => 'textfield',
'#title' => t('Generated password length'),
'#default_value' => variable_get('genpass_length', 8),
'#size' => 2,
'#maxlength' => 2,
'#description' => t('Set the length of generated passwords here. Allowed range: 5 to 32.'),
);
$form['registration']['genpass_entropy'] = array(
'#type' => 'textfield',
'#title' => t('Generated password entropy'),
'#default_value' => variable_get('genpass_entropy', _genpass_default_entropy()),
'#description' => t('Give a list of possible characters for a generated password. Note that the list must contain at least X different characters where X is defined by the length you have given above.'),
);
$form['registration']['genpass_algorithm'] = array(
'#type' => 'radios',
'#title' => t('Password generation algorithm'),
'#default_value' => genpass_algorithm_module(),
'#options' => genpass_add_samples(genpass_algorithm_modules()),
'#description' => t('If third party modules define a password generation algorithm, you can select which one to use. Note that algorithms other than genpass will ignore the preferred entropy and password length. The currently selected algorithm produced the password @pw', array(
'@pw' => genpass_generate(),
)),
);
$form['registration']['genpass_display'] = array(
'#type' => 'radios',
'#title' => t('Generated password display'),
'#default_value' => variable_get('genpass_display', GENPASS_DISPLAY_BOTH),
'#options' => array(
GENPASS_DISPLAY_NONE => t('Do not display.'),
GENPASS_DISPLAY_ADMIN => t('Display when site administrators create new user accounts.'),
GENPASS_DISPLAY_USER => t('Display when users create their own accounts.'),
GENPASS_DISPLAY_BOTH => t('Display to both site administrators and users.'),
),
'#description' => t('Whether or not the generated password should display after a user account is created.'),
);
$form['#validate'][] = 'genpass_user_admin_settings_validate';
break;
case 'user_register':
$mode = variable_get('genpass_mode', GENPASS_DEFAULT);
$form['#validate'][] = 'genpass_register_validate';
if ($_GET['q'] == 'admin/user/user/create') {
$mode = GENPASS_OPTIONAL;
$notify_item =& _genpass_get_form_item($form, 'notify');
$notify_item['#description'] = t('This is recommended when auto-generating the password; otherwise, neither you nor the new user will know the password.');
}
$form['genpass_mode'] = array(
'#type' => 'value',
'#value' => $mode,
);
$pass_item =& _genpass_get_form_item($form, 'pass');
switch ($mode) {
case GENPASS_OPTIONAL:
$pass_item['#required'] = FALSE;
$pass_item['#description'] .= (empty($pass_item['#description']) ? '' : $pass_item['#description'] . ' ') . t('If left blank, a password will be generated for you.');
break;
case GENPASS_RESTRICTED:
$pass_item['#access'] = FALSE;
$pass_item['#required'] = FALSE;
break;
}
break;
}
}
function genpass_user_admin_settings_validate($form, &$form_state) {
$length = $form_state['values']['genpass_length'];
if (!is_numeric($length) || $length < 5 || $length > 32) {
form_set_error('genpass_length', t('The length of a generated password must be between 5 and 32.'));
return;
}
$chars = array_unique(preg_split('//', $form_state['values']['genpass_entropy'], -1, PREG_SPLIT_NO_EMPTY));
if (count($chars) < $length) {
form_set_error('genpass_entropy', t('The list of possible characters is not long or unique enough.'));
return;
}
return $form;
}
function genpass_register_validate($form, &$form_state) {
if (empty($form_state['values']['pass']) && !form_get_errors()) {
$pass = genpass_generate();
$pass_item =& _genpass_get_form_item($form, 'pass');
form_set_value($pass_item, $pass, $form_state);
$display = variable_get('genpass_display', GENPASS_DISPLAY_BOTH);
if ($_GET['q'] == 'admin/user/user/create') {
$message = t('Since you did not provide a password, it was generated automatically for this account.');
if (in_array($display, array(
GENPASS_DISPLAY_ADMIN,
GENPASS_DISPLAY_BOTH,
))) {
$message .= ' ' . t('The password is: <strong class="nowrap">@password</strong>', array(
'@password' => $pass,
));
}
}
elseif ($form_state['values']['genpass_mode'] == GENPASS_OPTIONAL) {
$message = t('Since you did not provide a password, it was generated for you.');
if (in_array($display, array(
GENPASS_DISPLAY_USER,
GENPASS_DISPLAY_BOTH,
))) {
$message .= ' ' . t('Your password is: <strong class="nowrap">@password</strong>', array(
'@password' => $pass,
));
}
}
elseif ($form_state['values']['genpass_mode'] == GENPASS_RESTRICTED && in_array($display, array(
GENPASS_DISPLAY_USER,
GENPASS_DISPLAY_BOTH,
))) {
$message = t('The following password was generated for you: <strong class="nowrap">@password</strong>', array(
'@password' => $pass,
));
}
if (!empty($message)) {
drupal_set_message($message);
}
}
return $form;
}
function genpass_algorithm_modules() {
$return = array();
foreach (module_implements('password') as $module) {
$return[$module] = $module;
}
return $return;
}
function genpass_algorithm_module() {
$modules = genpass_algorithm_modules();
$module = variable_get('genpass_algorithm', 'genpass');
if (in_array($module, array_keys($modules))) {
return $module;
}
else {
return 'genpass';
}
}
function genpass_add_samples($array) {
$return = array();
foreach ($array as $module => $name) {
$return[$module] = $module . ' (' . t('examples') . ': <strong>' . htmlentities(module_invoke($module, 'password')) . '</strong>, <strong>' . htmlentities(module_invoke($module, 'password')) . '</strong>)';
}
return $return;
}