1 package OpenILS::Application::Actor;
2 use base qw/OpenSRF::Application/;
3 use strict; use warnings;
5 $Data::Dumper::Indent = 0;
8 use Digest::MD5 qw(md5_hex);
10 use OpenSRF::EX qw(:try);
14 use OpenILS::Application::AppUtils;
16 use OpenILS::Utils::Fieldmapper;
17 use OpenILS::Application::Search::Actor;
18 use OpenILS::Utils::ModsParser;
19 use OpenSRF::Utils::Logger qw/$logger/;
20 use OpenSRF::Utils qw/:datetime/;
22 use OpenSRF::Utils::Cache;
25 use DateTime::Format::ISO8601;
27 use OpenILS::Application::Actor::Container;
30 OpenILS::Application::Actor::Container->initialize();
33 my $apputils = "OpenILS::Application::AppUtils";
36 sub _d { warn "Patron:\n" . Dumper(shift()); }
41 my $set_user_settings;
44 __PACKAGE__->register_method(
45 method => "set_user_settings",
46 api_name => "open-ils.actor.patron.settings.update",
48 sub set_user_settings {
49 my( $self, $client, $user_session, $uid, $settings ) = @_;
51 $logger->debug("Setting user settings: $user_session, $uid, " . Dumper($settings));
53 my( $staff, $user, $evt ) =
54 $apputils->checkses_requestor( $user_session, $uid, 'UPDATE_USER' );
59 # [{ usr => $user->id, name => $_}, {value => $$settings{$_}}] } keys %$settings;
62 [{ usr => $user->id, name => $_}, {value => $$settings{$_}}] } keys %$settings;
64 $logger->activity("User " . $staff->id . " updating user $uid settings with: " . Dumper(\@params));
66 return $apputils->simplereq(
68 'open-ils.storage.direct.actor.user_setting.batch.merge', @params );
74 __PACKAGE__->register_method(
75 method => "set_ou_settings",
76 api_name => "open-ils.actor.org_unit.settings.update",
79 my( $self, $client, $user_session, $ouid, $settings ) = @_;
81 my( $staff, $evt ) = $apputils->checkses( $user_session );
83 $evt = $apputils->check_perms( $staff->id, $ouid, 'UPDATE_ORG_UNIT' );
88 map { [{ org_unit => $ouid, name => $_}, {value => $$settings{$_}}] } keys %$settings;
90 $logger->activity("Updating org unit [$ouid] settings with: " . Dumper($params));
92 return $apputils->simplereq(
94 'open-ils.storage.direct.actor.org_unit_setting.merge', @$params );
98 my $fetch_user_settings;
99 my $fetch_ou_settings;
101 __PACKAGE__->register_method(
102 method => "user_settings",
103 api_name => "open-ils.actor.patron.settings.retrieve",
106 my( $self, $client, $user_session, $uid ) = @_;
108 my( $staff, $user, $evt ) =
109 $apputils->checkses_requestor( $user_session, $uid, 'VIEW_USER' );
112 $logger->debug("User " . $staff->id . " fetching user $uid\n");
113 my $s = $apputils->simplereq(
115 'open-ils.storage.direct.actor.user_setting.search.usr.atomic',$uid );
117 return { map { ($_->name,$_->value) } @$s };
122 __PACKAGE__->register_method(
123 method => "ou_settings",
124 api_name => "open-ils.actor.org_unit.settings.retrieve",
127 my( $self, $client, $ouid ) = @_;
129 my $s = $apputils->simplereq(
131 'open-ils.storage.direct.actor.org_unit_setting.search.org_unit.atomic', $ouid);
133 return { map { ($_->name,$_->value) } @$s };
136 __PACKAGE__->register_method (
137 method => "ou_setting_delete",
138 api_name => 'open-ils.actor.org_setting.delete',
140 Deletes a specific org unit setting for a specific location
141 @param authtoken The login session key
142 @param orgid The org unit whose setting we're changing
143 @param setting The name of the setting to delete
144 @return True value on success.
148 sub ou_setting_delete {
149 my( $self, $conn, $authtoken, $orgid, $setting ) = @_;
150 my( $reqr, $evt) = $U->checkses($authtoken);
152 $evt = $U->check_perms($reqr->id, $orgid, 'UPDATE_ORG_SETTING');
155 my $id = $U->storagereq(
156 'open-ils.storage.id_list.actor.org_unit_setting.search_where',
157 { name => $setting, org_unit => $orgid } );
159 $logger->debug("Retrieved setting $id in org unit setting delete");
161 my $s = $U->storagereq(
162 'open-ils.storage.direct.actor.org_unit_setting.delete', $id );
164 $logger->activity("User ".$reqr->id." deleted org unit setting $id") if $s;
170 __PACKAGE__->register_method(
171 method => "update_patron",
172 api_name => "open-ils.actor.patron.update",);
175 my( $self, $client, $user_session, $patron ) = @_;
177 my $session = $apputils->start_db_session();
180 $logger->info("Creating new patron...") if $patron->isnew;
181 $logger->info("Updating Patron: " . $patron->id) unless $patron->isnew;
183 my( $user_obj, $evt ) = $U->checkses($user_session);
186 # XXX does this user have permission to add/create users. Granularity?
187 # $new_patron is the patron in progress. $patron is the original patron
188 # passed in with the method. new_patron will change as the components
189 # of patron are added/updated.
193 # unflesh the real items on the patron
194 $patron->card( $patron->card->id ) if(ref($patron->card));
195 $patron->billing_address( $patron->billing_address->id )
196 if(ref($patron->billing_address));
197 $patron->mailing_address( $patron->mailing_address->id )
198 if(ref($patron->mailing_address));
200 # create/update the patron first so we can use his id
201 if($patron->isnew()) {
202 ( $new_patron, $evt ) = _add_patron($session, _clone_patron($patron), $user_obj);
204 } else { $new_patron = $patron; }
206 ( $new_patron, $evt ) = _add_update_addresses($session, $patron, $new_patron, $user_obj);
209 ( $new_patron, $evt ) = _add_update_cards($session, $patron, $new_patron, $user_obj);
212 ( $new_patron, $evt ) = _add_survey_responses($session, $patron, $new_patron, $user_obj);
215 # re-update the patron if anything has happened to him during this process
216 if($new_patron->ischanged()) {
217 ( $new_patron, $evt ) = _update_patron($session, $new_patron, $user_obj);
221 #$session = OpenSRF::AppSession->create("open-ils.storage"); # why did i put this here?
223 ($new_patron, $evt) = _create_stat_maps($session, $user_session, $patron, $new_patron, $user_obj);
226 ($new_patron, $evt) = _create_perm_maps($session, $user_session, $patron, $new_patron, $user_obj);
229 ($new_patron, $evt) = _create_standing_penalties($session, $user_session, $patron, $new_patron, $user_obj);
232 $apputils->commit_db_session($session);
234 #warn "Patron Update/Create complete\n";
235 return flesh_user($new_patron->id());
241 __PACKAGE__->register_method(
242 method => "user_retrieve_fleshed_by_id",
243 api_name => "open-ils.actor.user.fleshed.retrieve",);
245 sub user_retrieve_fleshed_by_id {
246 my( $self, $client, $user_session, $user_id ) = @_;
248 my( $requestor, $target, $evt ) = $apputils->
249 checkses_requestor( $user_session, $user_id, 'VIEW_USER' );
252 return flesh_user($user_id);
256 # fleshes: card, cards, address, addresses, stat_cat_entries, standing_penalties
264 $session = OpenSRF::AppSession->create("open-ils.storage");
268 # grab the user with the given id
269 my $ureq = $session->request(
270 "open-ils.storage.direct.actor.user.retrieve", $id);
271 my $user = $ureq->gather(1);
273 if(!$user) { return undef; }
276 my $cards_req = $session->request(
277 "open-ils.storage.direct.actor.card.search.usr.atomic",
279 $user->cards( $cards_req->gather(1) );
281 for my $c(@{$user->cards}) {
282 if($c->id == $user->card || $c->id eq $user->card ) {
283 #warn "Setting my card to " . $c->id . "\n";
288 my $add_req = $session->request(
289 "open-ils.storage.direct.actor.user_address.search.usr.atomic",
291 $user->addresses( $add_req->gather(1) );
293 for my $c(@{$user->addresses}) {
294 if($c->id eq $user->billing_address ) { $user->billing_address($c); }
295 if($c->id eq $user->mailing_address ) { $user->mailing_address($c); }
298 my $stat_req = $session->request(
299 "open-ils.storage.direct.actor.stat_cat_entry_user_map.search.target_usr.atomic",
301 $user->stat_cat_entries($stat_req->gather(1));
303 my $standing_penalties_req = $session->request(
304 "open-ils.storage.direct.actor.user_standing_penalty.search.usr.atomic",
306 $user->standing_penalties($standing_penalties_req->gather(1));
308 if($kill) { $session->disconnect(); }
309 $user->clear_passwd();
315 # clone and clear stuff that would break the database
319 my $new_patron = $patron->clone;
321 # Using the Fieldmapper clone method
322 #my $new_patron = Fieldmapper::actor::user->new();
324 #my $fmap = $Fieldmapper::fieldmap;
325 #no strict; # shallow clone, may be useful in the fieldmapper
327 # (keys %{$fmap->{"Fieldmapper::actor::user"}->{'fields'}}) {
328 # $new_patron->$field( $patron->$field() );
333 $new_patron->clear_billing_address();
334 $new_patron->clear_mailing_address();
335 $new_patron->clear_addresses();
336 $new_patron->clear_card();
337 $new_patron->clear_cards();
338 $new_patron->clear_id();
339 $new_patron->clear_isnew();
340 $new_patron->clear_ischanged();
341 $new_patron->clear_isdeleted();
342 $new_patron->clear_stat_cat_entries();
343 $new_patron->clear_permissions();
344 $new_patron->clear_standing_penalties();
354 my $user_obj = shift;
356 my $evt = $U->check_perms($user_obj->id, $patron->home_ou, 'CREATE_USER');
357 return (undef, $evt) if $evt;
359 $logger->info("Creating new user in the DB with username: ".$patron->usrname());
361 my $id = $session->request(
362 "open-ils.storage.direct.actor.user.create", $patron)->gather(1);
363 return (undef, $U->DB_UPDATE_FAILED($patron)) unless $id;
365 $logger->info("Successfully created new user [$id] in DB");
367 return ( $session->request(
368 "open-ils.storage.direct.actor.user.retrieve", $id)->gather(1), undef );
373 my( $session, $patron, $user_obj) = @_;
375 $logger->info("Updating patron ".$patron->id." in DB");
376 my $evt = $U->check_perms($user_obj->id, $patron->home_ou, 'UPDATE_USER');
377 return (undef, $evt) if $evt;
379 $patron->clear_passwd unless $patron->passwd;
381 my $stat = $session->request(
382 "open-ils.storage.direct.actor.user.update",$patron )->gather(1);
383 return (undef, $U->DB_UPDATE_FAILED($patron)) unless defined($stat);
389 sub _add_update_addresses {
393 my $new_patron = shift;
397 my $current_id; # id of the address before creation
399 for my $address (@{$patron->addresses()}) {
401 $address->usr($new_patron->id());
403 if(ref($address) and $address->isnew()) {
405 $current_id = $address->id();
406 ($address, $evt) = _add_address($session,$address);
407 return (undef, $evt) if $evt;
409 if( $patron->billing_address() and
410 $patron->billing_address() == $current_id ) {
411 $new_patron->billing_address($address->id());
412 $new_patron->ischanged(1);
415 if( $patron->mailing_address() and
416 $patron->mailing_address() == $current_id ) {
417 $new_patron->mailing_address($address->id());
418 $new_patron->ischanged(1);
421 } elsif( ref($address) and $address->ischanged() ) {
423 $address->usr($new_patron->id());
424 ($address, $evt) = _update_address($session, $address);
425 return (undef, $evt) if $evt;
427 } elsif( ref($address) and $address->isdeleted() ) {
429 if( $address->id() == $new_patron->mailing_address() ) {
430 $new_patron->clear_mailing_address();
431 ($new_patron, $evt) = _update_patron($session, $new_patron);
432 return (undef, $evt) if $evt;
435 if( $address->id() == $new_patron->billing_address() ) {
436 $new_patron->clear_billing_address();
437 ($new_patron, $evt) = _update_patron($session, $new_patron);
438 return (undef, $evt) if $evt;
441 $evt = _delete_address($session, $address);
442 return (undef, $evt) if $evt;
446 return ( $new_patron, undef );
450 # adds an address to the db and returns the address with new id
452 my($session, $address) = @_;
453 $address->clear_id();
455 $logger->info("Creating new address at street ".$address->street1);
457 # put the address into the database
458 my $id = $session->request(
459 "open-ils.storage.direct.actor.user_address.create", $address )->gather(1);
460 return (undef, $U->DB_UPDATE_FAILED($address)) unless $id;
463 return ($address, undef);
467 sub _update_address {
468 my( $session, $address ) = @_;
470 $logger->info("Updating address ".$address->id." in the DB");
472 my $stat = $session->request(
473 "open-ils.storage.direct.actor.user_address.update", $address )->gather(1);
475 return (undef, $U->DB_UPDATE_FAILED($address)) unless defined($stat);
476 return ($address, undef);
481 sub _add_update_cards {
485 my $new_patron = shift;
489 my $virtual_id; #id of the card before creation
490 for my $card (@{$patron->cards()}) {
492 $card->usr($new_patron->id());
494 if(ref($card) and $card->isnew()) {
496 $virtual_id = $card->id();
497 ( $card, $evt ) = _add_card($session,$card);
498 return (undef, $evt) if $evt;
500 #if(ref($patron->card)) { $patron->card($patron->card->id); }
501 if($patron->card() == $virtual_id) {
502 $new_patron->card($card->id());
503 $new_patron->ischanged(1);
506 } elsif( ref($card) and $card->ischanged() ) {
507 $card->usr($new_patron->id());
508 $evt = _update_card($session, $card);
509 return (undef, $evt) if $evt;
513 return ( $new_patron, undef );
517 # adds an card to the db and returns the card with new id
519 my( $session, $card ) = @_;
522 $logger->info("Adding new patron card ".$card->barcode);
524 my $id = $session->request(
525 "open-ils.storage.direct.actor.card.create", $card )->gather(1);
526 return (undef, $U->DB_UPDATE_FAILED($card)) unless $id;
527 $logger->info("Successfully created patron card $id");
530 return ( $card, undef );
534 # returns event on error. returns undef otherwise
536 my( $session, $card ) = @_;
537 $logger->info("Updating patron card ".$card->id);
539 my $stat = $session->request(
540 "open-ils.storage.direct.actor.card.update", $card )->gather(1);
541 return $U->DB_UPDATE_FAILED($card) unless defined($stat);
548 # returns event on error. returns undef otherwise
549 sub _delete_address {
550 my( $session, $address ) = @_;
552 $logger->info("Deleting address ".$address->id." from DB");
554 my $stat = $session->request(
555 "open-ils.storage.direct.actor.user_address.delete", $address )->gather(1);
557 return $U->DB_UPDATE_FAILED($address) unless defined($stat);
563 sub _add_survey_responses {
564 my ($session, $patron, $new_patron) = @_;
566 $logger->info( "Updating survey responses for patron ".$new_patron->id );
568 my $responses = $patron->survey_responses;
572 $_->usr($new_patron->id) for (@$responses);
574 my $evt = $U->simplereq( "open-ils.circ",
575 "open-ils.circ.survey.submit.user_id", $responses );
577 return (undef, $evt) if defined($U->event_code($evt));
581 return ( $new_patron, undef );
585 sub _create_stat_maps {
587 my($session, $user_session, $patron, $new_patron) = @_;
589 my $maps = $patron->stat_cat_entries();
591 for my $map (@$maps) {
593 my $method = "open-ils.storage.direct.actor.stat_cat_entry_user_map.update";
595 if ($map->isdeleted()) {
596 $method = "open-ils.storage.direct.actor.stat_cat_entry_user_map.delete";
598 } elsif ($map->isnew()) {
599 $method = "open-ils.storage.direct.actor.stat_cat_entry_user_map.create";
604 $map->target_usr($new_patron->id);
607 $logger->info("Updating stat entry with method $method and map $map");
609 my $stat = $session->request($method, $map)->gather(1);
610 return (undef, $U->DB_UPDATE_FAILED($map)) unless defined($stat);
614 return ($new_patron, undef);
617 sub _create_perm_maps {
619 my($session, $user_session, $patron, $new_patron) = @_;
621 my $maps = $patron->permissions;
623 for my $map (@$maps) {
625 my $method = "open-ils.storage.direct.permission.usr_perm_map.update";
626 if ($map->isdeleted()) {
627 $method = "open-ils.storage.direct.permission.usr_perm_map.delete";
628 } elsif ($map->isnew()) {
629 $method = "open-ils.storage.direct.permission.usr_perm_map.create";
634 $map->usr($new_patron->id);
636 #warn( "Updating permissions with method $method and session $user_session and map $map" );
637 $logger->info( "Updating permissions with method $method and map $map" );
639 my $stat = $session->request($method, $map)->gather(1);
640 return (undef, $U->DB_UPDATE_FAILED($map)) unless defined($stat);
644 return ($new_patron, undef);
648 sub _create_standing_penalties {
650 my($session, $user_session, $patron, $new_patron) = @_;
652 my $maps = $patron->standing_penalties;
655 for my $map (@$maps) {
657 if ($map->isdeleted()) {
658 $method = "open-ils.storage.direct.actor.user_standing_penalty.delete";
659 } elsif ($map->isnew()) {
660 $method = "open-ils.storage.direct.actor.user_standing_penalty.create";
666 $map->usr($new_patron->id);
668 $logger->debug( "Updating standing penalty with method $method and session $user_session and map $map" );
670 my $stat = $session->request($method, $map)->gather(1);
671 return (undef, $U->DB_UPDATE_FAILED($map)) unless $stat;
674 return ($new_patron, undef);
679 __PACKAGE__->register_method(
680 method => "search_username",
681 api_name => "open-ils.actor.user.search.username",
684 sub search_username {
685 my($self, $client, $username) = @_;
686 my $users = OpenILS::Application::AppUtils->simple_scalar_request(
688 "open-ils.storage.direct.actor.user.search.usrname.atomic",
696 __PACKAGE__->register_method(
697 method => "user_retrieve_by_barcode",
698 api_name => "open-ils.actor.user.fleshed.retrieve_by_barcode",);
700 sub user_retrieve_by_barcode {
701 my($self, $client, $user_session, $barcode) = @_;
703 $logger->debug("Searching for user with barcode $barcode");
704 my ($user_obj, $evt) = $apputils->checkses($user_session);
708 my $session = OpenSRF::AppSession->create("open-ils.storage");
710 # find the card with the given barcode
711 my $creq = $session->request(
712 "open-ils.storage.direct.actor.card.search.barcode.atomic",
714 my $card = $creq->gather(1);
716 if(!$card || !$card->[0]) {
717 $session->disconnect();
718 return OpenILS::Event->new( 'USER_NOT_FOUND' );
722 my $user = flesh_user($card->usr(), $session);
724 $evt = $U->check_perms($user_obj->id, $user->home_ou, 'VIEW_USER');
727 $session->disconnect();
728 if(!$user) { return OpenILS::Event->new( 'USER_NOT_FOUND' ); }
735 __PACKAGE__->register_method(
736 method => "get_user_by_id",
737 api_name => "open-ils.actor.user.retrieve",);
740 my ($self, $client, $user_session, $id) = @_;
742 my $user_obj = $apputils->check_user_session( $user_session );
744 return $apputils->simple_scalar_request(
746 "open-ils.storage.direct.actor.user.retrieve",
752 __PACKAGE__->register_method(
753 method => "get_org_types",
754 api_name => "open-ils.actor.org_types.retrieve",);
758 my($self, $client) = @_;
760 return $org_types if $org_types;
762 $apputils->simple_scalar_request(
764 "open-ils.storage.direct.actor.org_unit_type.retrieve.all.atomic" );
769 __PACKAGE__->register_method(
770 method => "get_user_profiles",
771 api_name => "open-ils.actor.user.profiles.retrieve",
775 sub get_user_profiles {
776 return $user_profiles if $user_profiles;
778 return $user_profiles =
779 $apputils->simple_scalar_request(
781 "open-ils.storage.direct.actor.profile.retrieve.all.atomic");
786 __PACKAGE__->register_method(
787 method => "get_user_ident_types",
788 api_name => "open-ils.actor.user.ident_types.retrieve",
791 sub get_user_ident_types {
792 return $ident_types if $ident_types;
793 return $ident_types =
794 $apputils->simple_scalar_request(
796 "open-ils.storage.direct.config.identification_type.retrieve.all.atomic" );
802 __PACKAGE__->register_method(
803 method => "get_org_unit",
804 api_name => "open-ils.actor.org_unit.retrieve",
809 my( $self, $client, $user_session, $org_id ) = @_;
811 if(defined($user_session) && !defined($org_id)) {
813 OpenILS::Application::AppUtils->check_user_session( $user_session ); #throws EX on error
814 if(!defined($org_id)) {
815 $org_id = $user_obj->home_ou;
820 my $home_ou = OpenILS::Application::AppUtils->simple_scalar_request(
822 "open-ils.storage.direct.actor.org_unit.retrieve",
828 __PACKAGE__->register_method(
829 method => "search_org_unit",
830 api_name => "open-ils.actor.org_unit_list.search",
833 sub search_org_unit {
835 my( $self, $client, $field, $value ) = @_;
837 my $list = OpenILS::Application::AppUtils->simple_scalar_request(
839 "open-ils.storage.direct.actor.org_unit.search.$field.atomic",
848 __PACKAGE__->register_method(
849 method => "get_org_tree",
850 api_name => "open-ils.actor.org_tree.retrieve",
852 note => "Returns the entire org tree structure",
856 my( $self, $client) = @_;
859 $cache_client = OpenSRF::Utils::Cache->new("global", 0);
861 # see if it's in the cache
862 #warn "Getting ORG Tree\n";
863 my $tree = $cache_client->get_cache('orgtree');
865 #warn "Found orgtree in cache. returning...\n";
869 my $orglist = $apputils->simple_scalar_request(
871 "open-ils.storage.direct.actor.org_unit.retrieve.all.atomic" );
874 #warn "found org list\n";
877 $tree = $self->build_org_tree($orglist);
878 $cache_client->put_cache('orgtree', $tree);
884 # turns an org list into an org tree
887 my( $self, $orglist) = @_;
889 return $orglist unless (
890 ref($orglist) and @$orglist > 1 );
893 $a->ou_type <=> $b->ou_type ||
894 $a->name cmp $b->name } @$orglist;
896 for my $org (@list) {
898 next unless ($org and defined($org->parent_ou));
899 my ($parent) = grep { $_->id == $org->parent_ou } @list;
902 $parent->children([]) unless defined($parent->children);
903 push( @{$parent->children}, $org );
911 __PACKAGE__->register_method(
912 method => "get_org_descendants",
913 api_name => "open-ils.actor.org_tree.descendants.retrieve"
916 # depth is optional. org_unit is the id
917 sub get_org_descendants {
918 my( $self, $client, $org_unit, $depth ) = @_;
919 my $orglist = $apputils->simple_scalar_request(
921 "open-ils.storage.actor.org_unit.descendants.atomic",
923 return $self->build_org_tree($orglist);
927 __PACKAGE__->register_method(
928 method => "get_org_ancestors",
929 api_name => "open-ils.actor.org_tree.ancestors.retrieve"
932 # depth is optional. org_unit is the id
933 sub get_org_ancestors {
934 my( $self, $client, $org_unit, $depth ) = @_;
935 my $orglist = $apputils->simple_scalar_request(
937 "open-ils.storage.actor.org_unit.ancestors.atomic",
939 return $self->build_org_tree($orglist);
943 __PACKAGE__->register_method(
944 method => "get_standings",
945 api_name => "open-ils.actor.standings.retrieve"
950 return $user_standings if $user_standings;
951 return $user_standings =
952 $apputils->simple_scalar_request(
954 "open-ils.storage.direct.config.standing.retrieve.all.atomic" );
959 __PACKAGE__->register_method(
960 method => "get_my_org_path",
961 api_name => "open-ils.actor.org_unit.full_path.retrieve"
964 sub get_my_org_path {
965 my( $self, $client, $user_session, $org_id ) = @_;
966 my $user_obj = $apputils->check_user_session($user_session);
967 if(!defined($org_id)) { $org_id = $user_obj->home_ou; }
969 return $apputils->simple_scalar_request(
971 "open-ils.storage.actor.org_unit.full_path.atomic",
976 __PACKAGE__->register_method(
977 method => "patron_adv_search",
978 api_name => "open-ils.actor.patron.search.advanced" );
980 sub patron_adv_search {
981 my( $self, $client, $staff_login, $search_hash ) = @_;
983 #warn "patron adv with $staff_login and search " .
984 #Dumper($search_hash) . "\n";
986 my $session = OpenSRF::AppSession->create("open-ils.storage");
987 my $req = $session->request(
988 "open-ils.storage.actor.user.crazy_search", $search_hash);
990 my $ans = $req->gather(1);
992 my %hash = map { ($_ =>1) } @$ans;
993 $ans = [ keys %hash ];
995 #warn "Returning @$ans\n";
997 $session->disconnect();
1004 sub _verify_password {
1005 my($user_session, $password) = @_;
1006 my $user_obj = $apputils->check_user_session($user_session);
1008 #grab the user with password
1009 $user_obj = $apputils->simple_scalar_request(
1011 "open-ils.storage.direct.actor.user.retrieve",
1014 if($user_obj->passwd eq $password) {
1022 __PACKAGE__->register_method(
1023 method => "update_password",
1024 api_name => "open-ils.actor.user.password.update");
1026 __PACKAGE__->register_method(
1027 method => "update_password",
1028 api_name => "open-ils.actor.user.username.update");
1030 __PACKAGE__->register_method(
1031 method => "update_password",
1032 api_name => "open-ils.actor.user.email.update");
1034 sub update_password {
1035 my( $self, $client, $user_session, $new_value, $current_password ) = @_;
1039 #warn "Updating user with method " .$self->api_name . "\n";
1040 my $user_obj = $apputils->check_user_session($user_session);
1042 if($self->api_name =~ /password/o) {
1044 #make sure they know the current password
1045 if(!_verify_password($user_session, md5_hex($current_password))) {
1046 return OpenILS::EX->new("USER_WRONG_PASSWORD")->ex;
1049 $user_obj->passwd($new_value);
1051 elsif($self->api_name =~ /username/o) {
1052 my $users = search_username(undef, undef, $new_value);
1053 if( $users and $users->[0] ) {
1054 return OpenILS::Event->new('USERNAME_EXISTS');
1056 $user_obj->usrname($new_value);
1059 elsif($self->api_name =~ /email/o) {
1060 #warn "Updating email to $new_value\n";
1061 $user_obj->email($new_value);
1064 my $session = $apputils->start_db_session();
1066 ( $user_obj, $evt ) = _update_patron($session, $user_obj, $user_obj);
1067 return $evt if $evt;
1069 $apputils->commit_db_session($session);
1071 if($user_obj) { return 1; }
1076 __PACKAGE__->register_method(
1077 method => "check_user_perms",
1078 api_name => "open-ils.actor.user.perm.check",
1079 notes => <<" NOTES");
1080 Takes a login session, user id, an org id, and an array of perm type strings. For each
1081 perm type, if the user does *not* have the given permission it is added
1082 to a list which is returned from the method. If all permissions
1083 are allowed, an empty list is returned
1084 if the logged in user does not match 'user_id', then the logged in user must
1085 have VIEW_PERMISSION priveleges.
1088 sub check_user_perms {
1089 my( $self, $client, $login_session, $user_id, $org_id, $perm_types ) = @_;
1091 my( $staff, $evt ) = $apputils->checkses($login_session);
1092 return $evt if $evt;
1094 if($staff->id ne $user_id) {
1095 if( my $evt = $apputils->check_perms(
1096 $staff->id, $org_id, 'VIEW_PERMISSION') ) {
1102 for my $perm (@$perm_types) {
1103 if($apputils->check_perms($user_id, $org_id, $perm)) {
1104 push @not_allowed, $perm;
1108 return \@not_allowed
1111 __PACKAGE__->register_method(
1112 method => "check_user_perms2",
1113 api_name => "open-ils.actor.user.perm.check.multi_org",
1115 Checks the permissions on a list of perms and orgs for a user
1116 @param authtoken The login session key
1117 @param user_id The id of the user to check
1118 @param orgs The array of org ids
1119 @param perms The array of permission names
1120 @return An array of [ orgId, permissionName ] arrays that FAILED the check
1121 if the logged in user does not match 'user_id', then the logged in user must
1122 have VIEW_PERMISSION priveleges.
1125 sub check_user_perms2 {
1126 my( $self, $client, $authtoken, $user_id, $orgs, $perms ) = @_;
1128 my( $staff, $target, $evt ) = $apputils->checkses_requestor(
1129 $authtoken, $user_id, 'VIEW_PERMISSION' );
1130 return $evt if $evt;
1133 for my $org (@$orgs) {
1134 for my $perm (@$perms) {
1135 if($apputils->check_perms($user_id, $org, $perm)) {
1136 push @not_allowed, [ $org, $perm ];
1141 return \@not_allowed
1145 __PACKAGE__->register_method(
1146 method => 'check_user_perms3',
1147 api_name => 'open-ils.actor.user.perm.highest_org',
1149 Returns the highest org unit id at which a user has a given permission
1150 If the requestor does not match the target user, the requestor must have
1151 'VIEW_PERMISSION' rights at the home org unit of the target user
1152 @param authtoken The login session key
1153 @param userid The id of the user in question
1154 @param perm The permission to check
1155 @return The org unit highest in the org tree within which the user has
1156 the requested permission
1159 sub check_user_perms3 {
1160 my( $self, $client, $authtoken, $userid, $perm ) = @_;
1162 my( $staff, $target, $org, $evt );
1164 ( $staff, $target, $evt ) = $apputils->checkses_requestor(
1165 $authtoken, $userid, 'VIEW_PERMISSION' );
1166 return $evt if $evt;
1168 my $tree = $self->get_org_tree();
1169 return _find_highest_perm_org( $perm, $userid, $target->home_ou, $tree );
1173 sub _find_highest_perm_org {
1174 my ( $perm, $userid, $start_org, $org_tree ) = @_;
1175 my $org = $apputils->find_org($org_tree, $start_org );
1179 last if ($apputils->check_perms( $userid, $org->id, $perm )); # perm failed
1181 $org = $apputils->find_org( $org_tree, $org->parent_ou() );
1187 __PACKAGE__->register_method(
1188 method => 'check_user_perms4',
1189 api_name => 'open-ils.actor.user.perm.highest_org.batch',
1191 Returns the highest org unit id at which a user has a given permission
1192 If the requestor does not match the target user, the requestor must have
1193 'VIEW_PERMISSION' rights at the home org unit of the target user
1194 @param authtoken The login session key
1195 @param userid The id of the user in question
1196 @param perms An array of perm names to check
1197 @return An array of orgId's representing the org unit
1198 highest in the org tree within which the user has the requested permission
1199 The arrah of orgId's has matches the order of the perms array
1202 sub check_user_perms4 {
1203 my( $self, $client, $authtoken, $userid, $perms ) = @_;
1205 my( $staff, $target, $org, $evt );
1207 ( $staff, $target, $evt ) = $apputils->checkses_requestor(
1208 $authtoken, $userid, 'VIEW_PERMISSION' );
1209 return $evt if $evt;
1212 return [] unless ref($perms);
1213 my $tree = $self->get_org_tree();
1215 for my $p (@$perms) {
1216 push( @arr, _find_highest_perm_org( $p, $userid, $target->home_ou, $tree ) );
1224 __PACKAGE__->register_method(
1225 method => "user_fines_summary",
1226 api_name => "open-ils.actor.user.fines.summary",
1227 notes => <<" NOTES");
1228 Returns a short summary of the users total open fines, excluding voided fines
1229 Params are login_session, user_id
1230 Returns a 'mous' object.
1233 sub user_fines_summary {
1234 my( $self, $client, $login_session, $user_id ) = @_;
1236 my $user_obj = $apputils->check_user_session($login_session);
1237 if($user_obj->id ne $user_id) {
1238 if($apputils->check_user_perms($user_obj->id, $user_obj->home_ou, "VIEW_USER_FINES_SUMMARY")) {
1239 return OpenILS::Perm->new("VIEW_USER_FINES_SUMMARY");
1243 return $apputils->simple_scalar_request(
1245 "open-ils.storage.direct.money.open_user_summary.search.usr",
1253 __PACKAGE__->register_method(
1254 method => "user_transactions",
1255 api_name => "open-ils.actor.user.transactions",
1256 notes => <<" NOTES");
1257 Returns a list of open user transactions (mbts objects);
1258 Params are login_session, user_id
1259 Optional third parameter is the transactions type. defaults to all
1262 __PACKAGE__->register_method(
1263 method => "user_transactions",
1264 api_name => "open-ils.actor.user.transactions.have_charge",
1265 notes => <<" NOTES");
1266 Returns a list of all open user transactions (mbts objects) that have an initial charge
1267 Params are login_session, user_id
1268 Optional third parameter is the transactions type. defaults to all
1271 __PACKAGE__->register_method(
1272 method => "user_transactions",
1273 api_name => "open-ils.actor.user.transactions.have_balance",
1274 notes => <<" NOTES");
1275 Returns a list of all open user transactions (mbts objects) that have a balance
1276 Params are login_session, user_id
1277 Optional third parameter is the transactions type. defaults to all
1280 __PACKAGE__->register_method(
1281 method => "user_transactions",
1282 api_name => "open-ils.actor.user.transactions.fleshed",
1283 notes => <<" NOTES");
1284 Returns an object/hash of transaction, circ, title where transaction = an open
1285 user transactions (mbts objects), circ is the attached circluation, and title
1286 is the title the circ points to
1287 Params are login_session, user_id
1288 Optional third parameter is the transactions type. defaults to all
1291 __PACKAGE__->register_method(
1292 method => "user_transactions",
1293 api_name => "open-ils.actor.user.transactions.have_charge.fleshed",
1294 notes => <<" NOTES");
1295 Returns an object/hash of transaction, circ, title where transaction = an open
1296 user transactions that has an initial charge (mbts objects), circ is the
1297 attached circluation, and title is the title the circ points to
1298 Params are login_session, user_id
1299 Optional third parameter is the transactions type. defaults to all
1302 __PACKAGE__->register_method(
1303 method => "user_transactions",
1304 api_name => "open-ils.actor.user.transactions.have_balance.fleshed",
1305 notes => <<" NOTES");
1306 Returns an object/hash of transaction, circ, title where transaction = an open
1307 user transaction that has a balance (mbts objects), circ is the attached
1308 circluation, and title is the title the circ points to
1309 Params are login_session, user_id
1310 Optional third parameter is the transaction type. defaults to all
1313 __PACKAGE__->register_method(
1314 method => "user_transactions",
1315 api_name => "open-ils.actor.user.transactions.count",
1316 notes => <<" NOTES");
1317 Returns an object/hash of transaction, circ, title where transaction = an open
1318 user transactions (mbts objects), circ is the attached circluation, and title
1319 is the title the circ points to
1320 Params are login_session, user_id
1321 Optional third parameter is the transactions type. defaults to all
1324 __PACKAGE__->register_method(
1325 method => "user_transactions",
1326 api_name => "open-ils.actor.user.transactions.have_charge.count",
1327 notes => <<" NOTES");
1328 Returns an object/hash of transaction, circ, title where transaction = an open
1329 user transactions that has an initial charge (mbts objects), circ is the
1330 attached circluation, and title is the title the circ points to
1331 Params are login_session, user_id
1332 Optional third parameter is the transactions type. defaults to all
1335 __PACKAGE__->register_method(
1336 method => "user_transactions",
1337 api_name => "open-ils.actor.user.transactions.have_balance.count",
1338 notes => <<" NOTES");
1339 Returns an object/hash of transaction, circ, title where transaction = an open
1340 user transaction that has a balance (mbts objects), circ is the attached
1341 circluation, and title is the title the circ points to
1342 Params are login_session, user_id
1343 Optional third parameter is the transaction type. defaults to all
1346 __PACKAGE__->register_method(
1347 method => "user_transactions",
1348 api_name => "open-ils.actor.user.transactions.have_balance.total",
1349 notes => <<" NOTES");
1350 Returns an object/hash of transaction, circ, title where transaction = an open
1351 user transaction that has a balance (mbts objects), circ is the attached
1352 circluation, and title is the title the circ points to
1353 Params are login_session, user_id
1354 Optional third parameter is the transaction type. defaults to all
1359 sub user_transactions {
1360 my( $self, $client, $login_session, $user_id, $type ) = @_;
1362 my( $user_obj, $target, $evt ) = $apputils->checkses_requestor(
1363 $login_session, $user_id, 'VIEW_USER_TRANSACTIONS' );
1364 return $evt if $evt;
1366 my $api = $self->api_name();
1370 if(defined($type)) { @xact = (xact_type => $type);
1372 } else { @xact = (); }
1374 if($api =~ /have_charge/o) {
1376 $trans = $apputils->simple_scalar_request(
1378 "open-ils.storage.direct.money.open_billable_transaction_summary.search_where.atomic",
1379 { usr => $user_id, total_owed => { ">" => 0 }, @xact });
1381 } elsif($api =~ /have_balance/o) {
1383 $trans = $apputils->simple_scalar_request(
1385 "open-ils.storage.direct.money.open_billable_transaction_summary.search_where.atomic",
1386 { usr => $user_id, balance_owed => { ">" => 0 }, @xact });
1390 $trans = $apputils->simple_scalar_request(
1392 "open-ils.storage.direct.money.open_billable_transaction_summary.search_where.atomic",
1393 { usr => $user_id, @xact });
1396 if($api =~ /total/o) {
1398 for my $t (@$trans) {
1399 $total += $t->balance_owed;
1402 $logger->debug("Total balance owed by user $user_id: $total");
1406 if($api =~ /count/o) { return scalar @$trans; }
1407 if($api !~ /fleshed/o) { return $trans; }
1409 #warn "API: $api\n";
1412 for my $t (@$trans) {
1414 #warn $t->id . "\n";
1417 if( $t->xact_type ne 'circulation' ) {
1418 push @resp, {transaction => $t};
1422 my $circ = $apputils->simple_scalar_request(
1424 "open-ils.storage.direct.action.circulation.retrieve",
1429 my $title = $apputils->simple_scalar_request(
1431 "open-ils.storage.fleshed.biblio.record_entry.retrieve_by_copy",
1432 $circ->target_copy );
1436 my $u = OpenILS::Utils::ModsParser->new();
1437 $u->start_mods_batch($title->marc());
1438 my $mods = $u->finish_mods_batch();
1440 push @resp, {transaction => $t, circ => $circ, record => $mods };
1448 __PACKAGE__->register_method(
1449 method => "user_transaction_retrieve",
1450 api_name => "open-ils.actor.user.transaction.fleshed.retrieve",
1452 notes => <<" NOTES");
1453 Returns a fleshedtransaction record
1455 __PACKAGE__->register_method(
1456 method => "user_transaction_retrieve",
1457 api_name => "open-ils.actor.user.transaction.retrieve",
1459 notes => <<" NOTES");
1460 Returns a transaction record
1462 sub user_transaction_retrieve {
1463 my( $self, $client, $login_session, $bill_id ) = @_;
1465 my $trans = $apputils->simple_scalar_request(
1467 "open-ils.storage.direct.money.billable_transaction_summary.retrieve",
1471 my( $user_obj, $target, $evt ) = $apputils->checkses_requestor(
1472 $login_session, $trans->usr, 'VIEW_USER_TRANSACTIONS' );
1473 return $evt if $evt;
1475 my $api = $self->api_name();
1476 if($api !~ /fleshed/o) { return $trans; }
1478 if( $trans->xact_type ne 'circulation' ) {
1479 $logger->debug("Returning non-circ transaction");
1480 return {transaction => $trans};
1483 my $circ = $apputils->simple_scalar_request(
1485 "open-ils.storage.direct.action.circulation.retrieve",
1488 return {transaction => $trans} unless $circ;
1489 $logger->debug("Found the circ transaction");
1491 my $title = $apputils->simple_scalar_request(
1493 "open-ils.storage.fleshed.biblio.record_entry.retrieve_by_copy",
1494 $circ->target_copy );
1496 return {transaction => $trans, circ => $circ } unless $title;
1497 $logger->debug("Found the circ title");
1501 my $u = OpenILS::Utils::ModsParser->new();
1502 $u->start_mods_batch($title->marc());
1503 $mods = $u->finish_mods_batch();
1505 if ($title->id == -1) {
1506 my $copy = $apputils->simple_scalar_request(
1508 "open-ils.storage.direct.asset.copy.retrieve",
1509 $circ->target_copy );
1511 $mods = new Fieldmapper::metabib::virtual_record;
1513 $mods->title($copy->dummy_title);
1514 $mods->author($copy->dummy_author);
1518 $logger->debug("MODSized the circ title");
1520 return {transaction => $trans, circ => $circ, record => $mods };
1524 __PACKAGE__->register_method(
1525 method => "hold_request_count",
1526 api_name => "open-ils.actor.user.hold_requests.count",
1528 notes => <<" NOTES");
1529 Returns hold ready/total counts
1531 sub hold_request_count {
1532 my( $self, $client, $login_session, $userid ) = @_;
1534 my( $user_obj, $target, $evt ) = $apputils->checkses_requestor(
1535 $login_session, $userid, 'VIEW_HOLD' );
1536 return $evt if $evt;
1539 my $holds = $apputils->simple_scalar_request(
1541 "open-ils.storage.direct.action.hold_request.search_where.atomic",
1543 fulfillment_time => {"=" => undef } }
1547 for my $h (@$holds) {
1548 next unless $h->capture_time;
1550 my $copy = $apputils->simple_scalar_request(
1552 "open-ils.storage.direct.asset.copy.retrieve",
1556 if ($copy->status == 8) {
1561 return { total => scalar(@$holds), ready => scalar(@ready) };
1565 __PACKAGE__->register_method(
1566 method => "checkedout_count",
1567 api_name => "open-ils.actor.user.checked_out.count",
1569 notes => <<" NOTES");
1570 Returns a transaction record
1572 sub checkedout_count {
1573 my( $self, $client, $login_session, $userid ) = @_;
1575 my( $user_obj, $target, $evt ) = $apputils->checkses_requestor(
1576 $login_session, $userid, 'VIEW_CIRCULATIONS' );
1577 return $evt if $evt;
1580 my $circs = $apputils->simple_scalar_request(
1582 "open-ils.storage.direct.action.circulation.search_where.atomic",
1584 checkin_time => {"=" => undef } }
1587 my $parser = DateTime::Format::ISO8601->new;
1590 for my $c (@$circs) {
1591 my $due_dt = $parser->parse_datetime( clense_ISO8601( $c->due_date ) );
1592 my $due = $due_dt->epoch;
1594 if ($due < DateTime->today->epoch) {
1599 return { total => scalar(@$circs), overdue => scalar(@overdue) };
1602 __PACKAGE__->register_method(
1603 method => "user_transaction_history",
1604 api_name => "open-ils.actor.user.transactions.history",
1606 notes => <<" NOTES");
1607 Returns a list of billable transaction ids for a user, optionally by type
1609 sub user_transaction_history {
1610 my( $self, $client, $login_session, $user_id, $type ) = @_;
1612 my( $user_obj, $target, $evt ) = $apputils->checkses_requestor(
1613 $login_session, $user_id, 'VIEW_USER_TRANSACTIONS' );
1614 return $evt if $evt;
1616 my $api = $self->api_name();
1619 @xact = (xact_type => $type) if(defined($type));
1621 my $trans = $apputils->simple_scalar_request(
1623 "open-ils.storage.direct.money.billable_transaction_summary.search_where.atomic",
1624 { usr => $user_id, @xact }, { order_by => 'xact_start DESC' });
1626 return [ map { $_->id } @$trans ];
1630 __PACKAGE__->register_method(
1631 method => "user_perms",
1632 api_name => "open-ils.actor.permissions.user_perms.retrieve",
1634 notes => <<" NOTES");
1635 Returns a list of permissions
1638 my( $self, $client, $authtoken, $user ) = @_;
1640 my( $staff, $evt ) = $apputils->checkses($authtoken);
1641 return $evt if $evt;
1643 $user ||= $staff->id;
1645 if( $user != $staff->id and $evt = $apputils->check_perms( $staff->id, $staff->home_ou, 'VIEW_PERMISSION') ) {
1649 return $apputils->simple_scalar_request(
1651 "open-ils.storage.permission.user_perms.atomic",
1655 __PACKAGE__->register_method(
1656 method => "retrieve_perms",
1657 api_name => "open-ils.actor.permissions.retrieve",
1658 notes => <<" NOTES");
1659 Returns a list of permissions
1661 sub retrieve_perms {
1662 my( $self, $client ) = @_;
1663 return $apputils->simple_scalar_request(
1665 "open-ils.storage.direct.permission.perm_list.retrieve.all.atomic");
1668 __PACKAGE__->register_method(
1669 method => "retrieve_groups",
1670 api_name => "open-ils.actor.groups.retrieve",
1671 notes => <<" NOTES");
1672 Returns a list of user groupss
1674 sub retrieve_groups {
1675 my( $self, $client ) = @_;
1676 return $apputils->simple_scalar_request(
1678 "open-ils.storage.direct.permission.grp_tree.retrieve.all.atomic");
1681 __PACKAGE__->register_method(
1682 method => "retrieve_groups_tree",
1683 api_name => "open-ils.actor.groups.tree.retrieve",
1684 notes => <<" NOTES");
1685 Returns a list of user groups
1687 sub retrieve_groups_tree {
1688 my( $self, $client ) = @_;
1689 my $groups = $apputils->simple_scalar_request(
1691 "open-ils.storage.direct.permission.grp_tree.retrieve.all.atomic");
1692 return $self->build_group_tree($groups);
1696 # turns an org list into an org tree
1697 sub build_group_tree {
1699 my( $self, $grplist) = @_;
1701 return $grplist unless (
1702 ref($grplist) and @$grplist > 1 );
1704 my @list = sort { $a->name cmp $b->name } @$grplist;
1707 for my $grp (@list) {
1709 if ($grp and !defined($grp->parent)) {
1713 my ($parent) = grep { $_->id == $grp->parent} @list;
1715 $parent->children([]) unless defined($parent->children);
1716 push( @{$parent->children}, $grp );
1724 __PACKAGE__->register_method(
1725 method => "add_user_to_groups",
1726 api_name => "open-ils.actor.user.set_groups",
1727 notes => <<" NOTES");
1728 Adds a user to one or more permission groups
1731 sub add_user_to_groups {
1732 my( $self, $client, $authtoken, $userid, $groups ) = @_;
1734 my( $requestor, $target, $evt ) = $apputils->checkses_requestor(
1735 $authtoken, $userid, 'CREATE_USER_GROUP_LINK' );
1736 return $evt if $evt;
1738 ( $requestor, $target, $evt ) = $apputils->checkses_requestor(
1739 $authtoken, $userid, 'REMOVE_USER_GROUP_LINK' );
1740 return $evt if $evt;
1742 $apputils->simplereq(
1744 'open-ils.storage.direct.permission.usr_grp_map.mass_delete', { usr => $userid } );
1746 for my $group (@$groups) {
1747 my $link = Fieldmapper::permission::usr_grp_map->new;
1749 $link->usr($userid);
1751 my $id = $apputils->simplereq(
1753 'open-ils.storage.direct.permission.usr_grp_map.create', $link );
1759 __PACKAGE__->register_method(
1760 method => "get_user_perm_groups",
1761 api_name => "open-ils.actor.user.get_groups",
1762 notes => <<" NOTES");
1763 Retrieve a user's permission groups.
1767 sub get_user_perm_groups {
1768 my( $self, $client, $authtoken, $userid ) = @_;
1770 my( $requestor, $target, $evt ) = $apputils->checkses_requestor(
1771 $authtoken, $userid, 'VIEW_PERM_GROUPS' );
1772 return $evt if $evt;
1774 return $apputils->simplereq(
1776 'open-ils.storage.direct.permission.usr_grp_map.search.usr.atomic', $userid );
1781 __PACKAGE__->register_method (
1782 method => 'register_workstation',
1783 api_name => 'open-ils.actor.workstation.register',
1785 Registers a new workstion in the system
1786 @param authtoken The login session key
1787 @param name The name of the workstation id
1788 @param owner The org unit that owns this workstation
1789 @return The workstation id on success, WORKSTATION_NAME_EXISTS
1790 if the name is already in use.
1793 sub register_workstation {
1794 my( $self, $connection, $authtoken, $name, $owner ) = @_;
1795 my( $requestor, $evt ) = $U->checkses($authtoken);
1796 return $evt if $evt;
1797 $evt = $U->check_perms($requestor->id, $owner, 'REGISTER_WORKSTATION');
1798 return $evt if $evt;
1800 my $ws = $U->storagereq(
1801 'open-ils.storage.direct.actor.workstation.search.name', $name );
1802 return OpenILS::Event->new('WORKSTATION_NAME_EXISTS') if $ws;
1804 $ws = Fieldmapper::actor::workstation->new;
1805 $ws->owning_lib($owner);
1808 my $id = $U->storagereq(
1809 'open-ils.storage.direct.actor.workstation.create', $ws );
1810 return $U->DB_UPDATE_FAILED($ws) unless $id;
1817 __PACKAGE__->register_method (
1818 method => 'fetch_patron_note',
1819 api_name => 'open-ils.actor.note.retrieve.all',
1821 Returns a list of notes for a given user
1822 Requestor must have VIEW_USER permission if pub==false and
1823 @param authtoken The login session key
1824 @param args Hash of params including
1825 patronid : the patron's id
1826 pub : true if retrieving only public notes
1830 sub fetch_patron_note {
1831 my( $self, $conn, $authtoken, $args ) = @_;
1832 my $patronid = $$args{patronid};
1834 my($reqr, $evt) = $U->checkses($authtoken);
1837 ($patron, $evt) = $U->fetch_user($patronid);
1838 return $evt if $evt;
1841 if( $patronid ne $reqr->id ) {
1842 $evt = $U->check_perms($reqr->id, $patron->home_ou, 'VIEW_USER');
1843 return $evt if $evt;
1845 return $U->storagereq(
1846 'open-ils.storage.direct.actor.usr_note.search_where.atomic',
1847 { usr => $patronid, pub => 't' } );
1850 $evt = $U->check_perms($reqr->id, $patron->home_ou, 'VIEW_USER');
1851 return $evt if $evt;
1853 return $U->storagereq(
1854 'open-ils.storage.direct.actor.usr_note.search.usr.atomic', $patronid );
1857 __PACKAGE__->register_method (
1858 method => 'create_user_note',
1859 api_name => 'open-ils.actor.note.create',
1861 Creates a new note for the given user
1862 @param authtoken The login session key
1863 @param note The note object
1866 sub create_user_note {
1867 my( $self, $conn, $authtoken, $note ) = @_;
1868 my( $reqr, $patron, $evt ) =
1869 $U->checkses_requestor($authtoken, $note->usr, 'UPDATE_USER');
1870 return $evt if $evt;
1871 $logger->activity("user ".$reqr->id." creating note for user ".$note->usr);
1873 $note->creator($reqr->id);
1874 my $id = $U->storagereq(
1875 'open-ils.storage.direct.actor.usr_note.create', $note );
1876 return $U->DB_UPDATE_FAILED($note) unless $id;
1881 __PACKAGE__->register_method (
1882 method => 'delete_user_note',
1883 api_name => 'open-ils.actor.note.delete',
1885 Deletes a note for the given user
1886 @param authtoken The login session key
1887 @param noteid The note id
1890 sub delete_user_note {
1891 my( $self, $conn, $authtoken, $noteid ) = @_;
1893 my $note = $U->storagereq(
1894 'open-ils.storage.direct.actor.usr_note.retrieve', $noteid);
1895 return OpenILS::Event->new('USER_NOTE_NOT_FOUND') unless $note;
1897 my( $reqr, $patron, $evt ) =
1898 $U->checkses_requestor($authtoken, $note->usr, 'UPDATE_USER');
1899 return $evt if $evt;
1900 $logger->activity("user ".$reqr->id." deleting note [$noteid] for user ".$note->usr);
1902 my $stat = $U->storagereq(
1903 'open-ils.storage.direct.actor.usr_note.delete', $noteid );
1904 return $U->DB_UPDATE_FAILED($note) unless defined $stat;