]> git.ipfire.org Git - thirdparty/bugzilla.git/commitdiff
Bug 87795: Creating an account should send token and wait for confirmation (prevent...
authorlpsolit%gmail.com <>
Sun, 20 Aug 2006 01:11:59 +0000 (01:11 +0000)
committerlpsolit%gmail.com <>
Sun, 20 Aug 2006 01:11:59 +0000 (01:11 +0000)
17 files changed:
Bugzilla/BugMail.pm
Bugzilla/Constants.pm
Bugzilla/DB/Schema.pm
Bugzilla/Install/DB.pm
Bugzilla/Token.pm
Bugzilla/User.pm
createaccount.cgi
template/en/default/account/cancel-token.txt.tmpl
template/en/default/account/create.html.tmpl
template/en/default/account/created.html.tmpl
template/en/default/account/email/confirm-new.html.tmpl [new file with mode: 0644]
template/en/default/account/email/request-new.txt.tmpl [new file with mode: 0644]
template/en/default/email/password.txt.tmpl [deleted file]
template/en/default/global/messages.html.tmpl
template/en/default/global/user-error.html.tmpl
token.cgi
userprefs.cgi

index 07ebf226b3c8732e5967173dd48c6d3031433883..35b05d231a17a28af63c6a4b584c54fc7604280b 100644 (file)
@@ -654,20 +654,6 @@ sub sendMail {
     return 1;
 }
 
-# Send the login name and password of the newly created account to the user.
-sub MailPassword {
-    my ($login, $password) = (@_);
-    my $template = Bugzilla->template;
-    my $vars = {
-      mailaddress => $login . Bugzilla->params->{'emailsuffix'},
-      login => $login,
-      password => $password };
-    my $msg;
-    $template->process("email/password.txt.tmpl", $vars, \$msg)
-      || ThrowTemplateError($template->error());
-    MessageToMTA($msg);
-}
-
 # Get bug comments for the given period and format them to be used in emails.
 sub get_comments_by_bug {
     my ($id, $start, $end) = @_;
index 9493ea400d568821b0d8d5331069e2db77deffb6..2d6c2f561b02120c66d06502e52f0816770ad02b 100644 (file)
@@ -120,6 +120,8 @@ use File::Basename;
     DB_MODULE
     ROOT_USER
     ON_WINDOWS
+
+    MAX_TOKEN_AGE
 );
 
 @Bugzilla::Constants::EXPORT_OK = qw(contenttypes);
@@ -295,6 +297,9 @@ use constant SENDMAIL_EXE => '/usr/lib/sendmail.exe';
 use constant FIELD_TYPE_UNKNOWN   => 0;
 use constant FIELD_TYPE_FREETEXT  => 1;
 
+# The maximum number of days a token will remain valid.
+use constant MAX_TOKEN_AGE => 3;
+
 # States that are considered to be "open" for bugs.
 use constant BUG_STATE_OPEN => ('NEW', 'REOPENED', 'ASSIGNED', 
                                 'UNCONFIRMED');
index 50785c5b7ebc97a77346200a24a54b96e55b8aac..1888c76c06aad39e85a26f6e7ee2130cf79b9c6b 100644 (file)
@@ -715,7 +715,7 @@ use constant ABSTRACT_SCHEMA => {
     #     for these changes.
     tokens => {
         FIELDS => [
-            userid    => {TYPE => 'INT3', NOTNULL => 1} ,
+            userid    => {TYPE => 'INT3'},
             issuedate => {TYPE => 'DATETIME', NOTNULL => 1} ,
             token     => {TYPE => 'varchar(16)', NOTNULL => 1,
                           PRIMARYKEY => 1},
index a4ab54260ef55c0d7410795038c09afe2bc417ef..d34a11f24e69059a38055ec22936dd2139985da7 100644 (file)
@@ -471,6 +471,9 @@ sub update_table_definitions {
     $dbh->bz_alter_column('keyworddefs', 'id',
         {TYPE => 'SMALLSERIAL', NOTNULL => 1, PRIMARYKEY => 1});
 
+    # 2006-08-19 LpSolit@gmail.com - Bug 87795
+    $dbh->bz_alter_column('tokens', 'userid', {TYPE => 'INT3'});
+
     ################################################################
     # New --TABLE-- changes should go *** A B O V E *** this point #
     ################################################################
index 447d27507d93cb5b449736c2dc4564eee7b931e8..6dd8baa6ea5f370e8146a8920080d35ab69ce3db 100644 (file)
@@ -29,6 +29,7 @@ use strict;
 # Bundle the functions in this file together into the "Bugzilla::Token" package.
 package Bugzilla::Token;
 
+use Bugzilla::Constants;
 use Bugzilla::Error;
 use Bugzilla::Mailer;
 use Bugzilla::Util;
@@ -37,15 +38,45 @@ use Date::Format;
 use Date::Parse;
 
 ################################################################################
-# Constants
+# Public Functions
 ################################################################################
 
-# The maximum number of days a token will remain valid.
-use constant MAX_TOKEN_AGE => 3;
+# Creates and sends a token to create a new user account.
+# It assumes that the login has the correct format and is not already in use.
+sub issue_new_user_account_token {
+    my $login_name = shift;
+    my $dbh = Bugzilla->dbh;
+    my $template = Bugzilla->template;
+    my $vars = {};
 
-################################################################################
-# Public Functions
-################################################################################
+    # Is there already a pending request for this login name? If yes, do not throw
+    # an error because the user may have lost his email with the token inside.
+    # But to prevent using this way to mailbomb an email address, make sure
+    # the last request is at least 10 minutes old before sending a new email.
+    trick_taint($login_name);
+
+    my $pending_requests =
+        $dbh->selectrow_array('SELECT COUNT(*)
+                                 FROM tokens
+                                WHERE tokentype = ?
+                                  AND ' . $dbh->sql_istrcmp('eventdata', '?') . '
+                                  AND issuedate > NOW() - ' . $dbh->sql_interval(10, 'MINUTE'),
+                               undef, ('account', $login_name));
+
+    ThrowUserError('too_soon_for_new_token', {'type' => 'account'}) if $pending_requests;
+
+    my ($token, $token_ts) = _create_token(undef, 'account', $login_name);
+
+    $vars->{'email'} = $login_name . Bugzilla->params->{'emailsuffix'};
+    $vars->{'token_ts'} = $token_ts;
+    $vars->{'token'} = $token;
+
+    my $message;
+    $template->process('account/email/request-new.txt.tmpl', $vars, \$message)
+      || ThrowTemplateError($template->error());
+
+    MessageToMTA($message);
+}
 
 sub IssueEmailChangeToken {
     my ($userid, $old_email, $new_email) = @_;
@@ -106,7 +137,7 @@ sub IssuePasswordToken {
                                 WHERE ' . $dbh->sql_istrcmp('login_name', '?'),
                                 undef, ('password', $loginname));
 
-    ThrowUserError('too_soon_for_new_token') if $too_soon;
+    ThrowUserError('too_soon_for_new_token', {'type' => 'password'}) if $too_soon;
 
     my ($token, $token_ts) = _create_token($userid, 'password', $::ENV{'REMOTE_ADDR'});
 
@@ -177,26 +208,25 @@ sub GenerateUniqueToken {
 sub Cancel {
     my ($token, $cancelaction, $vars) = @_;
     my $dbh = Bugzilla->dbh;
+    my $template = Bugzilla->template;
     $vars ||= {};
 
     # Get information about the token being cancelled.
     trick_taint($token);
-    my ($issuedate, $tokentype, $eventdata, $loginname, $realname) =
+    my ($issuedate, $tokentype, $eventdata, $loginname) =
         $dbh->selectrow_array('SELECT ' . $dbh->sql_date_format('issuedate') . ',
-                                      tokentype, eventdata, login_name, realname
+                                      tokentype, eventdata, login_name
                                  FROM tokens
-                           INNER JOIN profiles
+                            LEFT JOIN profiles
                                    ON tokens.userid = profiles.userid
                                 WHERE token = ?',
                                 undef, $token);
 
-    # Get the email address of the Bugzilla maintainer.
-    my $maintainer = Bugzilla->params->{'maintainer'};
-
-    my $template = Bugzilla->template;
-
+    # If we are cancelling the creation of a new user account, then there
+    # is no entry in the 'profiles' table.
+    $loginname ||= $eventdata;
     $vars->{'emailaddress'} = $loginname . Bugzilla->params->{'emailsuffix'};
-    $vars->{'maintainer'} = $maintainer;
+    $vars->{'maintainer'} = Bugzilla->params->{'maintainer'};
     $vars->{'remoteaddress'} = $::ENV{'REMOTE_ADDR'};
     $vars->{'token'} = $token;
     $vars->{'tokentype'} = $tokentype;
index 12c680f7818646a28a84f774c564ae1aee693f46..54d84020fe9322de7aafa083cfb5e6513b917a7d 100644 (file)
@@ -1355,9 +1355,8 @@ sub insert_new_user {
                    VALUES (?, ?, NOW(), ?, NOW())',
                    undef, ($user->id, $who, $creation_date_fieldid));
 
-    # Return the password to the calling code so it can be included
-    # in an email sent to the user.
-    return $password;
+    # Return the newly created user account.
+    return $user;
 }
 
 sub is_available_username {
@@ -1377,15 +1376,18 @@ sub is_available_username {
     # was unsafe and required weird escaping; using substring to pull out
     # the new/old email addresses and sql_position() to find the delimiter (':')
     # is cleaner/safer
-    my $sth = $dbh->prepare(
-        "SELECT eventdata FROM tokens WHERE tokentype = 'emailold'
-        AND SUBSTRING(eventdata, 1, (" 
-        . $dbh->sql_position(q{':'}, 'eventdata') . "-  1)) = ?
-        OR SUBSTRING(eventdata, (" 
-        . $dbh->sql_position(q{':'}, 'eventdata') . "+ 1)) = ?");
-    $sth->execute($username, $username);
-
-    if (my ($eventdata) = $sth->fetchrow_array()) {
+    my $eventdata = $dbh->selectrow_array(
+        "SELECT eventdata
+           FROM tokens
+          WHERE (tokentype = 'emailold'
+                AND SUBSTRING(eventdata, 1, (" .
+                    $dbh->sql_position(q{':'}, 'eventdata') . "-  1)) = ?)
+             OR (tokentype = 'emailnew'
+                AND SUBSTRING(eventdata, (" .
+                    $dbh->sql_position(q{':'}, 'eventdata') . "+ 1)) = ?)",
+         undef, ($username, $username));
+
+    if ($eventdata) {
         # Allow thru owner of token
         if($old_username && ($eventdata eq "$old_username:$username")) {
             return 1;
@@ -1459,7 +1461,7 @@ Bugzilla::User - Object for a Bugzilla user
       $user->get_selectable_classifications;
 
   # Class Functions
-  $password = insert_new_user($username, $realname, $password, $disabledtext);
+  $user = insert_new_user($username, $realname, $password, $disabledtext);
 
 =head1 DESCRIPTION
 
@@ -1815,8 +1817,7 @@ Params: $username (scalar, string) - The login name for the new user.
                                           be sent depending on the user's 
                                           email preferences.
 
-Returns: The password for this user, in plain text, so it can be included
-         in an e-mail sent to the user.
+Returns: The Bugzilla::User object representing the new user account.
 
 =item C<is_available_username>
 
index ab011f3366d990e899ba5bddbf89edede131ae81..6f325347e5cc42fe23606d67ef1055320c205d0a 100755 (executable)
@@ -60,21 +60,13 @@ unless ($createexp) {
 my $login = $cgi->param('login');
 
 if (defined($login)) {
-    # We've been asked to create an account.
-    my $realname = trim($cgi->param('realname'));
-
     validate_email_syntax($login)
       || ThrowUserError('illegal_email_address', {addr => $login});
 
     $vars->{'login'} = $login;
 
-    $dbh->bz_lock_tables('profiles WRITE', 'profiles_activity WRITE',
-                         'user_group_map WRITE', 'email_setting WRITE',
-                         'groups READ', 'tokens READ', 'fielddefs READ');
-
     if (!is_available_username($login)) {
         # Account already exists
-        $dbh->bz_unlock_tables();
         $template->process("account/exists.html.tmpl", $vars)
           || ThrowTemplateError($template->error());
         exit;
@@ -83,17 +75,10 @@ if (defined($login)) {
     if ($login !~ /$createexp/) {
         ThrowUserError("account_creation_disabled");
     }
-    
-    # Create account
-    my $password = insert_new_user($login, $realname);
-
-    $dbh->bz_unlock_tables();
 
-    # Clear out the login cookies in case the user is currently logged in.
-    Bugzilla->logout();
+    # Create and send a token for this new account.
+    Bugzilla::Token::issue_new_user_account_token($login);
 
-    Bugzilla::BugMail::MailPassword($login, $password);
-    
     $template->process("account/created.html.tmpl", $vars)
       || ThrowTemplateError($template->error());
     exit;
index 5124759ed6f3e79ff6022a2628cbad4cf3d46809..f9d310534e77d4ceffacdc21619fcefd01debe0b 100644 (file)
@@ -42,7 +42,9 @@ to [% maintainer %] if you suspect foul play.
 Cancelled Because: [% PROCESS cancelactionmessage %]
 
 [% BLOCK subject %]
-  [% IF tokentype == 'password' %]
+  [% IF tokentype == 'new_account' %]
+    User account creation request cancelled
+  [% ELSIF tokentype == 'password' %]
     Password change request cancelled
   [% ELSIF tokentype == 'emailnew' OR tokentype == 'emailold' %]
     Email change request cancelled
@@ -72,6 +74,10 @@ Cancelled Because: [% PROCESS cancelactionmessage %]
   [% ELSIF cancelaction == 'password_change_cancelled' %]
     You have requested cancellation.
 
+  [% ELSIF cancelaction == 'account_creation_cancelled' %]
+    The creation of the user account [% emailaddress %]
+    has been cancelled.
+
   [% ELSIF cancelaction == 'user_logged_in' %]
     You have logged in.
 
@@ -84,6 +90,9 @@ Cancelled Because: [% PROCESS cancelactionmessage %]
   [% ELSIF cancelaction == 'wrong_token_for_confirming_email_change' %]
     You have tried to use the token to confirm the email address change.
 
+  [% ELSIF cancelaction == 'wrong_token_for_creating_account' %]
+    You have tried to use the token to create a user account.
+
   [% ELSE %]
     [%# Give sensible error if the cancel-token function is used incorrectly.
       #%]
index 052a2b7feef85c15fa9ef64d7b0dea70e896ffd7..2e8739b79c3f593941c5896bc5f35fcd229eaf23 100644 (file)
 [% PROCESS global/variables.none.tmpl %]
 
 [% title = BLOCK %]
-Create a new [% terms.Bugzilla %] account
+  Create a new [% terms.Bugzilla %] account
 [% END %]
-[% PROCESS global/header.html.tmpl %]
+
+[% PROCESS global/header.html.tmpl
+           title = title
+           onload = "document.forms['account_creation_form'].login.focus();" %]
 
 <p>
-  To create a [% terms.Bugzilla %] account, all you need to do is
-  enter a legitimate e-mail address. The account will be created, and
-  its password will be mailed to you. <b>You will not be able to log
-  in until you receive the password.</b> If it doesn't arrive within a
+  To create a [% terms.Bugzilla %] account, all you need to do is to enter
+  a legitimate e-mail address. You will receive an email at this address
+  to confirm the creation of your account. <b>You will not be able to log
+  in until you receive the email.</b> If it doesn't arrive within a
   reasonable amount of time, you can contact the maintainer of
   this [% terms.Bugzilla %] installation
   at <a href="mailto:[% Param("maintainer") %]">[% Param("maintainer") %]</a>.
 </p>
 
-<p>
-  Optionally you may enter your real name as well.
-</p>
-
-<form method="get" action="createaccount.cgi">
+<form id="account_creation_form" method="get" action="createaccount.cgi">
   <table>
     <tr>
       <td align="right">
         <b>E-mail address:</b>
       </td>
       <td>
-        <input size="35" name="login">
+        <input size="35" id="login" name="login">
         [% Param('emailsuffix') FILTER html %]
       </td>
     </tr>
-
-    <tr>
-      <td align="right">
-        <b>Real name:</b>
-      </td>
-      <td>
-        <input size="35" name="realname">
-      </td>
-    </tr>
   </table>
   <br>
-  <input type="submit" id="create" value="Create Account">
+  <input type="submit" id="send" value="Send">
 </form>
 
 [% PROCESS global/footer.html.tmpl %]
index 2d507b4cfd5e901106957d78925475fe707e7ece..58064f24cab40c52d9425c1a3cf8a324bcc82c6e 100644 (file)
   # Rights Reserved.
   #
   # Contributor(s): Gervase Markham <gerv@gerv.net>
+  #                 Frédéric Buclin <LpSolit@gmail.com>
   #%]
 
 [%# INTERFACE:
   # login: string. The user's Bugzilla login email address.
   #%]
 
-[% PROCESS global/header.html.tmpl 
-  title = "Account Created"
-%]
+[% PROCESS global/variables.none.tmpl %]
 
-<p>
-  A new account,  
-  <tt>[% login FILTER html %]</tt>,
-  has been created and a randomly-generated password has been e-mailed 
-  to that address.
-</p>
+[% title = BLOCK %]
+  Request for new user account '[% login FILTER html %]' submitted
+[% END %]
+
+[% PROCESS global/header.html.tmpl title = title %]
 
 <p>
-  When the e-mail arrives, 
-  <a href="index.cgi?GoAheadAndLogIn=1">log in here</a>.
+  To confirm the creation of the user account <tt>[% login FILTER html %]</tt>,
+  use the URL given in the email you will receive. If you take no action in the
+  next [% constants.MAX_TOKEN_AGE FILTER html %] days, this request will
+  automatically be canceled.
 </p>
 
 [% PROCESS global/footer.html.tmpl %] 
diff --git a/template/en/default/account/email/confirm-new.html.tmpl b/template/en/default/account/email/confirm-new.html.tmpl
new file mode 100644 (file)
index 0000000..0e9ab98
--- /dev/null
@@ -0,0 +1,64 @@
+[%# 1.0@bugzilla.org %]
+[%# The contents of this file are subject to the Mozilla Public
+  # License Version 1.1 (the "License"); you may not use this file
+  # except in compliance with the License. You may obtain a copy of
+  # the License at http://www.mozilla.org/MPL/
+  #
+  # Software distributed under the License is distributed on an "AS
+  # IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
+  # implied. See the License for the specific language governing
+  # rights and limitations under the License.
+  #
+  # The Original Code is the Bugzilla Bug Tracking System.
+  #
+  # Contributor(s): Frédéric Buclin <LpSolit@gmail.com>
+  #%]
+
+[%# INTERFACE:
+  # token: string. The token to be used in the user account creation.
+  # email: email address of the user account.
+  # date: creation date of the token.
+  #%]
+
+[% title = BLOCK %]Create a new user account for '[% email FILTER html %]'[% END %]
+[% PROCESS "global/header.html.tmpl"
+           title = title
+           onload = "document.forms['confirm_account_form'].realname.focus();" %]
+
+[% expiration_ts = date + (constants.MAX_TOKEN_AGE * 86400) %]
+<div>
+  To complete the creation of your user account, you must choose a password in the
+  form below. You can also enter your real name, which is optional.<p>
+  If you don't fill this form before
+  <u>[%+ time2str("%H:%M on the %o of %B, %Y", expiration_ts) %]</u>, the creation
+  of this account will be automatically cancelled.
+</div>
+
+<form id="confirm_account_form" method="post" action="token.cgi">
+  <input type="hidden" name="t" value="[% token FILTER html %]">
+  <input type="hidden" name="a" value="confirm_new_account">
+  <table>
+    <tr>
+      <th align="right">Email Address:</th>
+      <td>[% email FILTER html %]</td>
+    </tr>
+    <tr>
+      <th align="right"><label for="realname">Real Name</label>:</th>
+      <td><input type="text" id="realname" name="realname" value=""></td>
+    </tr>
+    <tr>
+      <th align="right"><label for="passwd1">Type your password</label>:</th>
+      <td><input type="password" id="passwd1" name="passwd1" value=""></td>
+    </tr>
+    <tr>
+      <th align="right"><label for="passwd1">Re-type your password</label>:</th>
+      <td><input type="password" id="passwd2" name="passwd2" value=""></td>
+    </tr>
+    <tr>
+      <th align="right">&nbsp;</th>
+      <td><input type="submit" id="confirm" value="Send"></td>
+    </tr>
+  </table>
+</form>
+
+[% PROCESS global/footer.html.tmpl %]
diff --git a/template/en/default/account/email/request-new.txt.tmpl b/template/en/default/account/email/request-new.txt.tmpl
new file mode 100644 (file)
index 0000000..85fdec1
--- /dev/null
@@ -0,0 +1,44 @@
+[%# 1.0@bugzilla.org %]
+[%# The contents of this file are subject to the Mozilla Public
+  # License Version 1.1 (the "License"); you may not use this file
+  # except in compliance with the License. You may obtain a copy of
+  # the License at http://www.mozilla.org/MPL/
+  #
+  # Software distributed under the License is distributed on an "AS
+  # IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
+  # implied. See the License for the specific language governing
+  # rights and limitations under the License.
+  #
+  # The Original Code is the Bugzilla Bug Tracking System.
+  #
+  # Contributor(s): Frédéric Buclin <LpSolit@gmail.com>
+  #%]
+
+[%# INTERFACE:
+  # token: random string used to authenticate the transaction.
+  # token_ts: creation date of the token.
+  # email: email address of the new account.
+  #%]
+
+[% PROCESS global/variables.none.tmpl %]
+
+[% expiration_ts = token_ts + (constants.MAX_TOKEN_AGE * 86400) %]
+From: bugzilla-admin-daemon
+To: [% email %]
+Subject: [% terms.Bugzilla %]: confirm account creation
+
+[%+ terms.Bugzilla %] has received a request to create a user account
+using your email address ([% email %]).
+
+To confirm that you want to create an account using that email address,
+visit the following link:
+
+[%+ Param('urlbase') %]token.cgi?t=[% token FILTER url_quote %]&a=request_new_account
+
+If you are not the person who made this request, or you wish to cancel
+this request, visit the following link:
+
+[%+ Param('urlbase') %]token.cgi?t=[% token FILTER url_quote %]&a=cancel_new_account
+
+If you do nothing, the request will lapse after [%+ constants.MAX_TOKEN_AGE %] days
+(at precisely [%+ time2str("%H:%M on the %o of %B, %Y", expiration_ts) %]).
diff --git a/template/en/default/email/password.txt.tmpl b/template/en/default/email/password.txt.tmpl
deleted file mode 100644 (file)
index 5993a90..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-[%# 1.0@bugzilla.org %]
-[%# The contents of this file are subject to the Mozilla Public
-  # License Version 1.1 (the "License"); you may not use this file
-  # except in compliance with the License. You may obtain a copy of
-  # the License at http://www.mozilla.org/MPL/
-  #
-  # Software distributed under the License is distributed on an "AS
-  # IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
-  # implied. See the License for the specific language governing
-  # rights and limitations under the License.
-  #
-  # The Original Code is the Bugzilla Bug Tracking System.
-  #
-  # The Initial Developer of the Original Code is Netscape Communications
-  # Corporation. Portions created by Netscape are
-  # Copyright (C) 1998 Netscape Communications Corporation. All
-  # Rights Reserved.
-  #
-  # Contributor(s): Emmanuel Seyman <eseyman@linagora.com>
-  #%]
-
-[% PROCESS global/variables.none.tmpl %]
-
-From: bugzilla-daemon
-To: [% mailaddress %]
-Subject: Your [% terms.Bugzilla %] password.
-
-To use the wonders of [% terms.Bugzilla %], you can use the following:
-
- E-mail address:  [% login %]
-       Password:  [% password %]
-
- To change your password, go to:
- [%+ Param("urlbase") %]userprefs.cgi
-
index 08321ed2c27bf585528c1140b63355f0a6dd11f8..2e1878b5feb6e451f4053faa1115cdba0a996a48 100644 (file)
     [% IF groups.size %]
       You may want to edit the group settings now, using the form below.
     [% END %]
+    [% IF login_info %]
+      You can now go to the <a href="index.cgi">Log In</a> page to enter
+      this [% terms.Bugzilla %] installation.
+    [% END %]
+
+  [% ELSIF message_tag == "account_creation_cancelled" %]
+    [% title = "User Account Creation Cancelled" %]
+    The creation of the user account [% account FILTER html %] has been
+    cancelled.
 
   [% ELSIF message_tag == "account_updated" %]
     [% IF changed_fields.size
index 53fb3ae2733afc4647e0362babebe12e8326fe80..e67c1a81cfd3706c37c8ee5e4b1329d65428837a 100644 (file)
 
   [% ELSIF error == "too_soon_for_new_token" %]
     [% title = "Too Soon For New Token" %]
-    You have requested a password token too recently to request
-    another.  Please wait a while and try again.
+    You have requested
+    [% IF type == "password" %]
+      a password
+    [% ELSIF type == "account" %]
+      an account
+    [% END %]
+    token too recently to request another. Please wait a while and try again.
 
   [% ELSIF error == "unknown_keyword" %]
     [% title = "Unknown Keyword" %]
     [% title = "Wrong Token" %]
     That token cannot be used to change your email address.
 
+  [% ELSIF error == "wrong_token_for_creating_account" %]
+    [% title = "Wrong Token" %]
+    That token cannot be used to create a user account.
+
   [% ELSIF error == "zero_length_file" %]
     [% title = "File Is Empty" %]
     The file you are trying to attach is empty!
index 44e4567100ed9b0415ae12fb9d6d6c0e266f3272..6b72dfa363f91cce61ee0710d6f589a1009d5b94 100755 (executable)
--- a/token.cgi
+++ b/token.cgi
@@ -19,6 +19,7 @@
 # Rights Reserved.
 #
 # Contributor(s): Myk Melez <myk@mozilla.org>
+#                 Frédéric Buclin <LpSolit@gmail.com>
 
 ############################################################################
 # Script Initialization
@@ -36,6 +37,8 @@ use Bugzilla::Error;
 use Bugzilla::Token;
 use Bugzilla::User;
 
+use Date::Parse;
+
 my $dbh = Bugzilla->dbh;
 local our $cgi = Bugzilla->cgi;
 local our $template = Bugzilla->template;
@@ -87,6 +90,12 @@ if ($cgi->param('t')) {
     Bugzilla::Token::Cancel($::token, "wrong_token_for_confirming_email_change");
     ThrowUserError("wrong_token_for_confirming_email_change");
   }
+  if (($::action =~ /^(request|confirm|cancel)_new_account$/)
+      && ($tokentype ne 'account'))
+  {
+      Bugzilla::Token::Cancel($::token, 'wrong_token_for_creating_account');
+      ThrowUserError('wrong_token_for_creating_account');
+  }
 }
 
 
@@ -147,6 +156,12 @@ if ($::action eq 'reqpw') {
     cancelChangeEmail();
 } elsif ($::action eq 'chgem') {
     changeEmail();
+} elsif ($::action eq 'request_new_account') {
+    request_create_account();
+} elsif ($::action eq 'confirm_new_account') {
+    confirm_create_account();
+} elsif ($::action eq 'cancel_new_account') {
+    cancel_create_account();
 } else { 
     # If the action that the user wants to take (specified in the "a" form field)
     # is none of the above listed actions, display an error telling the user 
@@ -333,3 +348,75 @@ sub cancelChangeEmail {
       || ThrowTemplateError($template->error());
 }
 
+sub request_create_account {
+    my (undef, $date, $login_name) = Bugzilla::Token::GetTokenData($::token);
+    $vars->{'token'} = $::token;
+    $vars->{'email'} = $login_name . Bugzilla->params->{'emailsuffix'};
+    $vars->{'date'} = str2time($date);
+
+    # We require a HTTPS connection if possible.
+    if (Bugzilla->params->{'sslbase'} ne ''
+        && Bugzilla->params->{'ssl'} ne 'never')
+    {
+        $cgi->require_https(Bugzilla->params->{'sslbase'});
+    }
+    print $cgi->header();
+
+    $template->process('account/email/confirm-new.html.tmpl', $vars)
+      || ThrowTemplateError($template->error());
+}
+
+sub confirm_create_account {
+    my (undef, undef, $login_name) = Bugzilla::Token::GetTokenData($::token);
+
+    (defined $cgi->param('passwd1') && defined $cgi->param('passwd2'))
+      || ThrowUserError('new_password_missing');
+    validate_password($cgi->param('passwd1'), $cgi->param('passwd2'));
+
+    my $realname = $cgi->param('realname');
+    my $password = $cgi->param('passwd1');
+
+    $dbh->bz_lock_tables('profiles WRITE', 'profiles_activity WRITE',
+                         'email_setting WRITE', 'user_group_map WRITE',
+                         'groups READ', 'tokens READ', 'fielddefs READ');
+
+    # The email syntax may have changed since the initial creation request.
+    validate_email_syntax($login_name)
+      || ThrowUserError('illegal_email_address', {addr => $login_name});
+    # Also, maybe that this user account has already been created meanwhile.
+    is_available_username($login_name)
+      || ThrowUserError('account_exists', {email => $login_name});
+
+    # Login and password are validated now, and realname is allowed to
+    # contain anything.
+    trick_taint($realname);
+    trick_taint($password);
+
+    my $otheruser = insert_new_user($login_name, $realname, $password);
+    $dbh->bz_unlock_tables();
+
+    # Now delete this token.
+    Bugzilla::Token::DeleteToken($::token);
+
+    # Let the user know that his user account has been successfully created.
+    $vars->{'message'} = 'account_created';
+    $vars->{'otheruser'} = $otheruser;
+    $vars->{'login_info'} = 1;
+
+    print $cgi->header();
+
+    $template->process('global/message.html.tmpl', $vars)
+      || ThrowTemplateError($template->error());
+}
+
+sub cancel_create_account {
+    my (undef, undef, $login_name) = Bugzilla::Token::GetTokenData($::token);
+
+    $vars->{'message'} = 'account_creation_cancelled';
+    $vars->{'account'} = $login_name;
+    Bugzilla::Token::Cancel($::token, $vars->{'message'});
+
+    print $cgi->header();
+    $template->process('global/message.html.tmpl', $vars)
+      || ThrowTemplateError($template->error());
+}
index 2a890f19d2d25c2c52f3884051aeb64a89122a83..2d7fa4de5d1bc637d29415cf240e7af7eaf1d2f0 100755 (executable)
@@ -53,7 +53,7 @@ sub DoAccount {
        && Bugzilla->user->authorizer->can_change_email) {
         my @token = $dbh->selectrow_array(
             "SELECT tokentype, issuedate + " .
-                    $dbh->sql_interval(3, 'DAY') . ", eventdata
+                    $dbh->sql_interval(MAX_TOKEN_AGE, 'DAY') . ", eventdata
                FROM tokens
               WHERE userid = ?
                 AND tokentype LIKE 'email%'