diff options
-rw-r--r-- | Bugzilla/Flag.pm | 59 | ||||
-rw-r--r-- | Bugzilla/User.pm | 36 | ||||
-rwxr-xr-x | attachment.cgi | 2 | ||||
-rwxr-xr-x | process_bug.cgi | 7 | ||||
-rw-r--r-- | template/en/default/global/confirm-user-match.html.tmpl | 15 | ||||
-rw-r--r-- | template/en/default/request/verify.html.tmpl | 108 |
6 files changed, 52 insertions, 175 deletions
diff --git a/Bugzilla/Flag.pm b/Bugzilla/Flag.pm index 997b46bf7..7395be09d 100644 --- a/Bugzilla/Flag.pm +++ b/Bugzilla/Flag.pm @@ -368,10 +368,6 @@ sub clear { sub FormToNewFlags { my ($target, $data) = @_; - # Flag for whether or not we must get verification of the requestees - # (if the user did not uniquely identify them). - my $verify_requestees = 0; - # Get information about the setter to add to each flag. # Uses a conditional to suppress Perl's "used only once" warnings. my $setter = new Bugzilla::User($::userid); @@ -396,67 +392,20 @@ sub FormToNewFlags { my $requestee_str = $data->{"requestee-$type_id"} || $data->{'requestee'}; if ($requestee_str) { - $flag->{'requestee_str'} = $requestee_str; - MatchRequestees($flag); - $verify_requestees = 1 if scalar(@{$flag->{'requestees'}}) != 1; + my $requestee_id = &::DBname_to_id($requestee_str); + $requestee_id + || &::ThrowUserError("invalid_username", {name => $requestee_str}); + $flag->{'requestee'} = new Bugzilla::User($requestee_id); } # Add the flag to the array of flags. push(@flags, $flag); } - if ($verify_requestees) { - $::vars->{'target'} = $target; - $::vars->{'flags'} = \@flags; - $::vars->{'form'} = $data; - $::vars->{'mform'} = \%::MFORM || \%::MFORM; - - print "Content-Type: text/html\n\n" unless $::vars->{'header_done'}; - $::template->process("request/verify.html.tmpl", $::vars) - || &::ThrowTemplateError($::template->error()); - exit; - } - # Return the list of flags. return \@flags; } -sub MatchRequestees { - my ($flag) = @_; - - my $requestee_str = $flag->{'requestee_str'}; - - # To reduce the size of queries, require the user to enter at least - # three characters of each requestee's name unless this installation - # automatically appends an email suffix to each user's login name, - # in which case we can't guarantee their names are at least three - # characters long. - if (!Param('emailsuffix') && length($requestee_str) < 3) { - &::ThrowUserError("requestee_too_short"); - } - - # Get a list of potential requestees whose email address or real name - # matches the substring entered by the user. Try an exact match first, - # then fall back to a substring search. Limit search to 100 matches, - # since at that point there are too many to make the user wade through, - # and we need to get the user to enter a more constrictive match string. - my $user_id = &::DBname_to_id($requestee_str); - if ($user_id) { $flag->{'requestees'} = [ new Bugzilla::User($user_id) ] } - else { $flag->{'requestees'} = Bugzilla::User::match($requestee_str, 101, 1) } - - # If there is only one requestee match, make them the requestee. - if (scalar(@{$flag->{'requestees'}}) == 1) { - $flag->{'requestee'} = $flag->{'requestees'}[0]; - } - - # If there are too many requestee matches, throw an error. - elsif (scalar(@{$flag->{'requestees'}}) == 101) { - &::ThrowUserError("requestee_too_many_matches", - { requestee => $requestee_str }); - } -} - - # Ideally, we'd use Bug.pm, but it's way too heavyweight, and it can't be # made lighter without totally rewriting it, so we'll use this function # until that one gets rewritten. diff --git a/Bugzilla/User.pm b/Bugzilla/User.pm index 1506e5dde..3bc02c723 100644 --- a/Bugzilla/User.pm +++ b/Bugzilla/User.pm @@ -217,6 +217,35 @@ sub match_field { # What does a "--do_not_change--" field look like (if any)? my $dontchange = $vars->{'form'}->{'dontchange'}; + # Fields can be regular expressions matching multiple form fields + # (f.e. "requestee-(\d+)"), so expand each non-literal field + # into the list of form fields it matches. + my $expanded_fields = {}; + foreach my $field_pattern (keys %{$fields}) { + # Check if the field has any non-word characters. Only those fields + # can be regular expressions, so don't expand the field if it doesn't + # have any of those characters. + if ($field_pattern =~ /^\w+$/) { + $expanded_fields->{$field_pattern} = $fields->{$field_pattern}; + } + else { + my @field_names = grep(/$field_pattern/, keys %{$vars->{'form'}}); + foreach my $field_name (@field_names) { + $expanded_fields->{$field_name} = + { type => $fields->{$field_pattern}->{'type'} }; + + # The field is a requestee field; in order for its name to show + # up correctly on the confirmation page, we need to find out + # the name of its flag type. + if ($field_name =~ /^requestee-(\d+)$/) { + $expanded_fields->{$field_name}->{'flag_type'} = + Bugzilla::FlagType::get($1); + } + } + } + } + $fields = $expanded_fields; + # Skip all of this if the option has been turned off return 1 if (&::Param('usermatchmode') eq 'off'); @@ -285,10 +314,8 @@ sub match_field { next; } - $matches->{$field}->{$query}->{'users'} = $users; - $matches->{$field}->{$query}->{'status'} = 'success'; - $matches->{$field}->{$query}->{'selecttype'} = - $fields->{$field}->{'type'}; + $matches->{$field}->{$query}->{'users'} = $users; + $matches->{$field}->{$query}->{'status'} = 'success'; # here is where it checks for multiple matches @@ -323,6 +350,7 @@ sub match_field { return 1 unless $need_confirm; # skip confirmation if not needed. $vars->{'script'} = $ENV{'SCRIPT_NAME'}; # for self-referencing URLs + $vars->{'fields'} = $fields; # fields being matched $vars->{'matches'} = $matches; # matches that were made $vars->{'matchsuccess'} = $matchsuccess; # continue or fail diff --git a/attachment.cgi b/attachment.cgi index 6e9379af1..971968b3e 100755 --- a/attachment.cgi +++ b/attachment.cgi @@ -44,6 +44,7 @@ require "CGI.pl"; # Use these modules to handle flags. use Bugzilla::Flag; use Bugzilla::FlagType; +use Bugzilla::User; # Establish a connection to the database backend. ConnectToDatabase(); @@ -109,6 +110,7 @@ elsif ($action eq "update") validateContentType() unless $::FORM{'ispatch'}; validateIsObsolete(); validatePrivate(); + Bugzilla::User::match_field({ '^requestee-(\d+)$' => { 'type' => 'single' } }); Bugzilla::Flag::validate(\%::FORM); Bugzilla::FlagType::validate(\%::FORM); update(); diff --git a/process_bug.cgi b/process_bug.cgi index 0450b7ce9..bcc5dd2c7 100755 --- a/process_bug.cgi +++ b/process_bug.cgi @@ -91,9 +91,10 @@ scalar(@idlist) || ThrowUserError("no_bugs_chosen"); # do a match on the fields if applicable &Bugzilla::User::match_field({ - 'qa_contact' => { 'type' => 'single' }, - 'newcc' => { 'type' => 'multi' }, - 'assigned_to' => { 'type' => 'single' }, + 'qa_contact' => { 'type' => 'single' }, + 'newcc' => { 'type' => 'multi' }, + 'assigned_to' => { 'type' => 'single' }, + '^requestee-(\d+)$' => { 'type' => 'single' }, }); # If we are duping bugs, let's also make sure that we can change diff --git a/template/en/default/global/confirm-user-match.html.tmpl b/template/en/default/global/confirm-user-match.html.tmpl index 2c1d0d2bd..4a12f44a9 100644 --- a/template/en/default/global/confirm-user-match.html.tmpl +++ b/template/en/default/global/confirm-user-match.html.tmpl @@ -23,13 +23,15 @@ [%# INTERFACE: # form: hash; the form values submitted to the script # mform: hash; the form multi-values submitted to the script + # fields: hash/record; the fields being matched, each of which has: + # type: single|multi: whether or not the user can select multiple matches + # flag_type: for flag requestee fields, the type of flag being requested # matches: hash; Hierarchical. The levels go like this: # field_name { # pattern_text { - # 'users' = @user_list (user objects) - # 'selecttype' = single|multi (selectbox type) - # 'status' = success|fail|trunc (result of search. - # 'trunc' (truncated) means max was reached) + # 'users' = @user_list (user objects) + # 'status' = success|fail|trunc (result of search. + # 'trunc' (truncated) means max was reached) # } # } # script: string; The name of the calling script, used to create a @@ -90,7 +92,7 @@ </font> Please go back and try again with a more specific name/address. - [% ELSIF query.value.selecttype == 'single' %] + [% ELSIF fields.${field.key}.type == 'single' %] matched:<br> <select name="[% field.key FILTER html %]" id="[% field.key FILTER html %]"> @@ -173,6 +175,9 @@ [%- # ELSIF for things that don't belong in the field_descs hash here -%] + [% ELSIF field_name.match("^requestee") %] + [% fields.${field_name}.flag_type.name %] requestee + [% ELSE %] [% field_name FILTER html %] [% END %] diff --git a/template/en/default/request/verify.html.tmpl b/template/en/default/request/verify.html.tmpl deleted file mode 100644 index ad4c07d2c..000000000 --- a/template/en/default/request/verify.html.tmpl +++ /dev/null @@ -1,108 +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): Myk Melez <myk@mozilla.org> - #%] - -[%# INTERFACE: - # form, mform: hashes; the form values submitted to the script, used by - # hidden-fields to generate hidden form fields replicating - # the original form - # flags: array; the flags the user made, including information about - # potential requestees for those flags (based on - # the string the user typed into the requestee fields) - # target: record; the bug/attachment for which the flags are being made - #%] - -[% UNLESS header_done %] - [% title = BLOCK %] - Verify Requests for Bug #[% target.bug.id %] - [% IF target.attachment %], Attachment #[% target.attachment.id %][% END %] - [% END %] - - [% h1 = BLOCK %] - Verify Requests for <a href="show_bug.cgi?id=[% target.bug.id %]">Bug #[% target.bug.id %]</a> - [% IF target.attachment.exists %], - <a href="attachment.cgi?id=[% target.attachment.id %]&action=edit">Attachment #[% target.attachment.id %]</a> - [% END %] - [% END %] - - [% h2 = BLOCK %] - [% target.bug.summary FILTER html %] - [% IF target.attachment.exists %] - : [% target.attachment.summary FILTER html %] - [% END %] - [% END %] - - [% PROCESS global/header.html.tmpl %] -[% END %] - -<form method="post"> - -[% PROCESS "global/hidden-fields.html.tmpl" - exclude=("^(flag_type|requestee)-") %] - -[% FOREACH flag = flags %] - [% IF flag.requestees.size == 0 %] - <p> - Sorry, I can't find a user whose name or email address contains - the string <em>[% flag.requestee_str FILTER html %]</em>. - Double-check that the user's name or email address contains that - string, or try entering a shorter string. - </p> - <p> - Ask <input type="text" size="20" maxlength="255" - name="requestee-[% flag.type.id %]" - value="[% flag.requestee_str FILTER html %]"> - for [% flag.type.name FILTER html %] - <input type="hidden" name="flag_type-[% flag.type.id %]" value="?"> - </p> - - [% ELSIF flag.requestees.size == 1 %] - <input type="hidden" - name="requestee-[% flag.type.id %]" - value="[% flag.requestee.email FILTER html %]"> - <input type="hidden" name="flag_type-[% flag.type.id %]" value="?"> - - [% ELSE %] - <p> - More than one user's name or email address contains the string - <em>[% flag.requestee_str FILTER html %]</em>. Choose the user - you meant from the following menu or click the back button and try - again with a more specific string. - </p> - <p> - Ask <select name="requestee-[% flag.type.id %]"> - [% FOREACH requestee = flag.requestees %] - <option value="[% requestee.email FILTER html %]"> - [% requestee.identity FILTER html%]</option> - [% END %] - </select> - for [% flag.type.name %] - <input type="hidden" name="flag_type-[% flag.type.id %]" value="?"> - </p> - - [% END %] -[% END %] - -<input type="submit" value="Commit"> - -</form> - -[% PROCESS global/footer.html.tmpl %] - |