Count in transit duplicates, metrics, testing
authorDoug Kyle <dkyle@grpl.org>
Tue, 10 Jun 2014 20:34:49 +0000 (16:34 -0400)
committerDoug Kyle <dkyle@grpl.org>
Tue, 10 Jun 2014 20:34:49 +0000 (16:34 -0400)
In transit dup counts, Optional and better metrics, rough cgi test script

Signed-off-by: Doug Kyle <dkyle@grpl.org>
Open-ILS/src/sql/Pg/002.functions.config.sql
Open-ILS/src/sql/Pg/smart_float.sql
Open-ILS/src/sql/Pg/version-upgrade/2.5.2-2.5.3-upgrade-db.sql
Open-ILS/src/support-scripts/test-scripts/smart_float_test.cgi [new file with mode: 0755]

index 3dab7d9..2c5ab18 100644 (file)
@@ -353,6 +353,10 @@ if ($schema eq 'biblio') {
         $new_901->add_subfields("d" => $_TD->{new}{share_depth});
     }
 
+    if ($_TD->{new}{source}) {
+        $new_901->add_subfields("s" => $_TD->{new}{source});
+    }
+
     $marc->append_fields($new_901);
 } elsif ($schema eq 'authority') {
     my $new_901 = MARC::Field->new("901", " ", " ",
index e64dc88..eedb492 100644 (file)
@@ -13,6 +13,7 @@ shelf_is_group BOOL NOT NULL DEFAULT FALSE,
 items_allowed INT,
 homing_threshold INT NOT NULL DEFAULT 0,
 homing_lifespan TEXT DEFAULT '1 day',
+log_metrics BOOL NOT NULL DEFAULT FALSE,
 CONSTRAINT org_unit_fkey  FOREIGN KEY (org_unit) REFERENCES actor.org_unit (id) DEFERRABLE INITIALLY DEFERRED,
 CONSTRAINT org_plus_loc UNIQUE(org_unit,shelf_location)
 );
@@ -26,20 +27,29 @@ BEGIN
     RETURN QUERY with sflibs as (
         select org_unit from config.smart_float where active is true group by 1
 ),
+dupcops as (select circ_lib,id from asset.copy where call_number in (select id from asset.call_number where record in (select record from asset.call_number join asset.copy on call_number.id=copy.call_number and copy.barcode=bcode))
+),
+holdtransits as (
+select target_copy from action.hold_transit_copy where dest_recv_time is null
+),
 duplibs as (
-select circ_lib,count(circ_lib) from asset.copy where barcode != bcode and status in (0,7) and call_number in (select id from asset.call_number where record in (select record from asset.call_number join asset.copy on call_number.id=copy.call_number and copy.barcode=bcode and copy.deleted is false)) group by 1
+select circ_lib,count(circ_lib) from asset.copy where barcode != bcode and status in (0,6,7) and deleted is false and id in (select id from dupcops) and id not in (select target_copy from holdtransits) group by 1
 )
-select sflibs.org_unit,coalesce(duplibs.count,0) as count from sflibs left join duplibs on sflibs.org_unit=duplibs.circ_lib;
+select sflibs.org_unit,coalesce(duplibs.count,0) as count from sflibs left join duplibs on sflibs.org_unit=duplibs.circ_lib order by 1;
 END;
 $function$;
 
 -- !!! smart_float.opens_and_dups !!! 
-CREATE OR REPLACE FUNCTION smart_float.opens_and_dups(bcode text, cloc integer)
- RETURNS TABLE(clib integer, taken bigint, allowed integer, open bigint, dups bigint, dups_threshold integer)
+CREATE OR REPLACE FUNCTION smart_float.opens_and_dups(bcode text)
+ RETURNS TABLE(clib integer, taken bigint, allowed integer, open bigint, dups_threshold integer, dups bigint)
  LANGUAGE plpgsql
 AS $function$
+DECLARE
+    cloc INT;
+
 BEGIN
-    RETURN QUERY select copy.circ_lib,count(copy.id),sf.items_allowed,(sf.items_allowed-count(copy.id)) as spaces,(select numdups from smart_float.dups(bcode) where smart_float_dups.clib=copy.circ_lib) as dups, sf.dups_threshold from asset.copy join config.smart_float sf on (copy.circ_lib=sf.org_unit and copy.location=sf.shelf_location and sf.active is true) where copy.location=cloc and copy.status in (0,7) group by circ_lib,sf.items_allowed,sf.dups_threshold;
+    SELECT INTO cloc location from asset.copy where barcode=bcode;
+    RETURN QUERY select openings.*,dups.numdups from smart_float.dups(bcode), smart_float.openings(cloc) where dups.clib=openings.clib;
 END;
 $function$;
 
@@ -113,7 +123,7 @@ DECLARE
     send_lib INT;
     homing_threshold_met BOOL;
     circs_needed INT;
-    days_to_go INT;    
+    days_to_go INT;
     open_space INT;
     duplicates INT;
     opcode TEXT;
@@ -124,8 +134,10 @@ BEGIN
     SELECT INTO shelf_loc_atts * FROM config.smart_float WHERE org_unit = chkin_org and shelf_location = copy_rec.location and active is true;
     IF NOT FOUND THEN
           -- no smart_float config for this org and shelf, so dumb float it here
-          PERFORM smart_float.save_metric(copy_rec.id,copy_rec.circ_lib,origin_owner,chkin_org,NULL,NULL,chkin_org,'not_active',NULL,NULL,NULL);
-          RETURN chkin_org;
+        IF shelf_loc_atts.log_metrics IS TRUE THEN
+           PERFORM smart_float.save_metric(copy_rec.id,copy_rec.circ_lib,origin_owner,chkin_org,NULL,NULL,chkin_org,'not_active',NULL,NULL,NULL);
+        END IF;
+           RETURN chkin_org;
     END IF;
 
     SELECT INTO origin_loc_atts * FROM config.smart_float WHERE org_unit = origin_owner and shelf_location = copy_rec.location;
@@ -133,10 +145,19 @@ BEGIN
 
    IF homing_threshold_met IS FALSE THEN
         -- send home, homing threshold not met
-        PERFORM smart_float.save_metric(copy_rec.id,copy_rec.circ_lib,origin_owner,chkin_org,NULL,NULL,NULL,'homed',origin_loc_atts.*,circs_needed,days_to_go);
+        IF shelf_loc_atts.log_metrics IS TRUE THEN
+           PERFORM smart_float.save_metric(copy_rec.id,copy_rec.circ_lib,origin_owner,chkin_org,NULL,NULL,NULL,'homed',origin_loc_atts.*,circs_needed,days_to_go);
+        END IF;
         RETURN origin_owner;
     END IF;
 
+   IF shelf_loc_atts.log_metrics IS TRUE THEN
+        -- store checkin lib data
+        SELECT INTO send_lib,open_space,duplicates o.clib,o.open,d.numdups from smart_float.openings(copy_rec.location) as o join smart_float.dups(copy_rec.barcode) as d on d.clib=o.clib where o.clib=chkin_org;
+        PERFORM smart_float.save_metric(copy_rec.id,copy_rec.circ_lib,origin_owner,chkin_org,open_space,duplicates,send_lib,'checkin',shelf_loc_atts.*,NULL,NULL);
+    END IF;
+
+
     -- can item float to checkin lib? aka the shelving location is not full and has less than dups_threshold duplicate titles?
     opcode := 'floated';
     SELECT INTO send_lib,open_space,duplicates o.clib,o.open,d.numdups from smart_float.openings(copy_rec.location) as o join smart_float.dups(copy_rec.barcode) as d on d.clib=o.clib where o.clib=chkin_org and o.open>0 and (d.numdups<o.dups_threshold or d.numdups=0);
@@ -156,7 +177,11 @@ BEGIN
                 END IF;
         END IF;
     END IF;
-    PERFORM smart_float.save_metric(copy_rec.id,copy_rec.circ_lib,origin_owner,chkin_org,open_space,duplicates,send_lib,opcode,shelf_loc_atts.*,NULL,NULL);
+    IF shelf_loc_atts.log_metrics IS TRUE THEN
+       -- store destination lib data
+       SELECT INTO shelf_loc_atts * FROM config.smart_float WHERE org_unit = send_lib and shelf_location = copy_rec.location;
+       PERFORM smart_float.save_metric(copy_rec.id,copy_rec.circ_lib,origin_owner,chkin_org,open_space,duplicates,send_lib,opcode,shelf_loc_atts.*,NULL,NULL);
+    END IF;
     RETURN send_lib;
 END;
 $function$;
@@ -267,9 +292,30 @@ CREATE OR REPLACE FUNCTION smart_float.add2_cap_store()
  LANGUAGE plpgsql
 AS $function$
 BEGIN
-  insert into smart_float.cap_store (branch,taken,allowed,open,percent_capacity,name,shelf_loc,cap_date) select sfcap.*,date(now()) from grpl.smart_float_capacities() sfcap;
+  insert into smart_float.cap_store (branch,taken,allowed,open,percent_capacity,name,shelf_loc,cap_date) select sfcap.*,date(now()) from smart_float.capacities() sfcap;
 END;
 $function$;
 
+-- smart_float.shelf_summary
+CREATE OR REPLACE FUNCTION smart_float.shelf_summary(sloc integer)
+ RETURNS TABLE(branch text, allowed integer, taken bigint, open bigint, available bigint, reshelving bigint, transit bigint)
+ LANGUAGE plpgsql
+ STABLE
+AS $function$
+BEGIN
+RETURN QUERY with a as(
+        select count(*) as available,circ_lib from asset.copy where location=sloc and status=0 and deleted is false group by circ_lib
+),
+r as (
+         select count(*) as reshelving,circ_lib from asset.copy where location=sloc and status=7 and deleted is false group by circ_lib
+),
+v as (
+        select arriving,library from smart_float.shelving_location_non_hold_transit_vectors(sloc)
+)
+select aou.shortname,o.allowed,o.taken,o.open,a.available,r.reshelving,v.arriving from actor.org_unit aou join smart_float.openings(sloc) o on aou.id=o.clib join a on o.clib=a.circ_lib join r on o.clib=r.circ_lib join v on o.clib=v.library;
+END;
+$function$;
+
+
 -- !!! need some new indexes
 create index concurrently cp_location_idx on asset.copy (location);
index 4c38217..b7e4741 100644 (file)
@@ -58,6 +58,10 @@ if ($schema eq 'biblio') {
         $new_901->add_subfields("d" => $_TD->{new}{share_depth});
     }
 
+    if ($_TD->{new}{source}) {
+        $new_901->add_subfields("s" => $_TD->{new}{source});
+    }
+
     $marc->append_fields($new_901);
 } elsif ($schema eq 'authority') {
     my $new_901 = MARC::Field->new("901", " ", " ",
diff --git a/Open-ILS/src/support-scripts/test-scripts/smart_float_test.cgi b/Open-ILS/src/support-scripts/test-scripts/smart_float_test.cgi
new file mode 100755 (executable)
index 0000000..024ce5c
--- /dev/null
@@ -0,0 +1,36 @@
+#!/usr/bin/perl -w
+
+use DBI;
+use CGI qw(:standard);
+print header;
+
+our %config;
+do '/openils/conf/live-db-setup.pl';
+
+my $bcode = param('bcode');
+
+unless ($bcode) {
+  print "<form method=post>Enter Item Barcode: <input name=bcode><submit></form><p>";
+  exit;
+}
+
+my $dbh = DBI->connect($config{dsn},$config{usr},$config{pw});
+my $cid = $dbh->prepare("select id,location from asset.copy where barcode=?");
+$cid->execute($bcode);
+my $cr = $cid->fetch;
+my $cp = $cr->[0];
+my $cl = $cr->[1];
+
+my $odresult = `/usr/local/pgsql/bin/psql -U postgres -c "select * from smart_float.opens_and_dups('$bcode')" -H evergreen`;
+print "Item $bcode Location $cl <br> $odresult";
+
+foreach $cklib (11..17) { #alter loop for your orgs
+print "Checkin at $cklib<br>";
+$dresult = `/usr/local/pgsql/bin/psql -U postgres -c "select * from smart_float.destination($cklib,$cp)" -H evergreen`;
+print $dresult;
+print "Metrics<br>";
+$mresult = `/usr/local/pgsql/bin/psql -U postgres -c "select * from smart_float.metrics where copy_id = $cp order by id desc limit 2" -H evergreen`;
+print $mresult;
+}
+
+exit;