1 package OpenILS::Application::Acq::Picklist;
2 use base qw/OpenILS::Application/;
3 use strict; use warnings;
6 use OpenSRF::Utils::Logger qw(:logger);
7 use OpenILS::Utils::Fieldmapper;
8 use OpenILS::Utils::CStoreEditor q/:funcs/;
9 use OpenILS::Const qw/:const/;
10 use OpenSRF::Utils::SettingsClient;
11 use OpenILS::Application::AppUtils;
12 my $U = 'OpenILS::Application::AppUtils';
15 __PACKAGE__->register_method(
16 method => 'create_lineitem',
17 api_name => 'open-ils.acq.lineitem.create',
19 desc => 'Creates a lineitem',
21 {desc => 'Authentication token', type => 'string'},
22 {desc => 'The lineitem object to create', type => 'object'},
24 return => {desc => 'ID of newly created lineitem on success, Event on error'}
29 my($self, $conn, $auth, $li) = @_;
30 my $e = new_editor(xact=>1, authtoken=>$auth);
31 return $e->die_event unless $e->checkauth;
35 my $picklist = $e->retrieve_acq_picklist($li->picklist)
36 or return $e->die_event;
38 if($picklist->owner != $e->requestor->id) {
39 return $e->die_event unless
40 $e->allowed('CREATE_PICKLIST', $picklist->org_unit, $picklist);
43 # indicate the picklist was updated
44 $picklist->edit_time('now');
45 $e->update_acq_picklist($picklist) or return $e->die_event;
48 if($li->purchase_order) {
49 my $po = $e->retrieve_acq_purchase_order($li->purchase_order)
50 or return $e->die_event;
51 return $e->die_event unless
52 $e->allowed('MANAGE_PROVIDER', $po->ordering_agency, $po);
55 $li->selector($e->requestor->id);
56 $e->create_acq_lineitem($li) or return $e->die_event;
62 __PACKAGE__->register_method(
63 method => 'create_po_assets',
64 api_name => 'open-ils.acq.purchase_order.assets.create',
66 desc => q/Creates assets for each lineitem in the purchase order/,
68 {desc => 'Authentication token', type => 'string'},
69 {desc => 'The purchase order id', type => 'number'},
70 {desc => q/Options hash./}
72 return => {desc => 'Streams a total versus completed counts object, event on error'}
76 sub create_po_assets {
77 my($self, $conn, $auth, $po_id, $options) = @_;
78 my $e = new_editor(authtoken=>$auth, xact=>1);
79 return $e->die_event unless $e->checkauth;
81 my $po = $e->retrieve_acq_purchase_order($po_id) or return $e->event;
82 return $e->die_event unless
83 $e->allowed('CREATE_PURCHASE_ORDER', $po->ordering_agency);
85 my $li_ids = $e->search_acq_lineitem({purchase_order=>$po_id},{idlist=>1});
89 for my $li_id (@$li_ids) {
90 my $resp = create_lineitem_assets_impl($e, $auth, $li_id);
91 if($U->event_code($resp)) {
95 $conn->respond({total=>$count, progress=>++$count});
98 $po->edit_time('now');
99 $e->update_acq_purchase_order($po) or return $e->die_event;
102 return {complete=>1};
105 __PACKAGE__->register_method(
106 method => 'create_lineitem_assets',
107 api_name => 'open-ils.acq.lineitem.assets.create',
109 desc => q/Creates the bibliographic data, volume, and copies associated with a lineitem./,
111 {desc => 'Authentication token', type => 'string'},
112 {desc => 'The lineitem id', type => 'number'},
113 {desc => q/Options hash./}
115 return => {desc => 'ID of newly created bib record, Event on error'}
119 sub create_lineitem_assets {
120 my($self, $conn, $auth, $li_id, $options) = @_;
121 my $e = new_editor(authtoken=>$auth, xact=>1);
122 return $e->die_event unless $e->checkauth;
123 my $resp = create_lineitem_assets_impl($e, $auth, $li_id, $options);
124 if($U->event_code($resp)) {
132 sub create_lineitem_assets_impl {
133 my($e, $auth, $li_id, $options) = @_;
134 my $li = $e->retrieve_acq_lineitem([
137 flesh_fields => {jub => ['purchase_order']}
139 ]) or return $e->die_event;
141 return OpenILS::Event->new('BAD_PARAMS') # make this perm-based, not owner-based
142 unless $li->purchase_order->owner == $e->requestor->id;
144 # -----------------------------------------------------------------
145 # first, create the bib record if necessary
146 # -----------------------------------------------------------------
147 unless($li->eg_bib_id) {
148 my $record = $U->simplereq(
150 'open-ils.cat.biblio.record.xml.import',
151 $auth, $li->marc, $li->source_label);
153 if($U->event_code($record)) {
158 $li->eg_bib_id($record->id);
159 $e->update_acq_lineitem($li) or return $e->die_event;
162 my $li_details = $e->search_acq_lineitem_detail({lineitem => $li_id}, {idlist=>1});
164 # -----------------------------------------------------------------
165 # for each lineitem_detail, create the volume if necessary, create
166 # a copy, and link them all together.
167 # -----------------------------------------------------------------
169 for my $li_detail_id (@{$li_details}) {
171 my $li_detail = $e->retrieve_acq_lineitem_detail($li_detail_id)
172 or return $e->die_event;
174 my $volume = $volcache{$li_detail->cn_label};
175 unless($volume and $volume->owning_lib == $li_detail->owning_lib) {
176 my $vol_id = $U->simplereq(
178 'open-ils.cat.call_number.find_or_create',
179 $auth, $li_detail->cn_label, $li->eg_bib_id, $li_detail->owning_lib);
180 $volume = $e->retrieve_asset_call_number($vol_id) or return $e->die_event;
181 $volcache{$vol_id} = $volume;
184 if($U->event_code($volume)) {
189 my $copy = Fieldmapper::asset::copy->new;
191 $copy->loan_duration(2);
192 $copy->fine_level(2);
193 $copy->status(OILS_COPY_STATUS_ON_ORDER);
194 $copy->barcode($li_detail->barcode);
195 $copy->location($li_detail->location);
196 $copy->call_number($volume->id);
197 $copy->circ_lib($volume->owning_lib);
199 my $stat = $U->simplereq(
201 'open-ils.cat.asset.copy.fleshed.batch.update', $auth, [$copy]);
203 if($U->event_code($stat)) {
208 my $new_copy = $e->search_asset_copy({deleted=>'f', barcode=>$copy->barcode})->[0]
209 or return $e->die_event;
211 $li_detail->eg_copy_id($new_copy->id);
212 $e->update_acq_lineitem_detail($li_detail) or return $e->die_event;
220 __PACKAGE__->register_method(
221 method => 'retrieve_lineitem',
222 api_name => 'open-ils.acq.lineitem.retrieve',
224 desc => 'Retrieves a lineitem',
226 {desc => 'Authentication token', type => 'string'},
227 {desc => 'lineitem ID to retrieve', type => 'number'},
228 {options => q/Hash of options, including
229 "flesh_attrs", which fleshes the attributes;
230 "flesh_li_details", which fleshes the order details objects/, type => 'hash'},
232 return => {desc => 'lineitem object on success, Event on error'}
237 sub retrieve_lineitem {
238 my($self, $conn, $auth, $li_id, $options) = @_;
239 my $e = new_editor(authtoken=>$auth);
240 return $e->die_event unless $e->checkauth;
243 # XXX finer grained perms...
247 if($$options{flesh_attrs}) {
248 $li = $e->retrieve_acq_lineitem([
249 $li_id, {flesh => 1, flesh_fields => {jub => ['attributes']}}])
252 $li = $e->retrieve_acq_lineitem($li_id) or return $e->event;
255 if($$options{flesh_li_details}) {
258 flesh_fields => {acqlid => []}
260 push(@{$ops->{flesh_fields}->{acqlid}}, 'fund') if $$options{flesh_fund};
261 push(@{$ops->{flesh_fields}->{acqlid}}, 'fund_debit') if $$options{flesh_fund_debit};
262 my $details = $e->search_acq_lineitem_detail([{lineitem => $li_id}, $ops]);
263 $li->lineitem_details($details);
264 $li->item_count(scalar(@$details));
266 my $details = $e->search_acq_lineitem_detail({lineitem => $li_id}, {idlist=>1});
267 $li->item_count(scalar(@$details));
271 my $picklist = $e->retrieve_acq_picklist($li->picklist)
274 if($picklist->owner != $e->requestor->id) {
275 return $e->event unless
276 $e->allowed('VIEW_PICKLIST', undef, $picklist);
280 $li->clear_marc if $$options{clear_marc};
287 __PACKAGE__->register_method(
288 method => 'delete_lineitem',
289 api_name => 'open-ils.acq.lineitem.delete',
291 desc => 'Deletes a lineitem',
293 {desc => 'Authentication token', type => 'string'},
294 {desc => 'lineitem ID to delete', type => 'number'},
296 return => {desc => '1 on success, Event on error'}
300 sub delete_lineitem {
301 my($self, $conn, $auth, $li_id) = @_;
302 my $e = new_editor(xact=>1, authtoken=>$auth);
303 return $e->die_event unless $e->checkauth;
305 my $li = $e->retrieve_acq_lineitem($li_id)
306 or return $e->die_event;
311 my $picklist = $e->retrieve_acq_picklist($li->picklist)
312 or return $e->die_event;
313 return OpenILS::Event->new('BAD_PARAMS')
314 if $picklist->owner != $e->requestor->id;
319 # delete the attached lineitem_details
320 my $lid_ids = $e->search_acq_lineitem_detail(
321 {lineitem => $li_id}, {idlist=>1});
323 for my $lid_id (@$lid_ids) {
324 $e->delete_acq_lineitem_detail(
325 $e->retrieve_acq_lineitem_detail($lid_id))
326 or return $e->die_event;
329 $e->delete_acq_lineitem($li) or return $e->die_event;
335 __PACKAGE__->register_method(
336 method => 'update_lineitem',
337 api_name => 'open-ils.acq.lineitem.update',
339 desc => 'Update a lineitem',
341 {desc => 'Authentication token', type => 'string'},
342 {desc => 'lineitem object update', type => 'object'}
344 return => {desc => '1 on success, Event on error'}
348 sub update_lineitem {
349 my($self, $conn, $auth, $li) = @_;
350 my $e = new_editor(xact=>1, authtoken=>$auth);
351 return $e->die_event unless $e->checkauth;
353 my $orig_li = $e->retrieve_acq_lineitem([
355 { flesh => 1, # grab the lineitem with picklist attached
356 flesh_fields => {jub => ['picklist', 'purchase_order']}
358 ]) or return $e->die_event;
360 # the marc may have been cleared on retrieval...
361 $li->marc($e->retrieve_acq_lineitem($li->id)->marc)
364 $e->update_acq_lineitem($li) or return $e->die_event;
369 __PACKAGE__->register_method(
370 method => 'lineitem_search',
371 api_name => 'open-ils.acq.lineitem.search',
374 desc => 'Searches lineitems',
376 {desc => 'Authentication token', type => 'string'},
377 {desc => 'Search definition', type => 'object'},
378 {desc => 'Optoins hash. idlist=true', type => 'object'},
379 {desc => 'List of lineitems', type => 'object/number'},
384 sub lineitem_search {
385 my($self, $conn, $auth, $search, $options) = @_;
386 my $e = new_editor(authtoken=>$auth, xact=>1);
387 return $e->event unless $e->checkauth;
388 return $e->event unless $e->allowed('CREATE_PICKLIST');
389 # XXX needs permissions consideration
390 my $lis = $e->search_acq_lineitem($search, {idlist=>1});
391 for my $li_id (@$lis) {
392 if($$options{idlist}) {
393 $conn->respond($li_id);
395 my $res = retrieve_lineitem($self, $conn, $auth, $li_id, $options);
396 $conn->respond($res) unless $U->event_code($res);
403 __PACKAGE__->register_method(
404 method => 'lineitem_search_ident',
405 api_name => 'open-ils.acq.lineitem.search.ident',
408 desc => 'Performs a search against lineitem_attrs where ident is true',
410 {desc => 'Authentication token', type => 'string'},
411 { desc => q/Search definition. Options are:
412 attr_values : list of attribute values (required)
413 li_states : list of lineitem states
414 po_agencies : list of purchase order ordering agencies (org) ids
419 Options hash. Options are:
420 idlist : if set, only return lineitem IDs
421 clear_marc : if set, strip the MARC xml from the lineitem before delivery
422 flesh_attrs : flesh lineitem attributes;
430 my $LI_ATTR_SEARCH = {
431 select => {acqlia => ['lineitem']},
444 fkey => 'purchase_order'
452 sub lineitem_search_ident {
453 my($self, $conn, $auth, $search, $options) = @_;
454 my $e = new_editor(authtoken=>$auth, xact=>1);
455 return $e->event unless $e->checkauth;
456 # XXX needs permissions consideration
458 return [] unless $search;
459 my $attr_values = $search->{attr_values};
460 my $li_states = $search->{li_states};
461 my $po_agencies = $search->{po_agencies}; # XXX if none, base it on perms
466 '+acqliad' => {ident => 't'},
470 push(@{$where_clause->{'-or'}}, {attr_value => {ilike => "%$_%"}}) for @$attr_values;
472 $where_clause->{'+jub'} = {state => {in => $li_states}}
473 if $li_states and @$li_states;
475 $where_clause->{'+acqpo'} = {ordering_agency => $po_agencies}
476 if $po_agencies and @$po_agencies;
478 $LI_ATTR_SEARCH->{where} = $where_clause;
480 my $lis = $e->json_query($LI_ATTR_SEARCH);
482 for my $li_id_obj (@$lis) {
483 my $li_id = $li_id_obj->{lineitem};
484 if($$options{idlist}) {
485 $conn->respond($li_id);
488 if($$options{flesh_attrs}) {
489 $li = $e->retrieve_acq_lineitem([
490 $li_id, {flesh => 1, flesh_fields => {jub => ['attributes']}}])
492 $li = $e->retrieve_acq_lineitem($li_id);
494 $li->clear_marc if $$options{clear_marc};
502 __PACKAGE__->register_method(
503 method => 'create_lineitem_detail',
504 api_name => 'open-ils.acq.lineitem_detail.create',
506 desc => q/Creates a new purchase order line item detail.
507 Additionally creates the associated fund_debit/,
509 {desc => 'Authentication token', type => 'string'},
510 {desc => 'lineitem_detail to create', type => 'object'},
512 return => {desc => 'The purchase order line item detail id, Event on failure'}
516 sub create_lineitem_detail {
517 my($self, $conn, $auth, $li_detail, $options) = @_;
518 my $e = new_editor(xact=>1, authtoken=>$auth);
519 return $e->die_event unless $e->checkauth;
522 my $li = $e->retrieve_acq_lineitem($li_detail->lineitem)
523 or return $e->die_event;
525 my $evt = update_li_edit_time($e, $li);
528 # XXX check lineitem provider perms
530 if($li_detail->fund) {
531 my $fund = $e->retrieve_acq_fund($li_detail->fund) or return $e->die_event;
532 return $e->die_event unless
533 $e->allowed('MANAGE_FUND', $fund->org, $fund);
536 $e->create_acq_lineitem_detail($li_detail) or return $e->die_event;
538 unless($li_detail->barcode) {
539 my $pfx = $U->ou_ancestor_setting_value($li_detail->owning_lib, 'acq.tmp_barcode_prefix') || 'ACQ';
540 $li_detail->barcode($pfx.$li_detail->id);
542 unless($li_detail->cn_label) {
543 my $pfx = $U->ou_ancestor_setting_value($li_detail->owning_lib, 'acq.tmp_callnumber_prefix') || 'ACQ';
544 $li_detail->cn_label($pfx.$li_detail->id);
547 if(my $loc = $U->ou_ancestor_setting_value($li_detail->owning_lib, 'acq.default_copy_location')) {
548 $li_detail->location($loc);
551 $e->update_acq_lineitem_detail($li_detail) or return $e->die_event;
554 return $li_detail if $$options{return_obj};
555 return $li_detail->id
558 __PACKAGE__->register_method(
559 method => 'update_lineitem_detail',
560 api_name => 'open-ils.acq.lineitem_detail.update',
562 desc => q/Updates a lineitem detail/,
564 {desc => 'Authentication token', type => 'string'},
565 {desc => 'lineitem_detail to update', type => 'object'},
567 return => {desc => '1 on success, Event on failure'}
571 sub update_lineitem_detail {
572 my($self, $conn, $auth, $li_detail) = @_;
573 my $e = new_editor(xact=>1, authtoken=>$auth);
574 return $e->die_event unless $e->checkauth;
576 if($li_detail->fund) {
577 my $fund = $e->retrieve_acq_fund($li_detail->fund) or return $e->die_event;
578 return $e->die_event unless
579 $e->allowed('MANAGE_FUND', $fund->org, $fund);
582 # XXX check lineitem perms
584 my $li = $e->retrieve_acq_lineitem($li_detail->lineitem)
585 or return $e->die_event;
586 my $evt = update_li_edit_time($e, $li);
589 $e->update_acq_lineitem_detail($li_detail) or return $e->die_event;
594 sub update_li_edit_time {
596 # some lineitem edits are allowed after approval time...
597 # return OpenILS::Event->new('ACQ_LINEITEM_APPROVED', payload => $li->id)
598 # if $li->state eq 'approved';
599 $li->edit_time('now');
600 $e->update_acq_lineitem($li) or return $e->die_event;
605 __PACKAGE__->register_method(
606 method => 'delete_lineitem_detail',
607 api_name => 'open-ils.acq.lineitem_detail.delete',
609 desc => q/Deletes a lineitem detail/,
611 {desc => 'Authentication token', type => 'string'},
612 {desc => 'lineitem_detail ID to delete', type => 'number'},
614 return => {desc => '1 on success, Event on failure'}
618 sub delete_lineitem_detail {
619 my($self, $conn, $auth, $li_detail_id) = @_;
620 my $e = new_editor(xact=>1, authtoken=>$auth);
621 return $e->die_event unless $e->checkauth;
622 my $li_detail = $e->retrieve_acq_lineitem_detail([
625 flesh_fields => {acqlid => ['lineitem']}
627 ]) or return $e->die_event;
629 my $li = $li_detail->lineitem;
631 my $evt = update_li_edit_time($e, $li);
634 return OpenILS::Event->new('BAD_PARAMS') unless
635 $li->state =~ /new|approved/;
637 # XXX check lineitem perms
639 $e->delete_acq_lineitem_detail($li_detail) or return $e->die_event;
645 __PACKAGE__->register_method(
646 method => 'retrieve_lineitem_detail',
647 api_name => 'open-ils.acq.lineitem_detail.retrieve',
649 desc => q/Updates a lineitem detail/,
651 {desc => 'Authentication token', type => 'string'},
652 {desc => 'id of lineitem_detail to retrieve', type => 'number'},
654 return => {desc => 'object on success, Event on failure'}
657 sub retrieve_lineitem_detail {
658 my($self, $conn, $auth, $li_detail_id) = @_;
659 my $e = new_editor(authtoken=>$auth);
660 return $e->event unless $e->checkauth;
662 my $li_detail = $e->retrieve_acq_lineitem_detail($li_detail_id)
665 if($li_detail->fund) {
666 my $fund = $e->retrieve_acq_fund($li_detail->fund) or return $e->event;
667 return $e->event unless
668 $e->allowed('MANAGE_FUND', $fund->org, $fund);
671 # XXX check lineitem perms
677 __PACKAGE__->register_method(
678 method => 'approve_lineitem',
679 api_name => 'open-ils.acq.lineitem.approve',
681 desc => 'Mark a lineitem as approved',
683 {desc => 'Authentication token', type => 'string'},
684 {desc => 'lineitem ID', type => 'number'}
686 return => {desc => '1 on success, Event on error'}
689 sub approve_lineitem {
690 my($self, $conn, $auth, $li_id) = @_;
691 my $e = new_editor(xact=>1, authtoken=>$auth);
692 return $e->die_event unless $e->checkauth;
694 # XXX perm checks for each lineitem detail
696 my $li = $e->retrieve_acq_lineitem($li_id)
697 or return $e->die_event;
699 return OpenILS::Event->new('ACQ_LINEITEM_APPROVED', payload => $li_id)
700 if $li->state eq 'approved';
702 my $details = $e->search_acq_lineitem_detail({lineitem => $li_id});
703 return OpenILS::Event->new('ACQ_LINEITEM_NO_COPIES', payload => $li_id)
704 unless scalar(@$details) > 0;
706 for my $detail (@$details) {
707 return OpenILS::Event->new('ACQ_LINEITEM_DETAIL_NO_FUND', payload => $detail->id)
708 unless $detail->fund;
710 return OpenILS::Event->new('ACQ_LINEITEM_DETAIL_NO_ORG', payload => $detail->id)
711 unless $detail->owning_lib;
714 $li->state('approved');
715 $li->edit_time('now');
716 $e->update_acq_lineitem($li) or return $e->die_event;
723 __PACKAGE__->register_method(
724 method => 'receive_lineitem_detail',
725 api_name => 'open-ils.acq.lineitem_detail.receive',
727 desc => 'Mark a lineitem_detail as received',
729 {desc => 'Authentication token', type => 'string'},
730 {desc => 'lineitem detail ID', type => 'number'}
732 return => {desc => '1 on success, Event on error'}
735 sub receive_lineitem_detail {
736 my($self, $conn, $auth, $lid_id) = @_;
737 my $e = new_editor(xact=>1, authtoken=>$auth);
738 return $e->die_event unless $e->checkauth;
739 my $resp = receive_lineitem_detail_impl($e, $lid_id);
740 if($resp) {$e->rollback; return $resp;}
745 sub receive_lineitem_detail_impl {
746 my($e, $lid_id) = @_;
748 my $lid = $e->retrieve_acq_lineitem_detail([
752 acqlid => ['fund_debit']
755 ]) or return $e->die_event;
757 return OpenILS::Event->new(
758 'ACQ_LINEITEM_DETAIL_RECEIVED') if $lid->recv_time;
760 $lid->recv_time('now');
761 $e->update_acq_lineitem_detail($lid) or return $e->die_event;
763 my $copy = $e->retrieve_asset_copy($lid->eg_copy_id)
764 or return $e->die_event;
766 $copy->status(OILS_COPY_STATUS_IN_PROCESS);
767 $copy->edit_date('now');
768 $copy->editor($e->requestor->id);
769 $e->update_asset_copy($copy) or return $e->die_event;
771 if($lid->fund_debit) {
772 $lid->fund_debit->encumbrance('f');
773 $e->update_acq_fund_debit($lid->fund_debit) or return $e->die_event;
776 # -------------------------------------------------------------
777 # if all of the lineitem details for this lineitem have
778 # been received, mark the lineitem as received
779 # -------------------------------------------------------------
780 my $non_recv = $e->search_acq_lineitem_detail(
781 {recv_time => undef, lineitem => $lid->lineitem}, {idlist=>1});
783 return undef if @$non_recv;
785 my $li = $e->retrieve_acq_lineitem($lid->lineitem);
786 $li->state('received');
787 $li->edit_time('now');
788 $e->update_acq_lineitem($li) or return $e->die_event;
790 # -------------------------------------------------------------
791 # if all of the lineitems for this PO are received,
792 # mark the PO as received
793 # -------------------------------------------------------------
794 my $non_recv_li = $e->search_acq_lineitem(
795 { purchase_order => $li->purchase_order,
796 state => {'!=' => 'received'}
799 return undef if @$non_recv_li;
801 my $po = $e->retrieve_acq_purchase_order($li->purchase_order);
802 $po->state('received');
803 $po->edit_time('now');
804 $e->update_acq_purchase_order($po) or return $e->die_event;
810 __PACKAGE__->register_method(
811 method => 'set_lineitem_attr',
812 api_name => 'open-ils.acq.lineitem_usr_attr.set',
814 desc => 'Sets a lineitem_usr_attr value',
816 {desc => 'Authentication token', type => 'string'},
817 {desc => 'Lineitem ID', type => 'number'},
818 {desc => 'Attr name', type => 'string'},
819 {desc => 'Attr value', type => 'string'}
821 return => {desc => '1 on success, Event on error'}
825 __PACKAGE__->register_method(
826 method => 'set_lineitem_attr',
827 api_name => 'open-ils.acq.lineitem_local_attr.set',
829 desc => 'Sets a lineitem_local_attr value',
831 {desc => 'Authentication token', type => 'string'},
832 {desc => 'Lineitem ID', type => 'number'},
833 {desc => 'Attr name', type => 'string'},
834 {desc => 'Attr value', type => 'string'}
836 return => {desc => 'ID of the attr object on success, Event on error'}
841 sub set_lineitem_attr {
842 my($self, $conn, $auth, $li_id, $attr_name, $attr_value) = @_;
843 my $e = new_editor(xact=>1, authtoken=>$auth);
844 return $e->die_event unless $e->checkauth;
848 my $attr_type = $self->api_name =~ /local_attr/ ?
849 'lineitem_local_attr_definition' : 'lineitem_usr_attr_definition';
851 my $attr = $e->search_acq_lineitem_attr({
853 attr_type => $attr_type,
854 attr_name => $attr_name})->[0];
856 my $find = "search_acq_$attr_type";
859 $attr->attr_value($attr_value);
860 $e->update_acq_lineitem_attr($attr) or return $e->die_event;
862 $attr = Fieldmapper::acq::lineitem_attr->new;
863 $attr->lineitem($li_id);
864 $attr->attr_type($attr_type);
865 $attr->attr_name($attr_name);
866 $attr->attr_value($attr_value);
868 my $attr_def_id = $e->$find({code => $attr_name}, {idlist=>1})->[0]
869 or return $e->die_event;
870 $attr->definition($attr_def_id);
871 $e->create_acq_lineitem_attr($attr) or return $e->die_event;
878 __PACKAGE__->register_method(
879 method => 'get_lineitem_attr_defs',
880 api_name => 'open-ils.acq.lineitem_attr_definition.retrieve.all',
882 desc => 'Retrieve lineitem attr definitions',
884 {desc => 'Authentication token', type => 'string'},
886 return => {desc => 'List of attr definitions'}
890 sub get_lineitem_attr_defs {
891 my($self, $conn, $auth) = @_;
892 my $e = new_editor(authtoken=>$auth);
893 return $e->event unless $e->checkauth;
895 for my $type (qw/generated marc local usr provider/) {
896 my $call = "retrieve_all_acq_lineitem_${type}_attr_definition";
897 $results{$type} = $e->$call;