Bugzilla – Attachment 136267 Details for
Bug 28854
Add ability to create bundles of items for circulation
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Help
|
New Account
|
Log In
[x]
|
Forgot Password
Login:
[x]
[patch]
Bug 28854: Update circulation functionality for bundles
Bug-28854-Update-circulation-functionality-for-bun.patch (text/plain), 23.79 KB, created by
Martin Renvoize (ashimema)
on 2022-06-17 13:40:19 UTC
(
hide
)
Description:
Bug 28854: Update circulation functionality for bundles
Filename:
MIME Type:
Creator:
Martin Renvoize (ashimema)
Created:
2022-06-17 13:40:19 UTC
Size:
23.79 KB
patch
obsolete
>From c81f46a61b941bae222f8ab290704de74a7e8e43 Mon Sep 17 00:00:00 2001 >From: Martin Renvoize <martin.renvoize@ptfs-europe.com> >Date: Thu, 23 Sep 2021 11:37:52 +0100 >Subject: [PATCH] Bug 28854: Update circulation functionality for bundles > >This patch updates the circulation system to account for bundle >checkins. We add a content verification step to ensure bundle content is >all present at checkin and we use this comparison to mark missing items >as lost. > >Test plan >0) Apply patches up to this point >1) Checkin an item that belongs to a bundle > * An alert should be triggered noting that the item belongs to a > bundle > * The option to remove the item from the bundle should be clear > * Click remove should result in the alert dissapearing and the item > having been removed from the bundle. >2) Checkin an item bundle > * A modal confirmation dialog should appear requesting each item > barcode be scanned > * As items are scanned they should be highlighted in yellow in the > bundle content table > * Upon submission; > * The user will be alerted to any unexpected items that were > scanned and told to put them to one side. > * The user will be alerted that any missing items in the validation > will have been marked as lost. > * The bundle item will be marked as checked in. >--- > C4/Circulation.pm | 6 + > circ/returns.pl | 58 +++++++- > .../intranet-tmpl/prog/css/src/_tables.scss | 2 +- > .../prog/en/includes/item-status.inc | 84 +++++++++++ > .../en/includes/modals/bundle_contents.inc | 35 +++++ > .../admin/preferences/circulation.pref | 4 + > .../prog/en/modules/circ/returns.tt | 134 ++++++++++++++++++ > 7 files changed, 320 insertions(+), 3 deletions(-) > create mode 100644 koha-tmpl/intranet-tmpl/prog/en/includes/item-status.inc > create mode 100644 koha-tmpl/intranet-tmpl/prog/en/includes/modals/bundle_contents.inc > >diff --git a/C4/Circulation.pm b/C4/Circulation.pm >index f5df973d1d..4c9779a491 100644 >--- a/C4/Circulation.pm >+++ b/C4/Circulation.pm >@@ -2433,6 +2433,12 @@ sub AddReturn { > } > } > >+ # Check for bundle status >+ if ( $item->in_bundle ) { >+ my $host = $item->bundle_host; >+ $messages->{InBundle} = $host; >+ } >+ > my $indexer = Koha::SearchEngine::Indexer->new({ index => $Koha::SearchEngine::BIBLIOS_INDEX }); > $indexer->index_records( $item->biblionumber, "specialUpdate", "biblioserver" ); > >diff --git a/circ/returns.pl b/circ/returns.pl >index 340efb4779..52df948d14 100755 >--- a/circ/returns.pl >+++ b/circ/returns.pl >@@ -338,10 +338,18 @@ if ($barcode) { > $template->param( 'multiple_confirmed' => 1 ) > if $query->param('multiple_confirm'); > >+ # Block return if bundle and confirm has not been received >+ my $bundle_confirm = >+ $item >+ && $item->is_bundle >+ && !$query->param('confirm_items_bundle_return'); >+ $template->param( 'confirm_items_bundle_returned' => 1 ) >+ if $query->param('confirm_items_bundle_return'); >+ > # do the return > ( $returned, $messages, $issue, $borrower ) = > AddReturn( $barcode, $userenv_branch, $exemptfine, $return_date ) >- unless $needs_confirm; >+ unless ( $needs_confirm || $bundle_confirm ); > > if ($returned) { > my $time_now = dt_from_string()->truncate( to => 'minute'); >@@ -382,7 +390,45 @@ if ($barcode) { > ); > } > } >- } elsif ( C4::Context->preference('ShowAllCheckins') and !$messages->{'BadBarcode'} and !$needs_confirm ) { >+ >+ # Mark missing bundle items as lost and report unexpected items >+ if ( $item->is_bundle ) { >+ my $BundleLostValue = C4::Context->preference('BundleLostValue'); >+ my $barcodes = $query->param('verify-items-bundle-contents-barcodes'); >+ my @barcodes = map { s/^\s+|\s+$//gr } ( split /\n/, $barcodes ); >+ my $expected_items = { map { $_->barcode => $_ } $item->bundle_items->as_list }; >+ my $verify_items = Koha::Items->search( { barcode => { 'in' => \@barcodes } } ); >+ my @unexpected_items; >+ my @missing_items; >+ my @bundle_items; >+ while ( my $verify_item = $verify_items->next ) { >+ # Fix and lost statuses >+ $verify_item->itemlost(0); >+ >+ # Expected item, remove from lookup table >+ if ( delete $expected_items->{$verify_item->barcode} ) { >+ push @bundle_items, $verify_item; >+ } >+ # Unexpected item, warn and remove from bundle >+ else { >+ $verify_item->remove_from_bundle; >+ push @unexpected_items, $verify_item; >+ } >+ # Store results >+ $verify_item->store(); >+ } >+ for my $missing_item ( keys %{$expected_items} ) { >+ my $bundle_item = $expected_items->{$missing_item}; >+ $bundle_item->itemlost($BundleLostValue)->store(); >+ push @missing_items, $bundle_item; >+ } >+ $template->param( >+ unexpected_items => \@unexpected_items, >+ missing_items => \@missing_items, >+ bundle_items => \@bundle_items >+ ); >+ } >+ } elsif ( C4::Context->preference('ShowAllCheckins') and !$messages->{'BadBarcode'} and !$needs_confirm and !$bundle_confirm ) { > $input{duedate} = 0; > $returneditems{0} = $barcode; > $riduedate{0} = 0; >@@ -393,6 +439,12 @@ if ($barcode) { > if ( $needs_confirm ) { > $template->param( needs_confirm => $needs_confirm ); > } >+ >+ if ( $bundle_confirm ) { >+ $template->param( >+ items_bundle_return_confirmation => 1, >+ ); >+ } > } > $template->param( inputloop => \@inputloop ); > >@@ -631,6 +683,8 @@ foreach my $code ( keys %$messages ) { > ; > } elsif ( $code eq 'TransferredRecall' ) { > ; >+ } elsif ( $code eq 'InBundle' ) { >+ $template->param( InBundle => $messages->{InBundle} ); > } else { > die "Unknown error code $code"; # note we need all the (empty) elsif's above, or we die. > # This forces the issue of staying in sync w/ Circulation.pm >diff --git a/koha-tmpl/intranet-tmpl/prog/css/src/_tables.scss b/koha-tmpl/intranet-tmpl/prog/css/src/_tables.scss >index 6f483a9e30..a62600d96f 100644 >--- a/koha-tmpl/intranet-tmpl/prog/css/src/_tables.scss >+++ b/koha-tmpl/intranet-tmpl/prog/css/src/_tables.scss >@@ -359,7 +359,7 @@ tbody { > border-right: 1px solid $table-border-color; > } > } >- &:nth-child(odd):not(.dtrg-group):not(.active) { >+ &:nth-child(odd):not(.dtrg-group):not(.active):not(.ok) { > td { > &:not(.bg-danger):not(.bg-warning):not(.bg-info):not(.bg-success):not(.bg-primary) { > background-color: $table-odd-row; >diff --git a/koha-tmpl/intranet-tmpl/prog/en/includes/item-status.inc b/koha-tmpl/intranet-tmpl/prog/en/includes/item-status.inc >new file mode 100644 >index 0000000000..ca6dc1d1ff >--- /dev/null >+++ b/koha-tmpl/intranet-tmpl/prog/en/includes/item-status.inc >@@ -0,0 +1,84 @@ >+[% USE AuthorisedValues %] >+[% USE Branches %] >+[% USE Koha %] >+[% USE KohaDates %] >+[% PROCESS 'i18n.inc' %] >+[% transfer = item.get_transfer() %] >+[% IF item.checkout %] >+ <span class="datedue"> >+ [% IF item.checkout.onsite_checkout %] >+ [% t('Currently in local use by') | html %] >+ [% ELSE %] >+ [% t('Checked out to') | html %] >+ [% END %] >+ [% INCLUDE 'patron-title.inc' patron=item.checkout.patron hide_patron_infos_if_needed=1 %] >+ : [% tx('due {date_due}', { date_due = item.checkout.date_due }) | html %] >+ </span> >+[% ELSIF transfer %] >+ [% datesent = BLOCK %][% transfer.datesent | $KohaDates %][% END %] >+ <span class="intransit">[% tx('In transit from {frombranch} to {tobranch} since {datesent}', { frombranch = Branches.GetName(transfer.frombranch), tobranch = Branches.GetName(transfer.tobranch), datesent = datesent }) %]</span> >+[% END %] >+ >+[% IF item.itemlost %] >+ [% itemlost_description = AuthorisedValues.GetDescriptionByKohaField({ kohafield = 'items.itemlost', authorised_value = item.itemlost }) %] >+ [% IF itemlost_description %] >+ <span class="lost">[% itemlost_description | html %]</span> >+ [% ELSE %] >+ <span class="lost">[% t('Unavailable (lost or missing)') | html %]</span> >+ [% END %] >+[% END %] >+ >+[% IF item.withdrawn %] >+ [% withdrawn_description = AuthorisedValues.GetDescriptionByKohaField({ kohafield = 'items.withdrawn', authorised_value = item.withdrawn }) %] >+ [% IF withdrawn_description %] >+ <span class="wdn">[% withdrawn_description | html %]</span> >+ [% ELSE %] >+ <span class="wdn">[% t('Withdrawn') | html %]</span> >+ [% END %] >+[% END %] >+ >+[% IF item.damaged %] >+ [% damaged_description = AuthorisedValues.GetDescriptionByKohaField({ kohafield = 'items.damaged', authorised_value = item.damaged }) %] >+ [% IF damaged_description %] >+ <span class="dmg">[% damaged_description | html %]</span> >+ [% ELSE %] >+ <span class="dmg">[% t('Damaged') | html %]</span> >+ [% END %] >+[% END %] >+ >+[% IF item.notforloan || item.effective_itemtype.notforloan %] >+ <span> >+ [% t('Not for loan') | html %] >+ [% notforloan_description = AuthorisedValues.GetDescriptionByKohaField({ kohafield = 'items.notforloan', authorised_value = item.notforloan }) %] >+ [% IF notforloan_description %] >+ ([% notforloan_description | html %]) >+ [% END %] >+ </span> >+[% END %] >+ >+[% hold = item.holds.next %] >+[% IF hold %] >+ <span> >+ [% IF hold.waitingdate %] >+ Waiting at [% Branches.GetName(hold.get_column('branchcode')) | html %] since [% hold.waitingdate | $KohaDates %]. >+ [% ELSE %] >+ Item-level hold (placed [% hold.reservedate | $KohaDates %]) for delivery at [% Branches.GetName(hold.get_column('branchcode')) | html %]. >+ [% END %] >+ [% IF Koha.Preference('canreservefromotherbranches') %] >+ [% t('Hold for:') | html %] >+ [% INCLUDE 'patron-title.inc' patron=hold.borrower hide_patron_infos_if_needed=1 %] >+ [% END %] >+ </span> >+[% END %] >+[% UNLESS item.notforloan || item.effective_itemtype.notforloan || item.onloan || item.itemlost || item.withdrawn || item.damaged || transfer || hold %] >+ <span>[% t('Available') | html %]</span> >+[% END %] >+ >+[% IF ( item.restricted ) %] >+ [% restricted_description = AuthorisedValues.GetDescriptionByKohaField({ kohafield = 'items.restricted', authorised_value = item.restricted }) %] >+ [% IF restricted_description %] >+ <span class="restricted">([% restricted_description | html %])</span> >+ [% ELSE %] >+ <span class="restricted">[% t('Restricted') | html %]</span> >+ [% END %] >+[% END %] >diff --git a/koha-tmpl/intranet-tmpl/prog/en/includes/modals/bundle_contents.inc b/koha-tmpl/intranet-tmpl/prog/en/includes/modals/bundle_contents.inc >new file mode 100644 >index 0000000000..fe0041923c >--- /dev/null >+++ b/koha-tmpl/intranet-tmpl/prog/en/includes/modals/bundle_contents.inc >@@ -0,0 +1,35 @@ >+<!-- Bundle contents modal --> >+<div class="modal printable" id="bundleContentsModal" tabindex="-1" role="dialog" aria-labelledby="bundleContentsLabel"> >+ <div class="modal-dialog" role="document"> >+ <div class="modal-content"> >+ <div class="modal-header"> >+ <button type="button" class="closebtn" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">×</span></button> >+ <h4 class="modal-title" id="bundleContentsLabel">Bundle contents for [% item.barcode | html %]</h4> >+ </div> >+ <div class="modal-body"> >+ <table style="width:100%"> >+ <thead> >+ <tr> >+ <th>Barcode</th> >+ <th>Title</th> >+ </tr> >+ </thead> >+ <tbody> >+ [% FOREACH bundle_item IN bundle_items %] >+ <tr> >+ <td>[% bundle_item.barcode | html %]</td> >+ <td>[% INCLUDE 'biblio-title.inc' biblio=bundle_item.biblio %]</td> >+ </tr> >+ [% END %] >+ </tbody> >+ <tfoot> >+ </tfoot> >+ </table> >+ </div> <!-- /.modal-body --> >+ <div class="modal-footer"> >+ <button type="button" class="btn btn-default" data-dismiss="modal">Close</button> >+ <button type="button" class="printModal btn btn-primary"><i class="fa fa-print"></i> Print</button> >+ </div> <!-- /.modal-footer --> >+ </div> <!-- /.modal-content --> >+ </div> <!-- /.modal-dialog --> >+</div> <!-- /#bundleContentsModal --> >diff --git a/koha-tmpl/intranet-tmpl/prog/en/modules/admin/preferences/circulation.pref b/koha-tmpl/intranet-tmpl/prog/en/modules/admin/preferences/circulation.pref >index bc3520c731..bc53efc0d8 100644 >--- a/koha-tmpl/intranet-tmpl/prog/en/modules/admin/preferences/circulation.pref >+++ b/koha-tmpl/intranet-tmpl/prog/en/modules/admin/preferences/circulation.pref >@@ -12,6 +12,10 @@ Circulation: > 1: "Require" > 0: "Don't require" > - staff to confirm that all parts of an item are present at checkin/checkout. >+ - >+ - Use the LOST authorised value >+ - pref: BundleLostValue >+ - to represent 'missing from bundle' at return. > - > - pref: AutoSwitchPatron > choices: >diff --git a/koha-tmpl/intranet-tmpl/prog/en/modules/circ/returns.tt b/koha-tmpl/intranet-tmpl/prog/en/modules/circ/returns.tt >index ab184328ea..9d95939065 100644 >--- a/koha-tmpl/intranet-tmpl/prog/en/modules/circ/returns.tt >+++ b/koha-tmpl/intranet-tmpl/prog/en/modules/circ/returns.tt >@@ -6,6 +6,7 @@ > [% USE ItemTypes %] > [% USE AuthorisedValues %] > [% USE TablesSettings %] >+[% PROCESS 'i18n.inc' %] > [% PROCESS 'member-display-address-style.inc' %] > [% SET footerjs = 1 %] > [% BLOCK display_bormessagepref %] >@@ -217,6 +218,36 @@ > </div> > [% END %] > >+ <!-- Bundle has items missing --> >+ [% IF missing_items %] >+ <div id="bundle_missing_items" class="dialog alert"> >+ <h3>Bundle had missing items</h3> >+ <p>Bundle contents list updated</p> >+ <p><a class="btn btn-default btn-xs" role="button" data-toggle="modal" href="#bundleContentsModal"><i class="fa fa-eye" aria-hidden="true"></i> View updated contents list</a></p> >+ </div> >+ [% END %] >+ >+ <!-- Bundle contained unexpected items --> >+ [% IF unexpected_items %] >+ <div id="bundle_unexpected_items" class="dialog alert"> >+ <h3>Bundle had unexpected items</h3> >+ <p>Please place the following items to one side</p> >+ <ul> >+ [% FOREACH unexpected_item IN unexpected_items %] >+ <li>[% INCLUDE 'biblio-title.inc' biblio=unexpected_item.biblio %] - [% unexpected_item.barcode | html %]</li> >+ [% END %] >+ </ul> >+ </div> >+ [% END %] >+ >+ <!-- Item checked in outside of bundle --> >+ [% IF InBundle %] >+ <div id="bundle_item_outside" class="dialog alert audio-alert-warning"> >+ <h3>Item belongs in bundle</h3> >+ <p>This item belongs to a bundle: [% INCLUDE 'biblio-title.inc' biblio=InBundle.biblio %] - [% InBundle.barcode | html %]</p> >+ <p><button class="btn btn-default btn-xs bundle_remove" role="button" data-itemnumber="[% itemnumber | uri %]" data-hostnumber="[% InBundle.itemnumber | uri %]"><i class="fa fa-minus"></i> Remove from bundle</button></p> >+ </div> >+ [% END %] > > [% IF ( errmsgloop ) %] > <div class="dialog alert audio-alert-warning"> >@@ -381,6 +412,63 @@ > </div> > [% END %] > >+ [% IF items_bundle_return_confirmation %] >+ <div id="bundle-needsconfirmation-modal" class="modal fade audio-alert-action block"> >+ <div class="modal-dialog modal-wide"> >+ <div class="modal-content"> >+ <form method="post"> >+ <div class="modal-header"> >+ <h3>Please confirm bundle contents</h3> >+ </div> >+ <div class="modal-body"> >+ >+ <table class="table table-condensed table-bordered" id="items-bundle-contents-table"> >+ <thead> >+ <tr> >+ <th>[% t('Title') | html %]</th> >+ <th>[% t('Author') | html %]</th> >+ <th>[% t('Item type') | html %]</th> >+ <th>[% t('Barcode') | html %]</th> >+ <th>[% t('Status') | html %]</th> >+ </tr> >+ </thead> >+ <tbody> >+ [% FOREACH bundle_item IN item.bundle_items %] >+ <tr data-barcode="[% bundle_item.barcode | html %]"> >+ <td>[% INCLUDE 'biblio-title.inc' biblio=bundle_item.biblio link = 1 %]</td> >+ <td>[% bundle_item.biblio.author | html %]</td> >+ <td>[% ItemTypes.GetDescription(bundle_item.itype) | html %]</td> >+ <td>[% bundle_item.barcode | html %]</td> >+ <td>[% INCLUDE 'item-status.inc' item=bundle_item %]</td> >+ </tr> >+ [% END %] >+ </tbody> >+ </table> >+ >+ <div class="form-group"> >+ <label for="verify-items-bundle-contents-barcodes">Barcodes</label> >+ <textarea autocomplete="off" id="verify-items-bundle-contents-barcodes" name="verify-items-bundle-contents-barcodes" class="form-control"></textarea> >+ <div class="help-block">[% t('Scan all barcodes of items found in the items bundle. If any items are missing, they will be marked as lost') | html %]</div> >+ </div> >+ >+ </div> >+ <div class="modal-footer"> >+ <input type="hidden" name="barcode" value="[% item.barcode | html %]"> >+ <input type="hidden" name="confirm_items_bundle_return" value="1"> >+ [% FOREACH inputloo IN inputloop %] >+ <input type="hidden" name="ri-[% inputloo.counter | html %]" value="[% inputloo.barcode | html %]" /> >+ <input type="hidden" name="dd-[% inputloo.counter | html %]" value="[% inputloo.duedate | html %]" /> >+ <input type="hidden" name="bn-[% inputloo.counter | html %]" value="[% inputloo.borrowernumber | html %]" /> >+ [% END %] >+ <button type="submit" class="btn btn-default"><i class="fa fa-check"></i> [% t('Confirm checkin and mark missing items as lost') | html %]</button> >+ <button type="button" data-dismiss="modal" class="btn btn-default"><i class="fa fa-close"></i> [% t('Cancel') | html %]</button> >+ </div> >+ </form> >+ </div> >+ </div> >+ </div> >+ [% END %] >+ > [% IF wrongbranch %] > <div id="wrong-branch-modal" class="modal fade audio-alert-action block"> > <div class="modal-dialog"> >@@ -1180,6 +1268,8 @@ > [% INCLUDE 'modals/resolve_return_claim.inc' %] > [% END %] > >+ [% INCLUDE 'modals/bundle_contents.inc' %] >+ > [% MACRO jsinclude BLOCK %] > [% INCLUDE 'datatables.inc' %] > [% INCLUDE 'columns_settings.inc' %] >@@ -1364,8 +1454,52 @@ > window.open("/cgi-bin/koha/members/printslip.pl?borrowernumber=" + borrowernumber + "&print=checkinslip", "printwindow"); > }); > >+ // item bundles >+ $('#verify-items-bundle-contents-barcodes').on('input', function (ev) { >+ const barcodes = ev.target.value.split('\n').map(function(s) { return s.trim() }); >+ $('#items-bundle-contents-table tr').each(function () { >+ const barcode = this.getAttribute('data-barcode'); >+ if (barcodes.includes(barcode)) { >+ this.classList.add('ok'); >+ } else { >+ this.classList.remove('ok'); >+ } >+ }) >+ }); >+ >+ $('.bundle_remove').on('click', function() { >+ var component_itemnumber = $(this).data('itemnumber'); >+ var host_itemnumber = $(this).data('hostnumber'); >+ var alert = $(this).closest('div'); >+ var unlink_item_url = "/api/v1/items/" + host_itemnumber + "/bundled_items/item/" + component_itemnumber; >+ $.ajax({ >+ type: "DELETE", >+ url: unlink_item_url, >+ success: function(){ >+ alert.remove(); >+ } >+ }); >+ }); >+ >+ // print modals >+ $('.modal.printable').on('shown.bs.modal', function() { >+ $('.modal-dialog', this).addClass('focused'); >+ $('body').addClass('modalprinter'); >+ >+ if ($(this).hasClass('autoprint')) { >+ window.print(); >+ } >+ }).on('hidden.bs.modal', function() { >+ $('.modal-dialog', this).removeClass('focused'); >+ $('body').removeClass('modalprinter'); >+ }); >+ >+ $('.printModal').click(function() { >+ window.print(); >+ }); > }); > </script> >+ > [% END %] > > [% INCLUDE 'intranet-bottom.inc' %] >-- >2.20.1
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
|
Splinter Review
Attachments on
bug 28854
:
124319
|
124498
|
124616
|
125200
|
125201
|
125202
|
125203
|
125204
|
125205
|
125206
|
126103
|
126104
|
126105
|
126106
|
126107
|
126108
|
126109
|
126110
|
126148
|
126149
|
126150
|
126151
|
126152
|
126153
|
126154
|
126155
|
126166
|
126167
|
126168
|
126169
|
126170
|
126171
|
126172
|
126173
|
127498
|
127499
|
127500
|
127501
|
127502
|
127503
|
127504
|
127505
|
127659
|
127660
|
127661
|
127662
|
127663
|
127664
|
127665
|
127666
|
127829
|
127830
|
127831
|
127832
|
127833
|
127834
|
127835
|
127836
|
127837
|
127838
|
130313
|
130314
|
130315
|
130316
|
130317
|
130318
|
130319
|
130320
|
130321
|
130322
|
130323
|
130324
|
130325
|
130326
|
130327
|
130328
|
130329
|
130330
|
130331
|
130332
|
130456
|
132703
|
132704
|
132705
|
132706
|
132707
|
132708
|
132709
|
132710
|
132711
|
132712
|
132713
|
132714
|
132715
|
132716
|
132717
|
132718
|
132719
|
132720
|
132721
|
132722
|
132723
|
135019
|
135020
|
135021
|
135022
|
135023
|
135024
|
135025
|
135026
|
135027
|
135028
|
135029
|
135030
|
135031
|
135032
|
135033
|
135034
|
135035
|
135036
|
135037
|
136226
|
136227
|
136228
|
136229
|
136230
|
136231
|
136232
|
136233
|
136234
|
136235
|
136236
|
136237
|
136238
|
136239
|
136240
|
136241
|
136242
|
136243
|
136244
|
136249
|
136253
|
136254
|
136264
|
136265
|
136266
|
136267
|
136268
|
136269
|
136270
|
136271
|
136272
|
136273
|
136274
|
136275
|
136276
|
136277
|
136278
|
136279
|
136280
|
136281
|
136282
|
136283
|
136284
|
136285
|
136287
|
136340
|
136341
|
136342
|
136343
|
136344
|
136345
|
136346
|
136347
|
136348
|
136349
|
136350
|
136351
|
136352
|
136353
|
136354
|
136355
|
136356
|
136357
|
136358
|
136359
|
136360
|
136361
|
136362
|
136363
|
136364
|
136365
|
136366
|
136367
|
136368
|
136369
|
136370
|
136371
|
136498
|
136529
|
136530
|
136613
|
136614
|
136615
|
136616
|
136617
|
136618
|
136619
|
136620
|
136621
|
136622
|
136623
|
136624
|
136625
|
136626
|
136627
|
136628
|
136629
|
136630
|
136631
|
136632
|
136633
|
136634
|
136635
|
136636
|
136637
|
136638
|
136639
|
136640
|
136641
|
136642
|
136643
|
136644
|
136645
|
136646
|
136647
|
136648
|
136649
|
136650
|
136651
|
136652
|
136654
|
136655
|
136806
|
136809
|
136811
|
136814
|
136817
|
136821
|
136824
|
136826
|
136829
|
136832
|
136835
|
136838
|
136841
|
136843
|
136846
|
136849
|
136850
|
136851
|
136852
|
136853
|
136854
|
136855
|
136856
|
136857
|
136858
|
136859
|
136860
|
136861
|
136862
|
136863
|
136864
|
136865
|
136866
|
136867
|
136868
|
136869
|
136870
|
136871
|
136872
|
136873
|
136874
|
136875
|
136876
|
136877
|
136905
|
136906
|
136907
|
136908
|
136909
|
136910
|
136911
|
136912
|
136913
|
136914
|
136915
|
136916
|
136917
|
136918
|
136919
|
136920
|
136921
|
136922
|
136923
|
136924
|
136925
|
136926
|
136927
|
136928
|
136929
|
136930
|
136931
|
136932
|
136933
|
136934
|
136935
|
136936
|
136937
|
136938
|
136939
|
136940
|
136941
|
136942
|
136943
|
136944
|
136945
|
136946
|
136947
|
136949
|
136978
|
136979
|
136980
|
136981
|
136982
|
136985
|
136988
|
136989
|
136990
|
136991
|
136992
|
136993
|
136994
|
136995
|
136996
|
136997
|
136998
|
136999
|
137000
|
137001
|
137002
|
137003
|
137004
|
137005
|
137006
|
137007
|
137008
|
137009
|
137010
|
137011
|
137012
|
137013
|
137014
|
137015
|
137016
|
137017
|
137018
|
137019
|
137020
|
137021
|
137022
|
137461
|
137462
|
137463
|
137464
|
137465
|
137466
|
137467
|
137468
|
137469
|
137470
|
137471
|
137472
|
137473
|
137474
|
137475
|
137476
|
137477
|
137478
|
137479
|
137480
|
137481
|
137482
|
137483
|
137484
|
137485
|
137486
|
137487
|
137488
|
137489
|
137490
|
137491
|
137492
|
137493
|
137494
|
137495
|
137496
|
137497
|
137498
|
137499
|
137500
|
137501
|
137503
|
137506
|
137524
|
137525
|
137527
|
137528
|
137529
|
137530
|
137531
|
137532
|
137533
|
137534
|
137535
|
137536
|
137537
|
137538
|
137540
|
137541
|
137542
|
137543
|
137544
|
137545
|
137546
|
137547
|
137548
|
137549
|
137550
|
137551
|
137552
|
137553
|
137554
|
137555
|
137556
|
137557
|
137558
|
137559
|
137560
|
137561
|
137562
|
137563
|
137564
|
137565
|
137566
|
137567
|
137568
|
137569
|
137570
|
137571
|
137684
|
137685
|
139347