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 $logger->info("Fetching org unit settings for org $ouid");
131 my $s = $apputils->simplereq(
133 'open-ils.storage.direct.actor.org_unit_setting.search.org_unit.atomic', $ouid);
135 return { map { ($_->name,$_->value) } @$s };
138 __PACKAGE__->register_method (
139 method => "ou_setting_delete",
140 api_name => 'open-ils.actor.org_setting.delete',
142 Deletes a specific org unit setting for a specific location
143 @param authtoken The login session key
144 @param orgid The org unit whose setting we're changing
145 @param setting The name of the setting to delete
146 @return True value on success.
150 sub ou_setting_delete {
151 my( $self, $conn, $authtoken, $orgid, $setting ) = @_;
152 my( $reqr, $evt) = $U->checkses($authtoken);
154 $evt = $U->check_perms($reqr->id, $orgid, 'UPDATE_ORG_SETTING');
157 my $id = $U->storagereq(
158 'open-ils.storage.id_list.actor.org_unit_setting.search_where',
159 { name => $setting, org_unit => $orgid } );
161 $logger->debug("Retrieved setting $id in org unit setting delete");
163 my $s = $U->storagereq(
164 'open-ils.storage.direct.actor.org_unit_setting.delete', $id );
166 $logger->activity("User ".$reqr->id." deleted org unit setting $id") if $s;
172 __PACKAGE__->register_method(
173 method => "update_patron",
174 api_name => "open-ils.actor.patron.update",);
177 my( $self, $client, $user_session, $patron ) = @_;
179 my $session = $apputils->start_db_session();
182 $logger->info("Creating new patron...") if $patron->isnew;
183 $logger->info("Updating Patron: " . $patron->id) unless $patron->isnew;
185 my( $user_obj, $evt ) = $U->checkses($user_session);
188 # XXX does this user have permission to add/create users. Granularity?
189 # $new_patron is the patron in progress. $patron is the original patron
190 # passed in with the method. new_patron will change as the components
191 # of patron are added/updated.
195 # unflesh the real items on the patron
196 $patron->card( $patron->card->id ) if(ref($patron->card));
197 $patron->billing_address( $patron->billing_address->id )
198 if(ref($patron->billing_address));
199 $patron->mailing_address( $patron->mailing_address->id )
200 if(ref($patron->mailing_address));
202 # create/update the patron first so we can use his id
203 if($patron->isnew()) {
204 ( $new_patron, $evt ) = _add_patron($session, _clone_patron($patron), $user_obj);
206 } else { $new_patron = $patron; }
208 ( $new_patron, $evt ) = _add_update_addresses($session, $patron, $new_patron, $user_obj);
211 ( $new_patron, $evt ) = _add_update_cards($session, $patron, $new_patron, $user_obj);
214 ( $new_patron, $evt ) = _add_survey_responses($session, $patron, $new_patron, $user_obj);
217 # re-update the patron if anything has happened to him during this process
218 if($new_patron->ischanged()) {
219 ( $new_patron, $evt ) = _update_patron($session, $new_patron, $user_obj);
223 #$session = OpenSRF::AppSession->create("open-ils.storage"); # why did i put this here?
225 ($new_patron, $evt) = _create_stat_maps($session, $user_session, $patron, $new_patron, $user_obj);
228 ($new_patron, $evt) = _create_perm_maps($session, $user_session, $patron, $new_patron, $user_obj);
231 ($new_patron, $evt) = _create_standing_penalties($session, $user_session, $patron, $new_patron, $user_obj);
234 $logger->activity("user ".$user_obj->id." updating/creating user ".$new_patron->id);
235 $apputils->commit_db_session($session);
237 #warn "Patron Update/Create complete\n";
238 return flesh_user($new_patron->id());
244 __PACKAGE__->register_method(
245 method => "user_retrieve_fleshed_by_id",
246 api_name => "open-ils.actor.user.fleshed.retrieve",);
248 sub user_retrieve_fleshed_by_id {
249 my( $self, $client, $user_session, $user_id ) = @_;
251 my( $requestor, $target, $evt ) = $apputils->
252 checkses_requestor( $user_session, $user_id, 'VIEW_USER' );
255 return flesh_user($user_id);
259 # fleshes: card, cards, address, addresses, stat_cat_entries, standing_penalties
267 $session = OpenSRF::AppSession->create("open-ils.storage");
271 # grab the user with the given id
272 my $ureq = $session->request(
273 "open-ils.storage.direct.actor.user.retrieve", $id);
274 my $user = $ureq->gather(1);
276 if(!$user) { return undef; }
279 my $cards_req = $session->request(
280 "open-ils.storage.direct.actor.card.search.usr.atomic",
282 $user->cards( $cards_req->gather(1) );
284 for my $c(@{$user->cards}) {
285 if($c->id == $user->card || $c->id eq $user->card ) {
286 #warn "Setting my card to " . $c->id . "\n";
291 my $add_req = $session->request(
292 "open-ils.storage.direct.actor.user_address.search.usr.atomic",
294 $user->addresses( $add_req->gather(1) );
296 for my $c(@{$user->addresses}) {
297 if($c->id eq $user->billing_address ) { $user->billing_address($c); }
298 if($c->id eq $user->mailing_address ) { $user->mailing_address($c); }
301 my $stat_req = $session->request(
302 "open-ils.storage.direct.actor.stat_cat_entry_user_map.search.target_usr.atomic",
304 $user->stat_cat_entries($stat_req->gather(1));
306 my $standing_penalties_req = $session->request(
307 "open-ils.storage.direct.actor.user_standing_penalty.search.usr.atomic",
309 $user->standing_penalties($standing_penalties_req->gather(1));
311 if($kill) { $session->disconnect(); }
312 $user->clear_passwd();
318 # clone and clear stuff that would break the database
322 my $new_patron = $patron->clone;
324 # Using the Fieldmapper clone method
325 #my $new_patron = Fieldmapper::actor::user->new();
327 #my $fmap = $Fieldmapper::fieldmap;
328 #no strict; # shallow clone, may be useful in the fieldmapper
330 # (keys %{$fmap->{"Fieldmapper::actor::user"}->{'fields'}}) {
331 # $new_patron->$field( $patron->$field() );
336 $new_patron->clear_billing_address();
337 $new_patron->clear_mailing_address();
338 $new_patron->clear_addresses();
339 $new_patron->clear_card();
340 $new_patron->clear_cards();
341 $new_patron->clear_id();
342 $new_patron->clear_isnew();
343 $new_patron->clear_ischanged();
344 $new_patron->clear_isdeleted();
345 $new_patron->clear_stat_cat_entries();
346 $new_patron->clear_permissions();
347 $new_patron->clear_standing_penalties();
357 my $user_obj = shift;
359 my $evt = $U->check_perms($user_obj->id, $patron->home_ou, 'CREATE_USER');
360 return (undef, $evt) if $evt;
362 $logger->info("Creating new user in the DB with username: ".$patron->usrname());
364 my $id = $session->request(
365 "open-ils.storage.direct.actor.user.create", $patron)->gather(1);
366 return (undef, $U->DB_UPDATE_FAILED($patron)) unless $id;
368 $logger->info("Successfully created new user [$id] in DB");
370 return ( $session->request(
371 "open-ils.storage.direct.actor.user.retrieve", $id)->gather(1), undef );
376 my( $session, $patron, $user_obj) = @_;
378 $logger->info("Updating patron ".$patron->id." in DB");
379 my $evt = $U->check_perms($user_obj->id, $patron->home_ou, 'UPDATE_USER');
380 return (undef, $evt) if $evt;
382 $patron->clear_passwd unless $patron->passwd;
384 if(!$patron->ident_type) {
385 $patron->clear_ident_type;
386 $patron->clear_ident_value;
389 if(!$patron->ident_type2) {
390 $patron->clear_ident_type2;
391 $patron->clear_ident_value2;
394 my $stat = $session->request(
395 "open-ils.storage.direct.actor.user.update",$patron )->gather(1);
396 return (undef, $U->DB_UPDATE_FAILED($patron)) unless defined($stat);
402 sub _add_update_addresses {
406 my $new_patron = shift;
410 my $current_id; # id of the address before creation
412 for my $address (@{$patron->addresses()}) {
414 $address->usr($new_patron->id());
416 if(ref($address) and $address->isnew()) {
418 $current_id = $address->id();
419 ($address, $evt) = _add_address($session,$address);
420 return (undef, $evt) if $evt;
422 if( $patron->billing_address() and
423 $patron->billing_address() == $current_id ) {
424 $new_patron->billing_address($address->id());
425 $new_patron->ischanged(1);
428 if( $patron->mailing_address() and
429 $patron->mailing_address() == $current_id ) {
430 $new_patron->mailing_address($address->id());
431 $new_patron->ischanged(1);
434 } elsif( ref($address) and $address->ischanged() ) {
436 $address->usr($new_patron->id());
437 ($address, $evt) = _update_address($session, $address);
438 return (undef, $evt) if $evt;
440 } elsif( ref($address) and $address->isdeleted() ) {
442 if( $address->id() == $new_patron->mailing_address() ) {
443 $new_patron->clear_mailing_address();
444 ($new_patron, $evt) = _update_patron($session, $new_patron);
445 return (undef, $evt) if $evt;
448 if( $address->id() == $new_patron->billing_address() ) {
449 $new_patron->clear_billing_address();
450 ($new_patron, $evt) = _update_patron($session, $new_patron);
451 return (undef, $evt) if $evt;
454 $evt = _delete_address($session, $address);
455 return (undef, $evt) if $evt;
459 return ( $new_patron, undef );
463 # adds an address to the db and returns the address with new id
465 my($session, $address) = @_;
466 $address->clear_id();
468 $logger->info("Creating new address at street ".$address->street1);
470 # put the address into the database
471 my $id = $session->request(
472 "open-ils.storage.direct.actor.user_address.create", $address )->gather(1);
473 return (undef, $U->DB_UPDATE_FAILED($address)) unless $id;
476 return ($address, undef);
480 sub _update_address {
481 my( $session, $address ) = @_;
483 $logger->info("Updating address ".$address->id." in the DB");
485 my $stat = $session->request(
486 "open-ils.storage.direct.actor.user_address.update", $address )->gather(1);
488 return (undef, $U->DB_UPDATE_FAILED($address)) unless defined($stat);
489 return ($address, undef);
494 sub _add_update_cards {
498 my $new_patron = shift;
502 my $virtual_id; #id of the card before creation
503 for my $card (@{$patron->cards()}) {
505 $card->usr($new_patron->id());
507 if(ref($card) and $card->isnew()) {
509 $virtual_id = $card->id();
510 ( $card, $evt ) = _add_card($session,$card);
511 return (undef, $evt) if $evt;
513 #if(ref($patron->card)) { $patron->card($patron->card->id); }
514 if($patron->card() == $virtual_id) {
515 $new_patron->card($card->id());
516 $new_patron->ischanged(1);
519 } elsif( ref($card) and $card->ischanged() ) {
520 $card->usr($new_patron->id());
521 $evt = _update_card($session, $card);
522 return (undef, $evt) if $evt;
526 return ( $new_patron, undef );
530 # adds an card to the db and returns the card with new id
532 my( $session, $card ) = @_;
535 $logger->info("Adding new patron card ".$card->barcode);
537 my $id = $session->request(
538 "open-ils.storage.direct.actor.card.create", $card )->gather(1);
539 return (undef, $U->DB_UPDATE_FAILED($card)) unless $id;
540 $logger->info("Successfully created patron card $id");
543 return ( $card, undef );
547 # returns event on error. returns undef otherwise
549 my( $session, $card ) = @_;
550 $logger->info("Updating patron card ".$card->id);
552 my $stat = $session->request(
553 "open-ils.storage.direct.actor.card.update", $card )->gather(1);
554 return $U->DB_UPDATE_FAILED($card) unless defined($stat);
561 # returns event on error. returns undef otherwise
562 sub _delete_address {
563 my( $session, $address ) = @_;
565 $logger->info("Deleting address ".$address->id." from DB");
567 my $stat = $session->request(
568 "open-ils.storage.direct.actor.user_address.delete", $address )->gather(1);
570 return $U->DB_UPDATE_FAILED($address) unless defined($stat);
576 sub _add_survey_responses {
577 my ($session, $patron, $new_patron) = @_;
579 $logger->info( "Updating survey responses for patron ".$new_patron->id );
581 my $responses = $patron->survey_responses;
585 $_->usr($new_patron->id) for (@$responses);
587 my $evt = $U->simplereq( "open-ils.circ",
588 "open-ils.circ.survey.submit.user_id", $responses );
590 return (undef, $evt) if defined($U->event_code($evt));
594 return ( $new_patron, undef );
598 sub _create_stat_maps {
600 my($session, $user_session, $patron, $new_patron) = @_;
602 my $maps = $patron->stat_cat_entries();
604 for my $map (@$maps) {
606 my $method = "open-ils.storage.direct.actor.stat_cat_entry_user_map.update";
608 if ($map->isdeleted()) {
609 $method = "open-ils.storage.direct.actor.stat_cat_entry_user_map.delete";
611 } elsif ($map->isnew()) {
612 $method = "open-ils.storage.direct.actor.stat_cat_entry_user_map.create";
617 $map->target_usr($new_patron->id);
620 $logger->info("Updating stat entry with method $method and map $map");
622 my $stat = $session->request($method, $map)->gather(1);
623 return (undef, $U->DB_UPDATE_FAILED($map)) unless defined($stat);
627 return ($new_patron, undef);
630 sub _create_perm_maps {
632 my($session, $user_session, $patron, $new_patron) = @_;
634 my $maps = $patron->permissions;
636 for my $map (@$maps) {
638 my $method = "open-ils.storage.direct.permission.usr_perm_map.update";
639 if ($map->isdeleted()) {
640 $method = "open-ils.storage.direct.permission.usr_perm_map.delete";
641 } elsif ($map->isnew()) {
642 $method = "open-ils.storage.direct.permission.usr_perm_map.create";
647 $map->usr($new_patron->id);
649 #warn( "Updating permissions with method $method and session $user_session and map $map" );
650 $logger->info( "Updating permissions with method $method and map $map" );
652 my $stat = $session->request($method, $map)->gather(1);
653 return (undef, $U->DB_UPDATE_FAILED($map)) unless defined($stat);
657 return ($new_patron, undef);
661 sub _create_standing_penalties {
663 my($session, $user_session, $patron, $new_patron) = @_;
665 my $maps = $patron->standing_penalties;
668 for my $map (@$maps) {
670 if ($map->isdeleted()) {
671 $method = "open-ils.storage.direct.actor.user_standing_penalty.delete";
672 } elsif ($map->isnew()) {
673 $method = "open-ils.storage.direct.actor.user_standing_penalty.create";
679 $map->usr($new_patron->id);
681 $logger->debug( "Updating standing penalty with method $method and session $user_session and map $map" );
683 my $stat = $session->request($method, $map)->gather(1);
684 return (undef, $U->DB_UPDATE_FAILED($map)) unless $stat;
687 return ($new_patron, undef);
692 __PACKAGE__->register_method(
693 method => "search_username",
694 api_name => "open-ils.actor.user.search.username",
697 sub search_username {
698 my($self, $client, $username) = @_;
699 my $users = OpenILS::Application::AppUtils->simple_scalar_request(
701 "open-ils.storage.direct.actor.user.search.usrname.atomic",
709 __PACKAGE__->register_method(
710 method => "user_retrieve_by_barcode",
711 api_name => "open-ils.actor.user.fleshed.retrieve_by_barcode",);
713 sub user_retrieve_by_barcode {
714 my($self, $client, $user_session, $barcode) = @_;
716 $logger->debug("Searching for user with barcode $barcode");
717 my ($user_obj, $evt) = $apputils->checkses($user_session);
721 my $session = OpenSRF::AppSession->create("open-ils.storage");
723 # find the card with the given barcode
724 my $creq = $session->request(
725 "open-ils.storage.direct.actor.card.search.barcode.atomic",
727 my $card = $creq->gather(1);
729 if(!$card || !$card->[0]) {
730 $session->disconnect();
731 return OpenILS::Event->new( 'ACTOR_USER_NOT_FOUND' );
735 my $user = flesh_user($card->usr(), $session);
737 $evt = $U->check_perms($user_obj->id, $user->home_ou, 'VIEW_USER');
740 $session->disconnect();
741 if(!$user) { return OpenILS::Event->new( 'ACTOR_USER_NOT_FOUND' ); }
748 __PACKAGE__->register_method(
749 method => "get_user_by_id",
750 api_name => "open-ils.actor.user.retrieve",);
753 my ($self, $client, $user_session, $id) = @_;
755 my $user_obj = $apputils->check_user_session( $user_session );
757 return $apputils->simple_scalar_request(
759 "open-ils.storage.direct.actor.user.retrieve",
765 __PACKAGE__->register_method(
766 method => "get_org_types",
767 api_name => "open-ils.actor.org_types.retrieve",);
771 my($self, $client) = @_;
773 return $org_types if $org_types;
775 $apputils->simple_scalar_request(
777 "open-ils.storage.direct.actor.org_unit_type.retrieve.all.atomic" );
782 __PACKAGE__->register_method(
783 method => "get_user_profiles",
784 api_name => "open-ils.actor.user.profiles.retrieve",
788 sub get_user_profiles {
789 return $user_profiles if $user_profiles;
791 return $user_profiles =
792 $apputils->simple_scalar_request(
794 "open-ils.storage.direct.actor.profile.retrieve.all.atomic");
799 __PACKAGE__->register_method(
800 method => "get_user_ident_types",
801 api_name => "open-ils.actor.user.ident_types.retrieve",
804 sub get_user_ident_types {
805 return $ident_types if $ident_types;
806 return $ident_types =
807 $apputils->simple_scalar_request(
809 "open-ils.storage.direct.config.identification_type.retrieve.all.atomic" );
815 __PACKAGE__->register_method(
816 method => "get_org_unit",
817 api_name => "open-ils.actor.org_unit.retrieve",
822 my( $self, $client, $user_session, $org_id ) = @_;
824 if(defined($user_session) && !defined($org_id)) {
826 OpenILS::Application::AppUtils->check_user_session( $user_session ); #throws EX on error
827 if(!defined($org_id)) {
828 $org_id = $user_obj->home_ou;
833 my $home_ou = OpenILS::Application::AppUtils->simple_scalar_request(
835 "open-ils.storage.direct.actor.org_unit.retrieve",
841 __PACKAGE__->register_method(
842 method => "search_org_unit",
843 api_name => "open-ils.actor.org_unit_list.search",
846 sub search_org_unit {
848 my( $self, $client, $field, $value ) = @_;
850 my $list = OpenILS::Application::AppUtils->simple_scalar_request(
852 "open-ils.storage.direct.actor.org_unit.search.$field.atomic",
861 __PACKAGE__->register_method(
862 method => "get_org_tree",
863 api_name => "open-ils.actor.org_tree.retrieve",
865 note => "Returns the entire org tree structure",
869 my( $self, $client) = @_;
872 $cache_client = OpenSRF::Utils::Cache->new("global", 0);
874 # see if it's in the cache
875 #warn "Getting ORG Tree\n";
876 my $tree = $cache_client->get_cache('orgtree');
878 #warn "Found orgtree in cache. returning...\n";
882 my $orglist = $apputils->simple_scalar_request(
884 "open-ils.storage.direct.actor.org_unit.retrieve.all.atomic" );
887 #warn "found org list\n";
890 $tree = $self->build_org_tree($orglist);
891 $cache_client->put_cache('orgtree', $tree);
897 # turns an org list into an org tree
900 my( $self, $orglist) = @_;
902 return $orglist unless (
903 ref($orglist) and @$orglist > 1 );
906 $a->ou_type <=> $b->ou_type ||
907 $a->name cmp $b->name } @$orglist;
909 for my $org (@list) {
911 next unless ($org and defined($org->parent_ou));
912 my ($parent) = grep { $_->id == $org->parent_ou } @list;
915 $parent->children([]) unless defined($parent->children);
916 push( @{$parent->children}, $org );
924 __PACKAGE__->register_method(
925 method => "get_org_descendants",
926 api_name => "open-ils.actor.org_tree.descendants.retrieve"
929 # depth is optional. org_unit is the id
930 sub get_org_descendants {
931 my( $self, $client, $org_unit, $depth ) = @_;
932 my $orglist = $apputils->simple_scalar_request(
934 "open-ils.storage.actor.org_unit.descendants.atomic",
936 return $self->build_org_tree($orglist);
940 __PACKAGE__->register_method(
941 method => "get_org_ancestors",
942 api_name => "open-ils.actor.org_tree.ancestors.retrieve"
945 # depth is optional. org_unit is the id
946 sub get_org_ancestors {
947 my( $self, $client, $org_unit, $depth ) = @_;
948 my $orglist = $apputils->simple_scalar_request(
950 "open-ils.storage.actor.org_unit.ancestors.atomic",
952 return $self->build_org_tree($orglist);
956 __PACKAGE__->register_method(
957 method => "get_standings",
958 api_name => "open-ils.actor.standings.retrieve"
963 return $user_standings if $user_standings;
964 return $user_standings =
965 $apputils->simple_scalar_request(
967 "open-ils.storage.direct.config.standing.retrieve.all.atomic" );
972 __PACKAGE__->register_method(
973 method => "get_my_org_path",
974 api_name => "open-ils.actor.org_unit.full_path.retrieve"
977 sub get_my_org_path {
978 my( $self, $client, $user_session, $org_id ) = @_;
979 my $user_obj = $apputils->check_user_session($user_session);
980 if(!defined($org_id)) { $org_id = $user_obj->home_ou; }
982 return $apputils->simple_scalar_request(
984 "open-ils.storage.actor.org_unit.full_path.atomic",
989 __PACKAGE__->register_method(
990 method => "patron_adv_search",
991 api_name => "open-ils.actor.patron.search.advanced" );
993 sub patron_adv_search {
994 my( $self, $client, $staff_login, $search_hash, $search_limit, $search_sort ) = @_;
996 #warn "patron adv with $staff_login and search " .
997 #Dumper($search_hash) . "\n";
999 my $session = OpenSRF::AppSession->create("open-ils.storage");
1000 my $req = $session->request(
1001 "open-ils.storage.actor.user.crazy_search", $search_hash, $search_limit, $search_sort);
1003 my $ans = $req->gather(1);
1005 my %hash = map { ($_ =>1) } @$ans;
1006 $ans = [ keys %hash ];
1008 #warn "Returning @$ans\n";
1010 $session->disconnect();
1017 sub _verify_password {
1018 my($user_session, $password) = @_;
1019 my $user_obj = $apputils->check_user_session($user_session);
1021 #grab the user with password
1022 $user_obj = $apputils->simple_scalar_request(
1024 "open-ils.storage.direct.actor.user.retrieve",
1027 if($user_obj->passwd eq $password) {
1035 __PACKAGE__->register_method(
1036 method => "update_password",
1037 api_name => "open-ils.actor.user.password.update");
1039 __PACKAGE__->register_method(
1040 method => "update_password",
1041 api_name => "open-ils.actor.user.username.update");
1043 __PACKAGE__->register_method(
1044 method => "update_password",
1045 api_name => "open-ils.actor.user.email.update");
1047 sub update_password {
1048 my( $self, $client, $user_session, $new_value, $current_password ) = @_;
1052 #warn "Updating user with method " .$self->api_name . "\n";
1053 my $user_obj = $apputils->check_user_session($user_session);
1055 if($self->api_name =~ /password/o) {
1057 #make sure they know the current password
1058 if(!_verify_password($user_session, md5_hex($current_password))) {
1059 return OpenILS::EX->new("USER_WRONG_PASSWORD")->ex;
1062 $user_obj->passwd($new_value);
1064 elsif($self->api_name =~ /username/o) {
1065 my $users = search_username(undef, undef, $new_value);
1066 if( $users and $users->[0] ) {
1067 return OpenILS::Event->new('USERNAME_EXISTS');
1069 $user_obj->usrname($new_value);
1072 elsif($self->api_name =~ /email/o) {
1073 #warn "Updating email to $new_value\n";
1074 $user_obj->email($new_value);
1077 my $session = $apputils->start_db_session();
1079 ( $user_obj, $evt ) = _update_patron($session, $user_obj, $user_obj);
1080 return $evt if $evt;
1082 $apputils->commit_db_session($session);
1084 if($user_obj) { return 1; }
1089 __PACKAGE__->register_method(
1090 method => "check_user_perms",
1091 api_name => "open-ils.actor.user.perm.check",
1092 notes => <<" NOTES");
1093 Takes a login session, user id, an org id, and an array of perm type strings. For each
1094 perm type, if the user does *not* have the given permission it is added
1095 to a list which is returned from the method. If all permissions
1096 are allowed, an empty list is returned
1097 if the logged in user does not match 'user_id', then the logged in user must
1098 have VIEW_PERMISSION priveleges.
1101 sub check_user_perms {
1102 my( $self, $client, $login_session, $user_id, $org_id, $perm_types ) = @_;
1104 my( $staff, $evt ) = $apputils->checkses($login_session);
1105 return $evt if $evt;
1107 if($staff->id ne $user_id) {
1108 if( my $evt = $apputils->check_perms(
1109 $staff->id, $org_id, 'VIEW_PERMISSION') ) {
1115 for my $perm (@$perm_types) {
1116 if($apputils->check_perms($user_id, $org_id, $perm)) {
1117 push @not_allowed, $perm;
1121 return \@not_allowed
1124 __PACKAGE__->register_method(
1125 method => "check_user_perms2",
1126 api_name => "open-ils.actor.user.perm.check.multi_org",
1128 Checks the permissions on a list of perms and orgs for a user
1129 @param authtoken The login session key
1130 @param user_id The id of the user to check
1131 @param orgs The array of org ids
1132 @param perms The array of permission names
1133 @return An array of [ orgId, permissionName ] arrays that FAILED the check
1134 if the logged in user does not match 'user_id', then the logged in user must
1135 have VIEW_PERMISSION priveleges.
1138 sub check_user_perms2 {
1139 my( $self, $client, $authtoken, $user_id, $orgs, $perms ) = @_;
1141 my( $staff, $target, $evt ) = $apputils->checkses_requestor(
1142 $authtoken, $user_id, 'VIEW_PERMISSION' );
1143 return $evt if $evt;
1146 for my $org (@$orgs) {
1147 for my $perm (@$perms) {
1148 if($apputils->check_perms($user_id, $org, $perm)) {
1149 push @not_allowed, [ $org, $perm ];
1154 return \@not_allowed
1158 __PACKAGE__->register_method(
1159 method => 'check_user_perms3',
1160 api_name => 'open-ils.actor.user.perm.highest_org',
1162 Returns the highest org unit id at which a user has a given permission
1163 If the requestor does not match the target user, the requestor must have
1164 'VIEW_PERMISSION' rights at the home org unit of the target user
1165 @param authtoken The login session key
1166 @param userid The id of the user in question
1167 @param perm The permission to check
1168 @return The org unit highest in the org tree within which the user has
1169 the requested permission
1172 sub check_user_perms3 {
1173 my( $self, $client, $authtoken, $userid, $perm ) = @_;
1175 my( $staff, $target, $org, $evt );
1177 ( $staff, $target, $evt ) = $apputils->checkses_requestor(
1178 $authtoken, $userid, 'VIEW_PERMISSION' );
1179 return $evt if $evt;
1181 my $tree = $self->get_org_tree();
1182 return _find_highest_perm_org( $perm, $userid, $target->home_ou, $tree );
1186 sub _find_highest_perm_org {
1187 my ( $perm, $userid, $start_org, $org_tree ) = @_;
1188 my $org = $apputils->find_org($org_tree, $start_org );
1192 last if ($apputils->check_perms( $userid, $org->id, $perm )); # perm failed
1194 $org = $apputils->find_org( $org_tree, $org->parent_ou() );
1200 __PACKAGE__->register_method(
1201 method => 'check_user_perms4',
1202 api_name => 'open-ils.actor.user.perm.highest_org.batch',
1204 Returns the highest org unit id at which a user has a given permission
1205 If the requestor does not match the target user, the requestor must have
1206 'VIEW_PERMISSION' rights at the home org unit of the target user
1207 @param authtoken The login session key
1208 @param userid The id of the user in question
1209 @param perms An array of perm names to check
1210 @return An array of orgId's representing the org unit
1211 highest in the org tree within which the user has the requested permission
1212 The arrah of orgId's has matches the order of the perms array
1215 sub check_user_perms4 {
1216 my( $self, $client, $authtoken, $userid, $perms ) = @_;
1218 my( $staff, $target, $org, $evt );
1220 ( $staff, $target, $evt ) = $apputils->checkses_requestor(
1221 $authtoken, $userid, 'VIEW_PERMISSION' );
1222 return $evt if $evt;
1225 return [] unless ref($perms);
1226 my $tree = $self->get_org_tree();
1228 for my $p (@$perms) {
1229 push( @arr, _find_highest_perm_org( $p, $userid, $target->home_ou, $tree ) );
1237 __PACKAGE__->register_method(
1238 method => "user_fines_summary",
1239 api_name => "open-ils.actor.user.fines.summary",
1240 notes => <<" NOTES");
1241 Returns a short summary of the users total open fines, excluding voided fines
1242 Params are login_session, user_id
1243 Returns a 'mous' object.
1246 sub user_fines_summary {
1247 my( $self, $client, $login_session, $user_id ) = @_;
1249 my $user_obj = $apputils->check_user_session($login_session);
1250 if($user_obj->id ne $user_id) {
1251 if($apputils->check_user_perms($user_obj->id, $user_obj->home_ou, "VIEW_USER_FINES_SUMMARY")) {
1252 return OpenILS::Perm->new("VIEW_USER_FINES_SUMMARY");
1256 return $apputils->simple_scalar_request(
1258 "open-ils.storage.direct.money.open_user_summary.search.usr",
1266 __PACKAGE__->register_method(
1267 method => "user_transactions",
1268 api_name => "open-ils.actor.user.transactions",
1269 notes => <<" NOTES");
1270 Returns a list of open user transactions (mbts objects);
1271 Params are login_session, user_id
1272 Optional third parameter is the transactions type. defaults to all
1275 __PACKAGE__->register_method(
1276 method => "user_transactions",
1277 api_name => "open-ils.actor.user.transactions.have_charge",
1278 notes => <<" NOTES");
1279 Returns a list of all open user transactions (mbts objects) that have an initial charge
1280 Params are login_session, user_id
1281 Optional third parameter is the transactions type. defaults to all
1284 __PACKAGE__->register_method(
1285 method => "user_transactions",
1286 api_name => "open-ils.actor.user.transactions.have_balance",
1287 notes => <<" NOTES");
1288 Returns a list of all open user transactions (mbts objects) that have a balance
1289 Params are login_session, user_id
1290 Optional third parameter is the transactions type. defaults to all
1293 __PACKAGE__->register_method(
1294 method => "user_transactions",
1295 api_name => "open-ils.actor.user.transactions.fleshed",
1296 notes => <<" NOTES");
1297 Returns an object/hash of transaction, circ, title where transaction = an open
1298 user transactions (mbts objects), circ is the attached circluation, and title
1299 is the title the circ points to
1300 Params are login_session, user_id
1301 Optional third parameter is the transactions type. defaults to all
1304 __PACKAGE__->register_method(
1305 method => "user_transactions",
1306 api_name => "open-ils.actor.user.transactions.have_charge.fleshed",
1307 notes => <<" NOTES");
1308 Returns an object/hash of transaction, circ, title where transaction = an open
1309 user transactions that has an initial charge (mbts objects), circ is the
1310 attached circluation, and title is the title the circ points to
1311 Params are login_session, user_id
1312 Optional third parameter is the transactions type. defaults to all
1315 __PACKAGE__->register_method(
1316 method => "user_transactions",
1317 api_name => "open-ils.actor.user.transactions.have_balance.fleshed",
1318 notes => <<" NOTES");
1319 Returns an object/hash of transaction, circ, title where transaction = an open
1320 user transaction that has a balance (mbts objects), circ is the attached
1321 circluation, and title is the title the circ points to
1322 Params are login_session, user_id
1323 Optional third parameter is the transaction type. defaults to all
1326 __PACKAGE__->register_method(
1327 method => "user_transactions",
1328 api_name => "open-ils.actor.user.transactions.count",
1329 notes => <<" NOTES");
1330 Returns an object/hash of transaction, circ, title where transaction = an open
1331 user transactions (mbts objects), circ is the attached circluation, and title
1332 is the title the circ points to
1333 Params are login_session, user_id
1334 Optional third parameter is the transactions type. defaults to all
1337 __PACKAGE__->register_method(
1338 method => "user_transactions",
1339 api_name => "open-ils.actor.user.transactions.have_charge.count",
1340 notes => <<" NOTES");
1341 Returns an object/hash of transaction, circ, title where transaction = an open
1342 user transactions that has an initial charge (mbts objects), circ is the
1343 attached circluation, and title is the title the circ points to
1344 Params are login_session, user_id
1345 Optional third parameter is the transactions type. defaults to all
1348 __PACKAGE__->register_method(
1349 method => "user_transactions",
1350 api_name => "open-ils.actor.user.transactions.have_balance.count",
1351 notes => <<" NOTES");
1352 Returns an object/hash of transaction, circ, title where transaction = an open
1353 user transaction that has a balance (mbts objects), circ is the attached
1354 circluation, and title is the title the circ points to
1355 Params are login_session, user_id
1356 Optional third parameter is the transaction type. defaults to all
1359 __PACKAGE__->register_method(
1360 method => "user_transactions",
1361 api_name => "open-ils.actor.user.transactions.have_balance.total",
1362 notes => <<" NOTES");
1363 Returns an object/hash of transaction, circ, title where transaction = an open
1364 user transaction that has a balance (mbts objects), circ is the attached
1365 circluation, and title is the title the circ points to
1366 Params are login_session, user_id
1367 Optional third parameter is the transaction type. defaults to all
1372 sub user_transactions {
1373 my( $self, $client, $login_session, $user_id, $type ) = @_;
1375 my( $user_obj, $target, $evt ) = $apputils->checkses_requestor(
1376 $login_session, $user_id, 'VIEW_USER_TRANSACTIONS' );
1377 return $evt if $evt;
1379 my $api = $self->api_name();
1383 if(defined($type)) { @xact = (xact_type => $type);
1385 } else { @xact = (); }
1387 if($api =~ /have_charge/o) {
1389 $trans = $apputils->simple_scalar_request(
1391 "open-ils.storage.direct.money.open_billable_transaction_summary.search_where.atomic",
1392 { usr => $user_id, total_owed => { ">" => 0 }, @xact });
1394 } elsif($api =~ /have_balance/o) {
1396 $trans = $apputils->simple_scalar_request(
1398 "open-ils.storage.direct.money.open_billable_transaction_summary.search_where.atomic",
1399 { usr => $user_id, balance_owed => { "<>" => 0 }, @xact });
1403 $trans = $apputils->simple_scalar_request(
1405 "open-ils.storage.direct.money.open_billable_transaction_summary.search_where.atomic",
1406 { usr => $user_id, @xact });
1409 if($api =~ /total/o) {
1411 for my $t (@$trans) {
1412 $total += $t->balance_owed;
1415 $logger->debug("Total balance owed by user $user_id: $total");
1419 if($api =~ /count/o) { return scalar @$trans; }
1420 if($api !~ /fleshed/o) { return $trans; }
1423 for my $t (@$trans) {
1425 if( $t->xact_type ne 'circulation' ) {
1426 push @resp, {transaction => $t};
1430 my $circ = $apputils->simple_scalar_request(
1432 "open-ils.storage.direct.action.circulation.retrieve",
1437 my $title = $apputils->simple_scalar_request(
1439 "open-ils.storage.fleshed.biblio.record_entry.retrieve_by_copy",
1440 $circ->target_copy );
1444 my $u = OpenILS::Utils::ModsParser->new();
1445 $u->start_mods_batch($title->marc());
1446 my $mods = $u->finish_mods_batch();
1448 push @resp, {transaction => $t, circ => $circ, record => $mods };
1456 __PACKAGE__->register_method(
1457 method => "user_transaction_retrieve",
1458 api_name => "open-ils.actor.user.transaction.fleshed.retrieve",
1460 notes => <<" NOTES");
1461 Returns a fleshedtransaction record
1463 __PACKAGE__->register_method(
1464 method => "user_transaction_retrieve",
1465 api_name => "open-ils.actor.user.transaction.retrieve",
1467 notes => <<" NOTES");
1468 Returns a transaction record
1470 sub user_transaction_retrieve {
1471 my( $self, $client, $login_session, $bill_id ) = @_;
1473 my $trans = $apputils->simple_scalar_request(
1475 "open-ils.storage.direct.money.billable_transaction_summary.retrieve",
1479 my( $user_obj, $target, $evt ) = $apputils->checkses_requestor(
1480 $login_session, $trans->usr, 'VIEW_USER_TRANSACTIONS' );
1481 return $evt if $evt;
1483 my $api = $self->api_name();
1484 if($api !~ /fleshed/o) { return $trans; }
1486 if( $trans->xact_type ne 'circulation' ) {
1487 $logger->debug("Returning non-circ transaction");
1488 return {transaction => $trans};
1491 my $circ = $apputils->simple_scalar_request(
1493 "open-ils.storage.direct.action.circulation.retrieve",
1496 return {transaction => $trans} unless $circ;
1497 $logger->debug("Found the circ transaction");
1499 my $title = $apputils->simple_scalar_request(
1501 "open-ils.storage.fleshed.biblio.record_entry.retrieve_by_copy",
1502 $circ->target_copy );
1504 return {transaction => $trans, circ => $circ } unless $title;
1505 $logger->debug("Found the circ title");
1509 my $u = OpenILS::Utils::ModsParser->new();
1510 $u->start_mods_batch($title->marc());
1511 $mods = $u->finish_mods_batch();
1513 if ($title->id == -1) {
1514 my $copy = $apputils->simple_scalar_request(
1516 "open-ils.storage.direct.asset.copy.retrieve",
1517 $circ->target_copy );
1519 $mods = new Fieldmapper::metabib::virtual_record;
1521 $mods->title($copy->dummy_title);
1522 $mods->author($copy->dummy_author);
1526 $logger->debug("MODSized the circ title");
1528 return {transaction => $trans, circ => $circ, record => $mods };
1532 __PACKAGE__->register_method(
1533 method => "hold_request_count",
1534 api_name => "open-ils.actor.user.hold_requests.count",
1536 notes => <<" NOTES");
1537 Returns hold ready/total counts
1539 sub hold_request_count {
1540 my( $self, $client, $login_session, $userid ) = @_;
1542 my( $user_obj, $target, $evt ) = $apputils->checkses_requestor(
1543 $login_session, $userid, 'VIEW_HOLD' );
1544 return $evt if $evt;
1547 my $holds = $apputils->simple_scalar_request(
1549 "open-ils.storage.direct.action.hold_request.search_where.atomic",
1551 fulfillment_time => {"=" => undef } }
1555 for my $h (@$holds) {
1556 next unless $h->capture_time;
1558 my $copy = $apputils->simple_scalar_request(
1560 "open-ils.storage.direct.asset.copy.retrieve",
1564 if ($copy->status == 8) {
1569 return { total => scalar(@$holds), ready => scalar(@ready) };
1573 __PACKAGE__->register_method(
1574 method => "checkedout_count",
1575 api_name => "open-ils.actor.user.checked_out.count",
1577 notes => <<" NOTES");
1578 Returns a transaction record
1580 sub checkedout_count {
1581 my( $self, $client, $login_session, $userid ) = @_;
1583 my( $user_obj, $target, $evt ) = $apputils->checkses_requestor(
1584 $login_session, $userid, 'VIEW_CIRCULATIONS' );
1585 return $evt if $evt;
1588 my $circs = $apputils->simple_scalar_request(
1590 "open-ils.storage.direct.action.circulation.search_where.atomic",
1592 checkin_time => {"=" => undef } }
1595 my $parser = DateTime::Format::ISO8601->new;
1598 for my $c (@$circs) {
1599 my $due_dt = $parser->parse_datetime( clense_ISO8601( $c->due_date ) );
1600 my $due = $due_dt->epoch;
1602 if ($due < DateTime->today->epoch) {
1607 return { total => scalar(@$circs), overdue => scalar(@overdue) };
1610 __PACKAGE__->register_method(
1611 method => "user_transaction_history",
1612 api_name => "open-ils.actor.user.transactions.history",
1614 notes => <<" NOTES");
1615 Returns a list of billable transaction ids for a user, optionally by type
1617 __PACKAGE__->register_method(
1618 method => "user_transaction_history",
1619 api_name => "open-ils.actor.user.transactions.history.have_charge",
1621 notes => <<" NOTES");
1622 Returns a list of billable transaction ids for a user that have an initial charge, optionally by type
1624 sub user_transaction_history {
1625 my( $self, $client, $login_session, $user_id, $type ) = @_;
1627 my( $user_obj, $target, $evt ) = $apputils->checkses_requestor(
1628 $login_session, $user_id, 'VIEW_USER_TRANSACTIONS' );
1629 return $evt if $evt;
1631 my $api = $self->api_name();
1635 @xact = (xact_type => $type) if(defined($type));
1636 @charge = (total_owed => { ">" => 0}) if($api =~ /have_charge/);
1638 my $trans = $apputils->simple_scalar_request(
1640 "open-ils.storage.direct.money.billable_transaction_summary.search_where.atomic",
1641 { usr => $user_id, @xact, @charge }, { order_by => 'xact_start DESC' });
1643 return [ map { $_->id } @$trans ];
1647 __PACKAGE__->register_method(
1648 method => "user_perms",
1649 api_name => "open-ils.actor.permissions.user_perms.retrieve",
1651 notes => <<" NOTES");
1652 Returns a list of permissions
1655 my( $self, $client, $authtoken, $user ) = @_;
1657 my( $staff, $evt ) = $apputils->checkses($authtoken);
1658 return $evt if $evt;
1660 $user ||= $staff->id;
1662 if( $user != $staff->id and $evt = $apputils->check_perms( $staff->id, $staff->home_ou, 'VIEW_PERMISSION') ) {
1666 return $apputils->simple_scalar_request(
1668 "open-ils.storage.permission.user_perms.atomic",
1672 __PACKAGE__->register_method(
1673 method => "retrieve_perms",
1674 api_name => "open-ils.actor.permissions.retrieve",
1675 notes => <<" NOTES");
1676 Returns a list of permissions
1678 sub retrieve_perms {
1679 my( $self, $client ) = @_;
1680 return $apputils->simple_scalar_request(
1682 "open-ils.storage.direct.permission.perm_list.retrieve.all.atomic");
1685 __PACKAGE__->register_method(
1686 method => "retrieve_groups",
1687 api_name => "open-ils.actor.groups.retrieve",
1688 notes => <<" NOTES");
1689 Returns a list of user groupss
1691 sub retrieve_groups {
1692 my( $self, $client ) = @_;
1693 return $apputils->simple_scalar_request(
1695 "open-ils.storage.direct.permission.grp_tree.retrieve.all.atomic");
1698 __PACKAGE__->register_method(
1699 method => "retrieve_org_address",
1700 api_name => "open-ils.actor.org_unit.address.retrieve",
1701 notes => <<' NOTES');
1702 Returns an org_unit address by ID
1703 @param An org_address ID
1705 sub retrieve_org_address {
1706 my( $self, $client, $id ) = @_;
1707 return $apputils->simple_scalar_request(
1709 "open-ils.storage.direct.actor.org_address.retrieve",
1714 __PACKAGE__->register_method(
1715 method => "retrieve_groups_tree",
1716 api_name => "open-ils.actor.groups.tree.retrieve",
1717 notes => <<" NOTES");
1718 Returns a list of user groups
1720 sub retrieve_groups_tree {
1721 my( $self, $client ) = @_;
1722 my $groups = $apputils->simple_scalar_request(
1724 "open-ils.storage.direct.permission.grp_tree.retrieve.all.atomic");
1725 return $self->build_group_tree($groups);
1729 # turns an org list into an org tree
1730 sub build_group_tree {
1732 my( $self, $grplist) = @_;
1734 return $grplist unless (
1735 ref($grplist) and @$grplist > 1 );
1737 my @list = sort { $a->name cmp $b->name } @$grplist;
1740 for my $grp (@list) {
1742 if ($grp and !defined($grp->parent)) {
1746 my ($parent) = grep { $_->id == $grp->parent} @list;
1748 $parent->children([]) unless defined($parent->children);
1749 push( @{$parent->children}, $grp );
1757 __PACKAGE__->register_method(
1758 method => "add_user_to_groups",
1759 api_name => "open-ils.actor.user.set_groups",
1760 notes => <<" NOTES");
1761 Adds a user to one or more permission groups
1764 sub add_user_to_groups {
1765 my( $self, $client, $authtoken, $userid, $groups ) = @_;
1767 my( $requestor, $target, $evt ) = $apputils->checkses_requestor(
1768 $authtoken, $userid, 'CREATE_USER_GROUP_LINK' );
1769 return $evt if $evt;
1771 ( $requestor, $target, $evt ) = $apputils->checkses_requestor(
1772 $authtoken, $userid, 'REMOVE_USER_GROUP_LINK' );
1773 return $evt if $evt;
1775 $apputils->simplereq(
1777 'open-ils.storage.direct.permission.usr_grp_map.mass_delete', { usr => $userid } );
1779 for my $group (@$groups) {
1780 my $link = Fieldmapper::permission::usr_grp_map->new;
1782 $link->usr($userid);
1784 my $id = $apputils->simplereq(
1786 'open-ils.storage.direct.permission.usr_grp_map.create', $link );
1792 __PACKAGE__->register_method(
1793 method => "get_user_perm_groups",
1794 api_name => "open-ils.actor.user.get_groups",
1795 notes => <<" NOTES");
1796 Retrieve a user's permission groups.
1800 sub get_user_perm_groups {
1801 my( $self, $client, $authtoken, $userid ) = @_;
1803 my( $requestor, $target, $evt ) = $apputils->checkses_requestor(
1804 $authtoken, $userid, 'VIEW_PERM_GROUPS' );
1805 return $evt if $evt;
1807 return $apputils->simplereq(
1809 'open-ils.storage.direct.permission.usr_grp_map.search.usr.atomic', $userid );
1814 __PACKAGE__->register_method (
1815 method => 'register_workstation',
1816 api_name => 'open-ils.actor.workstation.register',
1818 Registers a new workstion in the system
1819 @param authtoken The login session key
1820 @param name The name of the workstation id
1821 @param owner The org unit that owns this workstation
1822 @return The workstation id on success, WORKSTATION_NAME_EXISTS
1823 if the name is already in use.
1826 sub register_workstation {
1827 my( $self, $connection, $authtoken, $name, $owner ) = @_;
1828 my( $requestor, $evt ) = $U->checkses($authtoken);
1829 return $evt if $evt;
1830 $evt = $U->check_perms($requestor->id, $owner, 'REGISTER_WORKSTATION');
1831 return $evt if $evt;
1833 my $ws = $U->storagereq(
1834 'open-ils.storage.direct.actor.workstation.search.name', $name );
1835 return OpenILS::Event->new('WORKSTATION_NAME_EXISTS') if $ws;
1837 $ws = Fieldmapper::actor::workstation->new;
1838 $ws->owning_lib($owner);
1841 my $id = $U->storagereq(
1842 'open-ils.storage.direct.actor.workstation.create', $ws );
1843 return $U->DB_UPDATE_FAILED($ws) unless $id;
1850 __PACKAGE__->register_method (
1851 method => 'fetch_patron_note',
1852 api_name => 'open-ils.actor.note.retrieve.all',
1854 Returns a list of notes for a given user
1855 Requestor must have VIEW_USER permission if pub==false and
1856 @param authtoken The login session key
1857 @param args Hash of params including
1858 patronid : the patron's id
1859 pub : true if retrieving only public notes
1863 sub fetch_patron_note {
1864 my( $self, $conn, $authtoken, $args ) = @_;
1865 my $patronid = $$args{patronid};
1867 my($reqr, $evt) = $U->checkses($authtoken);
1870 ($patron, $evt) = $U->fetch_user($patronid);
1871 return $evt if $evt;
1874 if( $patronid ne $reqr->id ) {
1875 $evt = $U->check_perms($reqr->id, $patron->home_ou, 'VIEW_USER');
1876 return $evt if $evt;
1878 return $U->storagereq(
1879 'open-ils.storage.direct.actor.usr_note.search_where.atomic',
1880 { usr => $patronid, pub => 't' } );
1883 $evt = $U->check_perms($reqr->id, $patron->home_ou, 'VIEW_USER');
1884 return $evt if $evt;
1886 return $U->storagereq(
1887 'open-ils.storage.direct.actor.usr_note.search.usr.atomic', $patronid );
1890 __PACKAGE__->register_method (
1891 method => 'create_user_note',
1892 api_name => 'open-ils.actor.note.create',
1894 Creates a new note for the given user
1895 @param authtoken The login session key
1896 @param note The note object
1899 sub create_user_note {
1900 my( $self, $conn, $authtoken, $note ) = @_;
1901 my( $reqr, $patron, $evt ) =
1902 $U->checkses_requestor($authtoken, $note->usr, 'UPDATE_USER');
1903 return $evt if $evt;
1904 $logger->activity("user ".$reqr->id." creating note for user ".$note->usr);
1906 $note->pub('f') unless $note->pub;
1907 $note->creator($reqr->id);
1908 my $id = $U->storagereq(
1909 'open-ils.storage.direct.actor.usr_note.create', $note );
1910 return $U->DB_UPDATE_FAILED($note) unless $id;
1915 __PACKAGE__->register_method (
1916 method => 'delete_user_note',
1917 api_name => 'open-ils.actor.note.delete',
1919 Deletes a note for the given user
1920 @param authtoken The login session key
1921 @param noteid The note id
1924 sub delete_user_note {
1925 my( $self, $conn, $authtoken, $noteid ) = @_;
1927 my $note = $U->storagereq(
1928 'open-ils.storage.direct.actor.usr_note.retrieve', $noteid);
1929 return OpenILS::Event->new('USER_NOTE_NOT_FOUND') unless $note;
1931 my( $reqr, $patron, $evt ) =
1932 $U->checkses_requestor($authtoken, $note->usr, 'UPDATE_USER');
1933 return $evt if $evt;
1934 $logger->activity("user ".$reqr->id." deleting note [$noteid] for user ".$note->usr);
1936 my $stat = $U->storagereq(
1937 'open-ils.storage.direct.actor.usr_note.delete', $noteid );
1938 return $U->DB_UPDATE_FAILED($note) unless defined $stat;
1944 __PACKAGE__->register_method (
1945 method => 'create_closed_date',
1946 api_name => 'open-ils.actor.org_unit.closed_date.create',
1948 Creates a new closing entry for the given org_unit
1949 @param authtoken The login session key
1950 @param note The closed_date object
1953 sub create_closed_date {
1954 my( $self, $conn, $authtoken, $cd ) = @_;
1956 my( $user, $evt ) = $U->checkses($authtoken);
1957 return $evt if $evt;
1959 $evt = $U->check_perms($user->id, $cd->org_unit, 'CREATE_CLOSEING');
1960 return $evt if $evt;
1962 $logger->activity("user ".$user->id." creating library closing for ".$cd->org_unit);
1964 my $id = $U->storagereq(
1965 'open-ils.storage.direct.actor.org_unit.closed_date.create', $cd );
1966 return $U->DB_UPDATE_FAILED($cd) unless $id;
1971 __PACKAGE__->register_method (
1972 method => 'delete_closed_date',
1973 api_name => 'open-ils.actor.org_unit.closed_date.delete',
1975 Deletes a closing entry for the given org_unit
1976 @param authtoken The login session key
1977 @param noteid The close_date id
1980 sub delete_closed_date {
1981 my( $self, $conn, $authtoken, $cd ) = @_;
1983 my( $user, $evt ) = $U->checkses($authtoken);
1984 return $evt if $evt;
1987 ($cd_obj, $evt) = fetch_closed_date($cd);
1988 return $evt if $evt;
1990 $evt = $U->check_perms($user->id, $cd->org_unit, 'DELETE_CLOSEING');
1991 return $evt if $evt;
1993 $logger->activity("user ".$user->id." deleting library closing for ".$cd->org_unit);
1995 my $stat = $U->storagereq(
1996 'open-ils.storage.direct.actor.org_unit.closed_date.delete', $cd );
1997 return $U->DB_UPDATE_FAILED($cd) unless $stat;