LP1655158 Patron Search by Date of Birth
authorblake <blake@mobiusconsortium.org>
Thu, 31 Aug 2017 20:33:17 +0000 (20:33 +0000)
committerBill Erickson <berickxx@gmail.com>
Thu, 31 Aug 2017 21:02:59 +0000 (17:02 -0400)
Adds three UI boxes to the WBSC "Show Extra" patron search. One for the year, month and day.
The javascript on the page is altered to deliver group "4" to the backend. Local javascript
strips out non-numeric user entered data. The backend is updated to handle the new group.
SQL is genereated using the DATE_PART postgres function.

1. Open the web based staff client and browse to the patron search UI.
2. Click the show more down arrow button. Notice the lack of birth date field.
3. Apply the patch, repeat step one. Notice the addition of birth date boxes.
4. Type 1975 into the birth year box and press enter. Notice search results.
5. Try searching for partial names and partial birthdates.
6. Try entering non-numeric data into the birth date boxes.
7. Try searching for patrons without including the dob. Try with only the dob. Try a mix.

Signed-off-by: blake <blake@mobiusconsortium.org>
Signed-off-by: Bill Erickson <berickxx@gmail.com>
Open-ILS/src/perlmods/lib/OpenILS/Application/Storage/Publisher/actor.pm
Open-ILS/src/templates/staff/share/t_patron_search_form.tt2
Open-ILS/web/js/ui/default/staff/services/patron_search.js
docs/RELEASE_NOTES_NEXT/Circulation/lp1655158_search_by_dob_NOTES.adoc [new file with mode: 0755]

index bcf4508..a1e634d 100644 (file)
@@ -676,6 +676,7 @@ sub patron_search {
     # group 1 = address
     # group 2 = phone, ident
     # group 3 = barcode
+    # group 4 = dob
 
     # Treatment of name fields depends on whether the org has 
     # diacritic_insensitivity turned on or off.
@@ -685,6 +686,8 @@ sub patron_search {
     $diacritic_insensitive = ($diacritic_insensitive) ? $JSON->JSON2perl($diacritic_insensitive) : 0;
     my $usr;
     my @usrv;
+    my $dob;
+    my @dobv;
 
     if ($diacritic_insensitive) {
        $usr = join ' AND ', map { "evergreen.unaccent_and_squash(CAST($_ AS text)) ~ ?" } grep { ''.$$search{$_}{group} eq '0' } keys %$search;
@@ -695,6 +698,23 @@ sub patron_search {
        @usrv = map { "^" . _clean_regex_chars($$search{$_}{value}) } grep { ''.$$search{$_}{group} eq '0' } keys %$search;
     }
 
+    while (($key, $value) = each (%$search)) {
+        if($$search{$key}{group} eq '4') {
+            my $tval = $key;
+            $tval =~ s/dob_//g;
+            my $right = "RIGHT('0'|| ";
+            my $end = ", 2)";
+            $end = $right = '' if lc $tval eq 'year';
+            $dob .= $right."CAST(DATE_PART('$tval', dob) AS text)$end ~ ? AND ";
+        }
+    }
+    # Trim the last " AND "
+    $dob = substr($dob,0,-4);
+    @dobv = map { _clean_regex_chars($$search{$_}{value}) } grep { ''.$$search{$_}{group} eq '4' } keys %$search;
+    $usr .= ' AND ' if ( $usr && $dob );
+    $usr .= $dob if $dob; # $dob not in-line above in case $usr doesn't have any search vals (only searched for dob)
+    push(@usrv, @dobv) if @dobv;
+
     my $addr = join ' AND ', map { "evergreen.lowercase(CAST($_ AS text)) ~ ?" } grep { ''.$$search{$_}{group} eq '1' } keys %$search;
     my @addrv = map { "^" . _clean_regex_chars($$search{$_}{value}) } grep { ''.$$search{$_}{group} eq '1' } keys %$search;
 
index 49152d3..816076c 100644 (file)
           </div>
         </div>
       </div>
+      <div class="form-group" ng-show="showExtras">
+        <div class="col-md-2">
+            <input type="text" class="form-control" ng-model="searchArgs.dob_year"
+            placeholder="[% l('DOB Year') %]" title="[% l('DOB Year') %]"/>
+        </div>
+        <div class="col-md-2">
+            <input type="text" class="form-control" ng-model="searchArgs.dob_month"
+            placeholder="[% l('DOB Month') %]" title="[% l('DOB Month') %]"/>
+        </div>
+        <div class="col-md-2">
+            <input type="text" class="form-control" ng-model="searchArgs.dob_day"
+            placeholder="[% l('DOB Day') %]" title="[% l('DOB Day') %]"/>
+        </div>
+      </div>
     </form>
   </div>
 </div>
index 97c9152..21e477d 100644 (file)
@@ -760,6 +760,18 @@ function($scope,  $q,  $routeParams,  $timeout,  $window,  $location,  egCore,
                     search[key].group = 1;
                 } else if (key == 'card') {
                     search[key].group = 3
+                } else if (key.match(/dob_/)) {
+                    // DOB should always be numeric
+                    search[key].value = search[key].value.replace(/\D/g,'');
+                    if (search[key].value.length == 0) {
+                        delete search[key];
+                    }
+                    else {
+                        if (!key.match(/year/)) {
+                            search[key].value = ('0'+search[key].value).slice(-2);
+                        }
+                        search[key].group = 4;
+                    }
                 }
             }
         });
diff --git a/docs/RELEASE_NOTES_NEXT/Circulation/lp1655158_search_by_dob_NOTES.adoc b/docs/RELEASE_NOTES_NEXT/Circulation/lp1655158_search_by_dob_NOTES.adoc
new file mode 100755 (executable)
index 0000000..a014859
--- /dev/null
@@ -0,0 +1,8 @@
+Patron Search by Birth Date
+^^^^^^^^^^^^^^^^^^^^^^^^^^^
+* Now you can include the patron birth year and/or birth month and/or
+  birth day when searching for patrons using the web based staff client.
+* Day and month values are exact matches.  E.g. month "1" (or "01")
+  matches January, "12" matches December.
+* Year searches are "contains" searches.  E.g. year "15" matches 2015,
+  1915, 1599, etc.  For exact matches use the full 4-digit year.
\ No newline at end of file