]> git.ipfire.org Git - thirdparty/bugzilla.git/commitdiff
Bug 801664 - Add DATE type for custom fields. r=LpSolit.
authorGervase Markham <gerv@gerv.net>
Wed, 2 Jan 2013 17:58:34 +0000 (17:58 +0000)
committerGervase Markham <gerv@mozilla.org>
Wed, 2 Jan 2013 17:58:34 +0000 (17:58 +0000)
14 files changed:
Bugzilla/Bug.pm
Bugzilla/Constants.pm
Bugzilla/DB/Schema/Mysql.pm
Bugzilla/DB/Schema/Oracle.pm
Bugzilla/DB/Schema/Pg.pm
Bugzilla/DB/Schema/Sqlite.pm
Bugzilla/Field.pm
Bugzilla/Migrate.pm
Bugzilla/Search.pm
Bugzilla/WebService/Bug.pm
importxml.pl
template/en/default/bug/field.html.tmpl
template/en/default/global/field-descs.none.tmpl
template/en/default/search/field.html.tmpl

index c58fec4607579016ff2adb304e33745ee2613ec4..6680ede55fe1cd00c7425f583f215ba6681fcdae 100644 (file)
@@ -146,6 +146,9 @@ sub VALIDATORS {
         elsif ($field->type == FIELD_TYPE_DATETIME) {
             $validator = \&_check_datetime_field;
         }
+        elsif ($field->type == FIELD_TYPE_DATE) {
+            $validator = \&_check_date_field;
+        }
         elsif ($field->type == FIELD_TYPE_FREETEXT) {
             $validator = \&_check_freetext_field;
         }
@@ -233,7 +236,9 @@ use constant NUMERIC_COLUMNS => qw(
 );
 
 sub DATE_COLUMNS {
-    my @fields = @{ Bugzilla->fields({ type => FIELD_TYPE_DATETIME }) };
+    my @fields = (@{ Bugzilla->fields({ type => [FIELD_TYPE_DATETIME,
+                                                 FIELD_TYPE_DATE] })
+                   });
     return map { $_->name } @fields;
 }
 
@@ -1983,8 +1988,13 @@ sub _check_field_is_mandatory {
     }
 }
 
+sub _check_date_field {
+    my ($invocant, $date) = @_;
+    return _check_datetime_field($invocant, $date, 1);
+}
+
 sub _check_datetime_field {
-    my ($invocant, $date_time) = @_;
+    my ($invocant, $date_time, $date_only) = @_;
 
     # Empty datetimes are empty strings or strings only containing
     # 0's, whitespace, and punctuation.
@@ -1998,6 +2008,10 @@ sub _check_datetime_field {
         ThrowUserError('illegal_date', { date   => $date,
                                          format => 'YYYY-MM-DD' });
     }
+    if ($time && $date_only) {
+        ThrowUserError('illegal_date', { date   => $date_time,
+                                         format => 'YYYY-MM-DD' });
+    }
     if ($time && !validate_time($time)) {
         ThrowUserError('illegal_time', { 'time' => $time,
                                          format => 'HH:MM:SS' });
index 8410ae46a732ea8c0a6cb258f4cde21a0f9ff7ac..212816a052f6f62051b0cf6d77fe74c9a5a6938a 100644 (file)
@@ -104,10 +104,12 @@ use Memoize;
     FIELD_TYPE_MULTI_SELECT
     FIELD_TYPE_TEXTAREA
     FIELD_TYPE_DATETIME
+    FIELD_TYPE_DATE
     FIELD_TYPE_BUG_ID
     FIELD_TYPE_BUG_URLS
     FIELD_TYPE_KEYWORDS
-
+    FIELD_TYPE_HIGHEST_PLUS_ONE
+    
     EMPTY_DATETIME_REGEX
 
     ABNORMAL_SELECTS
@@ -385,6 +387,10 @@ use constant FIELD_TYPE_DATETIME  => 5;
 use constant FIELD_TYPE_BUG_ID  => 6;
 use constant FIELD_TYPE_BUG_URLS => 7;
 use constant FIELD_TYPE_KEYWORDS => 8;
+use constant FIELD_TYPE_DATE => 9;
+# Add new field types above this line, and change the below value in the
+# obvious fashion
+use constant FIELD_TYPE_HIGHEST_PLUS_ONE => 10;
 
 use constant EMPTY_DATETIME_REGEX => qr/^[0\-:\sA-Za-z]+$/; 
 
index d448647919d600cd03634864880213b830d83ff2..9d634243f83320887161502541128ba767e55848 100644 (file)
@@ -106,7 +106,7 @@ sub _initialize {
         LONGBLOB =>     'longblob',
 
         DATETIME =>     'datetime',
-
+        DATE     =>     'date',
     };
 
     $self->_adjust_schema;
index 275027954945367c1fa29a4186bc21c5d6887a92..1bed5b5cad7de33d9e16ea38edf44dcb515ecce0 100644 (file)
@@ -56,7 +56,7 @@ sub _initialize {
         LONGBLOB =>     'blob',
 
         DATETIME =>     'date',
-
+        DATE     =>     'date',
     };
 
     $self->_adjust_schema;
index 206a53def343723d64d4bcc7a1d727f26a2bc2b6..fa784ef7d4da82529df5a10749ac3c0b1206e83e 100644 (file)
@@ -66,7 +66,7 @@ sub _initialize {
         LONGBLOB =>     'bytea',
 
         DATETIME =>     'timestamp(0) without time zone',
-
+        DATE     =>     'date',
     };
 
     $self->_adjust_schema;
index 893e2387d84a5f176ab3af9be0d800f15ae88003..b29d7da22585146e1473d965e6b079270f1dc0bf 100644 (file)
@@ -46,6 +46,7 @@ sub _initialize {
         LONGBLOB =>     'blob',
 
         DATETIME =>     'DATETIME',
+        DATE     =>     'DATETIME',
     };
 
     $self->_adjust_schema;
index 14888287a7c9732015a5cfdc69ef94e7f208e065..c85d43bb803816a24658b6e6bf8deeec44c3f17d 100644 (file)
@@ -151,6 +151,7 @@ use constant SQL_DEFINITIONS => {
     FIELD_TYPE_TEXTAREA,      { TYPE => 'MEDIUMTEXT', 
                                 NOTNULL => 1, DEFAULT => "''"},
     FIELD_TYPE_DATETIME,      { TYPE => 'DATETIME'   },
+    FIELD_TYPE_DATE,          { TYPE => 'DATE'       },
     FIELD_TYPE_BUG_ID,        { TYPE => 'INT3'       },
 };
 
@@ -349,9 +350,7 @@ sub _check_sortkey {
 sub _check_type {
     my ($invocant, $type, undef, $params) = @_;
     my $saved_type = $type;
-    # The constant here should be updated every time a new,
-    # higher field type is added.
-    (detaint_natural($type) && $type <= FIELD_TYPE_KEYWORDS)
+    (detaint_natural($type) && $type < FIELD_TYPE_HIGHEST_PLUS_ONE)
       || ThrowCodeError('invalid_customfield_type', { type => $saved_type });
 
     my $custom = blessed($invocant) ? $invocant->custom : $params->{custom};
@@ -952,7 +951,10 @@ sub remove_from_db {
     }
     else {
         $bugs_query = "SELECT COUNT(*) FROM bugs WHERE $name IS NOT NULL";
-        if ($self->type != FIELD_TYPE_BUG_ID && $self->type != FIELD_TYPE_DATETIME) {
+        if ($self->type != FIELD_TYPE_BUG_ID
+            && $self->type != FIELD_TYPE_DATE
+            && $self->type != FIELD_TYPE_DATETIME)
+        {
             $bugs_query .= " AND $name != ''";
         }
         # Ignore the default single select value
index 6671ac3759097dc76d009df7f9a3ffa79d8b50b4..6f3570fd3c9c72bcee21c9e410e9c1da07e63c1c 100644 (file)
@@ -447,8 +447,11 @@ sub translate_value {
     }
 
     my $field_obj = $self->bug_fields->{$field};
-    if ($field eq 'creation_ts' or $field eq 'delta_ts'
-        or ($field_obj and $field_obj->type == FIELD_TYPE_DATETIME))
+    if ($field eq 'creation_ts'
+        or $field eq 'delta_ts'
+        or ($field_obj and
+             ($field_obj->type == FIELD_TYPE_DATETIME
+              or $field_obj->type == FIELD_TYPE_DATE)))
     {
         $value = trim($value);
         return undef if !$value;
index b9c37b4ed385e726bcf7d033de01498c50a42bd3..71893a5fc1ba71fee6694d0134c638b8d9fc538c 100644 (file)
@@ -108,6 +108,7 @@ use Storable qw(dclone);
 
 # When doing searches, NULL datetimes are treated as this date.
 use constant EMPTY_DATETIME => '1970-01-01 00:00:00';
+use constant EMPTY_DATE     => '1970-01-01';
 
 # This is the regex for real numbers from Regexp::Common, modified to be
 # more readable.
@@ -310,6 +311,7 @@ use constant OPERATOR_FIELD_OVERRIDE => {
     FIELD_TYPE_FREETEXT, { _non_changed => \&_nullable },
     FIELD_TYPE_BUG_ID,   { _non_changed => \&_nullable_int },
     FIELD_TYPE_DATETIME, { _non_changed => \&_nullable_datetime },
+    FIELD_TYPE_DATE,     { _non_changed => \&_nullable_date },
     FIELD_TYPE_TEXTAREA, { _non_changed => \&_nullable },
     FIELD_TYPE_MULTI_SELECT, MULTI_SELECT_OVERRIDE,
     FIELD_TYPE_BUG_URLS,     MULTI_SELECT_OVERRIDE,    
@@ -2511,6 +2513,13 @@ sub _nullable_datetime {
     $args->{full_field} = "COALESCE($field, $empty)";
 }
 
+sub _nullable_date {
+    my ($self, $args) = @_;
+    my $field = $args->{full_field};
+    my $empty = Bugzilla->dbh->quote(EMPTY_DATE);
+    $args->{full_field} = "COALESCE($field, $empty)";
+}
+
 sub _deadline {
     my ($self, $args) = @_;
     my $field = $args->{full_field};
index 7099833899639f7aaabb5965be235397c1577ace..fe102f70dd7c7f6097bc8498cc3ec32dd5bd062a 100644 (file)
@@ -929,7 +929,9 @@ sub _bug_to_hash {
         if ($field->type == FIELD_TYPE_BUG_ID) {
             $item{$name} = $self->type('int', $bug->$name);
         }
-        elsif ($field->type == FIELD_TYPE_DATETIME) {
+        elsif ($field->type == FIELD_TYPE_DATETIME
+               || $field->type == FIELD_TYPE_DATE)
+        {
             $item{$name} = $self->type('dateTime', $bug->$name);
         }
         elsif ($field->type == FIELD_TYPE_MULTI_SELECT) {
index 92a85c6da65246af2f468a525d524949af1b34f8..4e78f093f7caad8f9ec89220153c3bb8ff990c7e 100755 (executable)
@@ -1023,6 +1023,15 @@ sub process_bug {
                 push(@query, $custom_field);
                 push(@values, $value);
             }
+        } elsif ($field->type == FIELD_TYPE_DATE) {
+            eval { $value = Bugzilla::Bug->_check_date_field($value); };
+            if ($@) {
+                $err .= "Skipping illegal value \"$value\" in $custom_field.\n" ;
+            }
+            else {
+                push(@query, $custom_field);
+                push(@values, $value);
+            }
         } else {
             $err .= "Type of custom field $custom_field is an unhandled FIELD_TYPE: " .
                     $field->type . "\n";
index 4255b1702144168f7f8f3c27fff6b31eebe367b5..ef4d0e8b1d9f2a3bd253e54d3f0e845700620061 100644 (file)
@@ -41,8 +41,9 @@
                value="[% value FILTER html %]" size="40"
                maxlength="[% constants.MAX_FREETEXT_LENGTH FILTER none %]"
                [% ' aria-required="true"' IF field.is_mandatory %]>
-    [% CASE constants.FIELD_TYPE_DATETIME %]
-      <input name="[% field.name FILTER html %]" size="20"
+    [% CASE [constants.FIELD_TYPE_DATETIME, constants.FIELD_TYPE_DATE] %]
+      [% size = (field.type == constants.FIELD_TYPE_DATE) ? 10 : 20 %]
+      <input name="[% field.name FILTER html %]" size="[% size FILTER none %]"
              id="[% field.name FILTER html %]"
              value="[% value FILTER html %]"
              [% ' aria-required="true"' IF field.is_mandatory %]
index f1e0747dabcee0f8920cafe8e69844e79182ec13..948ee5efa502067d2b04285bd692f567442b8065 100644 (file)
@@ -43,6 +43,7 @@
                    ${constants.FIELD_TYPE_MULTI_SELECT}  => "Multiple-Selection Box",
                    ${constants.FIELD_TYPE_TEXTAREA}      => "Large Text Box",
                    ${constants.FIELD_TYPE_DATETIME}      => "Date/Time",
+                   ${constants.FIELD_TYPE_DATE}          => "Date",
                    ${constants.FIELD_TYPE_BUG_ID}        => "$terms.Bug ID",
                 } %]
 
index ab73808571ee6cc50789ec562b44a08fbeeb5640..dc1592e380b7281543ecf0439e25e69bdd154dd1 100644 (file)
@@ -52,7 +52,7 @@
       YAHOO.bugzilla.fieldAutocomplete.init('[% field.name FILTER js %]',
                                             '[% field.name FILTER js %]_autocomplete');
     </script>
-  [% CASE constants.FIELD_TYPE_DATETIME %]
+  [% CASE [constants.FIELD_TYPE_DATETIME, constants.FIELD_TYPE_DATE] %]
     [% INCLUDE "bug/field-label.html.tmpl"
       field = field
       tag_name = "span"