From f046fa0a17dc74916c62a255f8d08d7e9f3314af Mon Sep 17 00:00:00 2001
From: Bill Erickson <berick@esilibrary.com>
Date: Mon, 6 Feb 2012 12:31:23 -0500
Subject: [PATCH] User activity tracking : user usr_activity field

Added a new virtual field to actor.usr called "usr_activity".  When
fleshed, the value contains the most recent activities logged for the
user.  By default, only the most recent activity entry is fetched,
however this commit also adds an org unit setting
"circ.patron.usr_activity_retrieve.max" to control the number of entries
returned for standard patron fleshing calls.

Activity entries are fleshed in the calls:

open-ils.actor.user.fleshed.retrieve
open-ils.actor.user.fleshed.retrieve_by_barcode

This change also updates the permacrud <retrieve> permission for
usr_activity form VIEW_USER to RUN_REPORTS, with the assumption that
any activity data beyond the configured amount (above) should be
considered historical data that is not as readily accessable.

Signed-off-by: Bill Erickson <berick@esilibrary.com>
Signed-off-by: Thomas Berezansky <tsbere@mvlc.org>
---
 Open-ILS/examples/fm_IDL.xml                       |  4 ++-
 .../src/perlmods/lib/OpenILS/Application/Actor.pm  | 34 +++++++++++++++++++++-
 Open-ILS/src/sql/Pg/950.data.seed-values.sql       | 20 +++++++++++++
 .../sql/Pg/upgrade/XXXX.schema.user-activity.sql   | 21 +++++++++++++
 4 files changed, 77 insertions(+), 2 deletions(-)

diff --git a/Open-ILS/examples/fm_IDL.xml b/Open-ILS/examples/fm_IDL.xml
index 237c8c227a..2924bfca5c 100644
--- a/Open-ILS/examples/fm_IDL.xml
+++ b/Open-ILS/examples/fm_IDL.xml
@@ -2703,6 +2703,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA
 			<field reporter:label="Circulations Performed as Staff" name="performed_circulations" oils_persist:virtual="true" reporter:datatype="link"/>
 			<field reporter:label="Fund Allocation Percentages" name="fund_alloc_pcts" oils_persist:virtual="true" reporter:datatype="link"/>
 			<field reporter:label="Reservations" name="reservations" oils_persist:virtual="true" reporter:datatype="link"/>
+			<field reporter:label="User Activity Entries" name="usr_activity" oils_persist:virtual="true" reporter:datatype="link"/>
 		</fields>
 		<links>
 			<link field="demographic" reltype="might_have" key="id" map="" class="rud"/>
@@ -2734,6 +2735,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA
 			<link field="performed_circulations" reltype="has_many" key="circ_staff" map="" class="circ"/>
 			<link field="fund_alloc_pcts" reltype="has_many" key="allocator" map="" class="acqfap"/>
 			<link field="reservations" reltype="has_many" key="usr" map="" class="bresv"/>
+			<link field="usr_activity" reltype="has_many" key="usr" map="" class="auact"/>
 		</links>
 	</class>
 	<class id="cuat" controller="open-ils.cstore open-ils.pcrud" oils_obj:fieldmapper="config::usr_activity_type" oils_persist:tablename="config.usr_activity_type" reporter:label="User Activity Type">
@@ -2769,7 +2771,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA
 		</links>
 		<permacrud xmlns="http://open-ils.org/spec/opensrf/IDL/permacrud/v1">
 			<actions>
-				<retrieve permission="VIEW_USER">
+				<retrieve permission="RUN_REPORTS">
 					<context link="usr" field="home_ou" />
 				</retrieve>
 			</actions>
diff --git a/Open-ILS/src/perlmods/lib/OpenILS/Application/Actor.pm b/Open-ILS/src/perlmods/lib/OpenILS/Application/Actor.pm
index 60118d34e3..627ee87bcc 100644
--- a/Open-ILS/src/perlmods/lib/OpenILS/Application/Actor.pm
+++ b/Open-ILS/src/perlmods/lib/OpenILS/Application/Actor.pm
@@ -2955,7 +2955,8 @@ sub user_retrieve_fleshed_by_id {
 		"addresses",
 		"billing_address",
 		"mailing_address",
-		"stat_cat_entries" ];
+		"stat_cat_entries",
+		"usr_activity" ];
 	return new_flesh_user($user_id, $fields, $e);
 }
 
@@ -2972,6 +2973,12 @@ sub new_flesh_user {
         $fetch_penalties = 1;
     }
 
+    my $fetch_usr_act = 0;
+    if(grep {$_ eq 'usr_activity'} @$fields) {
+        $fields = [grep {$_ ne 'usr_activity'} @$fields];
+        $fetch_usr_act = 1;
+    }
+
 	my $user = $e->retrieve_actor_user(
    	[
       	$id,
@@ -3020,6 +3027,31 @@ sub new_flesh_user {
         );
     }
 
+    # retrieve the most recent usr_activity entry
+    if ($fetch_usr_act) {
+
+        # max number to return for simple patron fleshing
+        my $limit = $U->ou_ancestor_setting_value(
+            $e->requestor->ws_ou, 
+            'circ.patron.usr_activity_retrieve.max');
+
+        my $opts = {
+            flesh => 1,
+            flesh_fields => {auact => ['etype']},
+            order_by => {auact => 'event_time DESC'}, 
+        };
+
+        # 0 == none, <0 == return all
+        $limit = 1 unless defined $limit;
+        $opts->{limit} = $limit if $limit > 0;
+
+        $user->usr_activity( 
+            ($limit == 0) ? 
+                [] : # skip the DB call
+                $e->search_actor_usr_activity([{usr => $user->id}, $opts])
+        );
+    }
+
 	$e->rollback;
 	$user->clear_passwd();
 	return $user;
diff --git a/Open-ILS/src/sql/Pg/950.data.seed-values.sql b/Open-ILS/src/sql/Pg/950.data.seed-values.sql
index 2ca7c7bb64..94e7626f84 100644
--- a/Open-ILS/src/sql/Pg/950.data.seed-values.sql
+++ b/Open-ILS/src/sql/Pg/950.data.seed-values.sql
@@ -11352,3 +11352,23 @@ INSERT INTO config.usr_activity_type (id, ewho, ewhat, ehow, egroup, label) VALU
 -- reserve the first 1000 slots
 SELECT SETVAL('config.usr_activity_type_id_seq'::TEXT, 1000);
 
+INSERT INTO config.org_unit_setting_type 
+    (name, label, description, grp, datatype) 
+    VALUES (
+        'circ.patron.usr_activity_retrieve.max',
+         oils_i18n_gettext(
+            'circ.patron.usr_activity_retrieve.max',
+            'Max user activity entries to retrieve (staff client)',
+            'coust', 
+            'label'
+        ),
+        oils_i18n_gettext(
+            'circ.patron.usr_activity_retrieve.max',
+            'Sets the maxinum number of recent user activity entries to retrieve for display in the staff client.  0 means show none, -1 means show all.  Default is 1.',
+            'coust', 
+            'description'
+        ),
+        'gui',
+        'integer'
+    );
+
diff --git a/Open-ILS/src/sql/Pg/upgrade/XXXX.schema.user-activity.sql b/Open-ILS/src/sql/Pg/upgrade/XXXX.schema.user-activity.sql
index 30b33960a5..de8cc5eb7d 100644
--- a/Open-ILS/src/sql/Pg/upgrade/XXXX.schema.user-activity.sql
+++ b/Open-ILS/src/sql/Pg/upgrade/XXXX.schema.user-activity.sql
@@ -126,6 +126,27 @@ INSERT INTO config.usr_activity_type (id, ewho, ewhat, ehow, egroup, label) VALU
 -- reserve the first 1000 slots
 SELECT SETVAL('config.usr_activity_type_id_seq'::TEXT, 1000);
 
+INSERT INTO config.org_unit_setting_type 
+    (name, label, description, grp, datatype) 
+    VALUES (
+        'circ.patron.usr_activity_retrieve.max',
+         oils_i18n_gettext(
+            'circ.patron.usr_activity_retrieve.max',
+            'Max user activity entries to retrieve (staff client)',
+            'coust', 
+            'label'
+        ),
+        oils_i18n_gettext(
+            'circ.patron.usr_activity_retrieve.max',
+            'Sets the maxinum number of recent user activity entries to retrieve for display in the staff client.  0 means show none, -1 means show all.  Default is 1.',
+            'coust', 
+            'description'
+        ),
+        'gui',
+        'integer'
+    );
+
+
 COMMIT;
 
 /* 
-- 
2.11.0