Skip to content
Snippets Groups Projects
Commit 1d5856cf authored by Andreas Gohr's avatar Andreas Gohr
Browse files

two-stage password reset

This patch changes the password reset function to a two-stage process.
After requesting a new password a confirmation email is sent first, only
if the link contained in this mail is used the password is changed for real.

This makes sure malicious people can't reset passwords for other users.

darcs-hash:20060714110548-7ad00-c1e23fd51cc2d2f16473914421ebe0f9c3b2ba8c.gz
parent 75e487e9
No related branches found
No related tags found
No related merge requests found
......@@ -59,7 +59,7 @@ $conf['passcrypt'] = 'smd5'; //Used crypt method (smd5,md5,sha1,ssha
$conf['defaultgroup']= 'user'; //Default groups new Users are added to
$conf['superuser'] = '!!not set!!'; //The admin can be user or @group
$conf['profileconfirm'] = '1'; //Require current password to confirm changes to user profile
$conf['disableactions'] = 'resendpwd'; //comma separated list of actions to disable
$conf['disableactions'] = ''; //comma separated list of actions to disable
/* Advanced Options */
$conf['userewrite'] = 0; //this makes nice URLs: 0: off 1: .htaccess 2: internal
......
......@@ -570,8 +570,14 @@ function updateprofile() {
/**
* Send a new password
*
* This function handles both phases of the password reset:
*
* - handling the first request of password reset
* - validating the password reset auth token
*
* @author Benoit Chesneau <benoit@bchesneau.info>
* @author Chris Smith <chris@jalakai.co.uk>
* @author Andreas Gohr <andi@splitbrain.org>
*
* @return bool true on success, false on any error
*/
......@@ -580,40 +586,89 @@ function act_resendpwd(){
global $conf;
global $auth;
if(!$_POST['save']) return false;
if(!actionOK('resendpwd')) return false;
// should not be able to get here without modPass being possible...
if(!$auth->canDo('modPass')) {
msg($lang['resendna'],-1);
return false;
msg($lang['resendna'],-1);
return false;
}
if (empty($_POST['login'])) {
msg($lang['resendpwdmissing'], -1);
return false;
} else {
$user = $_POST['login'];
}
$token = preg_replace('/[^a-f0-9]+/','',$_REQUEST['pwauth']);
$userinfo = $auth->getUserData($user);
if(!$userinfo['mail']) {
msg($lang['resendpwdnouser'], -1);
return false;
}
if($token){
// we're in token phase
$pass = auth_pwgen();
if (!$auth->modifyUser($user,array('pass' => $pass))) {
msg('error modifying user data',-1);
return false;
}
$tfile = $conf['cachedir'].'/'.$token{0}.'/'.$token.'.pwauth';
if(!@file_exists($tfile)){
msg($lang['resendpwdbadauth'],-1);
return false;
}
$user = io_readfile($tfile);
@unlink($tfile);
$userinfo = $auth->getUserData($user);
if(!$userinfo['mail']) {
msg($lang['resendpwdnouser'], -1);
return false;
}
$pass = auth_pwgen();
if (!$auth->modifyUser($user,array('pass' => $pass))) {
msg('error modifying user data',-1);
return false;
}
if (auth_sendPassword($user,$pass)) {
msg($lang['resendpwdsuccess'],1);
} else {
msg($lang['regmailfail'],-1);
}
return true;
if (auth_sendPassword($user,$pass)) {
msg($lang['resendpwdsuccess'],1);
} else {
msg($lang['regmailfail'],-1);
// we're in request phase
if(!$_POST['save']) return false;
if (empty($_POST['login'])) {
msg($lang['resendpwdmissing'], -1);
return false;
} else {
$user = $_POST['login'];
}
$userinfo = $auth->getUserData($user);
if(!$userinfo['mail']) {
msg($lang['resendpwdnouser'], -1);
return false;
}
// generate auth token
$token = md5(auth_cookiesalt().$user); //secret but user based
$tfile = $conf['cachedir'].'/'.$token{0}.'/'.$token.'.pwauth';
$url = wl('',array('do'=>'resendpwd','pwauth'=>$token),true,'&');
io_saveFile($tfile,$user);
$text = rawLocale('pwconfirm');
$text = str_replace('@DOKUWIKIURL@',DOKU_URL,$text);
$text = str_replace('@FULLNAME@',$userinfo['name'],$text);
$text = str_replace('@LOGIN@',$user,$text);
$text = str_replace('@TITLE@',$conf['title'],$text);
$text = str_replace('@CONFIRM@',$url,$text);
if(mail_send($userinfo['name'].' <'.$userinfo['mail'].'>',
$lang['regpwmail'],
$text,
$conf['mailfrom'])){
msg($lang['resendpwdconfirm'],1);
}else{
msg($lang['regmailfail'],-1);
}
return true;
}
return true;
return false; // never reached
}
/**
......
......@@ -78,14 +78,14 @@ function html_login(){
if($auth->canDo('addUser') && actionOK('register')){
print '<p>';
print $lang['reghere'];
print ': <a href="'.wl($ID,'do=register').'" class="wikilink1">'.$lang['register'].'</a>';
print ': <a href="'.wl($ID,'do=register').'" rel="nofollow" class="wikilink1">'.$lang['register'].'</a>';
print '</p>';
}
if ($auth->canDo('modPass') && actionOK('resendpwd')) {
print '<p>';
print $lang['pwdforget'];
print ': <a href="'.wl($ID,'do=resendpwd').'" class="wikilink1">'.$lang['btn_resendpwd'].'</a>';
print ': <a href="'.wl($ID,'do=resendpwd').'" rel="nofollow" class="wikilink1">'.$lang['btn_resendpwd'].'</a>';
print '</p>';
}
?>
......
......@@ -78,6 +78,8 @@ $lang['resendna'] = 'This wiki does not support password resending.';
$lang['resendpwd'] = 'Send new password for';
$lang['resendpwdmissing'] = 'Sorry, you must fill in all fields.';
$lang['resendpwdnouser'] = 'Sorry, we can\'t find this user in our database.';
$lang['resendpwdbadauth'] = 'Sorry, this auth code is not valid. Make sure you used the complete confirmation link.';
$lang['resendpwdconfirm'] = 'A confirmation link has been sent by email.';
$lang['resendpwdsuccess'] = 'Your new password has been sent by email.';
$lang['txt_upload'] = 'Select file to upload';
......
Hi @FULLNAME@!
Here is your userdata for @TITLE@ at @DOKUWIKIURL@
Login : @LOGIN@
Password : @PASSWORD@
--
This mail was generated by DokuWiki at
@DOKUWIKIURL@
Hi @FULLNAME@!
Here is your userdata for @TITLE@ at @DOKUWIKIURL@
Login : @LOGIN@
Password : @PASSWORD@
--
This mail was generated by DokuWiki at
@DOKUWIKIURL@
Hi @FULLNAME@!
Someone requested a new password for your @TITLE@
login at @DOKUWIKIURL@
If you did not request a new password then just ignore this email.
To confirm that the request was really sent by you please use the
following link.
@CONFIRM@
--
This mail was generated by DokuWiki at
@DOKUWIKIURL@
====== Send new password ======
Fill in all the information below to get a new password for your account in this wiki.
Your new password will be sent to your registered email address. The user name should be
your wiki user name.
Please enter your user name in the form below to request a new password for your
account in this wiki. A confirmation link will be sent to your registered email
address.
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment