|
Lines 698-700
$(document).ready(function () {
Link Here
|
| 698 |
return toggle_suspend(this, inputs); |
698 |
return toggle_suspend(this, inputs); |
| 699 |
}); |
699 |
}); |
| 700 |
}); |
700 |
}); |
|
|
701 |
|
| 702 |
async function load_patron_holds_table(biblio_id, split_data) { |
| 703 |
const { name: split_name, value: split_value } = split_data; |
| 704 |
const table_id = `#patron_holds_table_${biblio_id}_${split_value}`; |
| 705 |
hold_table_settings.table = `patron_holds_table_${biblio_id}_${split_data.value}`; |
| 706 |
let url = `/api/v1/holds/?q={"me.biblio_id":${biblio_id}`; |
| 707 |
|
| 708 |
if (split_name === "branch" && split_value !== "any") { |
| 709 |
url += `, "me.pickup_library_id":"${split_value}"`; |
| 710 |
} else if (split_name === "itemtype" && split_value !== "any") { |
| 711 |
url += `, "me.itemtype":"${split_value}"`; |
| 712 |
} else if (split_name === "branch_itemtype") { |
| 713 |
const [branch, itemtype] = split_value.split("_"); |
| 714 |
url += |
| 715 |
itemtype === "any" |
| 716 |
? `, "me.pickup_library_id":"${branch}"` |
| 717 |
: `, "me.pickup_library_id":"${branch}", "me.itemtype":"${itemtype}"`; |
| 718 |
} |
| 719 |
|
| 720 |
url += "}"; |
| 721 |
const totalHolds = $(table_id).data("total-holds"); |
| 722 |
const totalHoldsSelect = parseInt(totalHolds) + 1; |
| 723 |
let pageStart; |
| 724 |
var holdsQueueTable = $(table_id).kohaTable( |
| 725 |
{ |
| 726 |
ajax: { |
| 727 |
url: url, |
| 728 |
data: function (params) { |
| 729 |
pageStart = params.start; |
| 730 |
var query = { |
| 731 |
_per_page: params.length, |
| 732 |
_page: params.start / params.length + 1, |
| 733 |
_order_by: "priority", |
| 734 |
_match: "exact", |
| 735 |
}; |
| 736 |
return query; |
| 737 |
}, |
| 738 |
}, |
| 739 |
embed: ["patron", "item", "item_group"], |
| 740 |
columnDefs: [ |
| 741 |
{ |
| 742 |
targets: [2, 3], |
| 743 |
className: "dt-body-nowrap", |
| 744 |
}, |
| 745 |
{ |
| 746 |
targets: [3, 9], |
| 747 |
visible: CAN_user_reserveforothers_modify_holds_priority |
| 748 |
? true |
| 749 |
: false, |
| 750 |
}, |
| 751 |
], |
| 752 |
columns: [ |
| 753 |
{ |
| 754 |
data: "hold_id", |
| 755 |
orderable: false, |
| 756 |
searchable: false, |
| 757 |
render: function (data, type, row, meta) { |
| 758 |
return ( |
| 759 |
'<input type="checkbox" class="select_hold" data-id="' + |
| 760 |
data + |
| 761 |
'"/>' |
| 762 |
); |
| 763 |
}, |
| 764 |
}, |
| 765 |
{ |
| 766 |
data: "priority", |
| 767 |
orderable: false, |
| 768 |
searchable: false, |
| 769 |
render: function (data, type, row, meta) { |
| 770 |
let select = |
| 771 |
'<select name="rank-request" class="rank-request" data-id="' + |
| 772 |
row.hold_id; |
| 773 |
if ( |
| 774 |
CAN_user_reserveforothers_modify_holds_priority && |
| 775 |
split_name == "any" |
| 776 |
) { |
| 777 |
for (var i = 0; i < totalHoldsSelect; i++) { |
| 778 |
let selected; |
| 779 |
let value; |
| 780 |
let desc; |
| 781 |
if (data == i && row.status == "T") { |
| 782 |
select += '" disabled="disabled">'; |
| 783 |
selected = " selected='selected' "; |
| 784 |
value = "T"; |
| 785 |
desc = "In transit"; |
| 786 |
} else if (data == i && row.status == "P") { |
| 787 |
select += '" disabled="disabled">'; |
| 788 |
selected = " selected='selected' "; |
| 789 |
value = "P"; |
| 790 |
desc = "In processing"; |
| 791 |
} else if (data == i && row.status == "W") { |
| 792 |
select += '" disabled="disabled">'; |
| 793 |
selected = " selected='selected' "; |
| 794 |
value = "W"; |
| 795 |
desc = "Waiting"; |
| 796 |
} else if (data == i && !row.status) { |
| 797 |
select += '">'; |
| 798 |
selected = " selected='selected' "; |
| 799 |
value = data; |
| 800 |
desc = data; |
| 801 |
} else { |
| 802 |
if (i != 0) { |
| 803 |
select += '">'; |
| 804 |
value = i; |
| 805 |
desc = i; |
| 806 |
} else { |
| 807 |
select += '">'; |
| 808 |
} |
| 809 |
} |
| 810 |
if (value) { |
| 811 |
select += |
| 812 |
'<option value="' + |
| 813 |
value + |
| 814 |
'"' + |
| 815 |
selected + |
| 816 |
">" + |
| 817 |
desc + |
| 818 |
"</option>"; |
| 819 |
} |
| 820 |
} |
| 821 |
} else { |
| 822 |
if (row.status == "T") { |
| 823 |
select += |
| 824 |
'" disabled="disabled"><option value="T" selected="selected">In transit</option></select>'; |
| 825 |
} else if (row.status == "P") { |
| 826 |
select += |
| 827 |
'" disabled="disabled"><option value="P" selected="selected">In processing</option></select>'; |
| 828 |
} else if (row.status == "W") { |
| 829 |
select += |
| 830 |
'" disabled="disabled"><option value="W" selected="selected">Waiting</option></select>'; |
| 831 |
} else { |
| 832 |
if ( |
| 833 |
HoldsSplitQueue !== "nothing" && |
| 834 |
HoldsSplitQueueNumbering === "virtual" |
| 835 |
) { |
| 836 |
let virtualPriority = |
| 837 |
pageStart + meta.row + 1; |
| 838 |
select += |
| 839 |
'" disabled="disabled"><option value="' + |
| 840 |
data + |
| 841 |
'" selected="selected">' + |
| 842 |
virtualPriority + |
| 843 |
"</option></select>"; |
| 844 |
} else { |
| 845 |
select += |
| 846 |
'" disabled="disabled"><option value="' + |
| 847 |
data + |
| 848 |
'" selected="selected">' + |
| 849 |
data + |
| 850 |
"</option></select>"; |
| 851 |
} |
| 852 |
} |
| 853 |
} |
| 854 |
select += "</select>"; |
| 855 |
return select; |
| 856 |
}, |
| 857 |
}, |
| 858 |
{ |
| 859 |
data: "", |
| 860 |
orderable: false, |
| 861 |
searchable: false, |
| 862 |
render: function (data, type, row, meta) { |
| 863 |
if (row.status) { |
| 864 |
return null; |
| 865 |
} |
| 866 |
let buttons = |
| 867 |
'<a class="hold-arrow move-hold" title="Move hold up" href="#" data-move-hold="up" data-priority="' + |
| 868 |
row.priority + |
| 869 |
'" reserve_id="' + |
| 870 |
row.hold_id + |
| 871 |
'"><i class="fa fa-lg icon-move-hold-up" aria-hidden="true"></i></a>'; |
| 872 |
buttons += |
| 873 |
'<a class="hold-arrow move-hold" title="Move hold to top" href="#" data-move-hold="top" data-priority="' + |
| 874 |
row.priority + |
| 875 |
'" reserve_id="' + |
| 876 |
row.hold_id + |
| 877 |
'"><i class="fa fa-lg icon-move-hold-top" aria-hidden="true"></i></a>'; |
| 878 |
buttons += |
| 879 |
'<a class="hold-arrow move-hold" title="Move hold to bottom" href="#" data-move-hold="bottom" data-priority="' + |
| 880 |
row.priority + |
| 881 |
'" reserve_id="' + |
| 882 |
row.hold_id + |
| 883 |
'"><i class="fa fa-lg icon-move-hold-bottom" aria-hidden="true"></i></a>'; |
| 884 |
buttons += |
| 885 |
'<a class="hold-arrow move-hold" title="Move hold down" href="#" data-move-hold="down" data-priority="' + |
| 886 |
row.priority + |
| 887 |
'" reserve_id="' + |
| 888 |
row.hold_id + |
| 889 |
'"><i class="fa fa-lg icon-move-hold-down" aria-hidden="true"></i></a>'; |
| 890 |
return buttons; |
| 891 |
}, |
| 892 |
}, |
| 893 |
{ |
| 894 |
data: "patron.cardnumber", |
| 895 |
orderable: false, |
| 896 |
searchable: true, |
| 897 |
render: function (data, type, row, meta) { |
| 898 |
if (data == null) { |
| 899 |
let library = libraries.find( |
| 900 |
library => library._id == row.pickup_library_id |
| 901 |
); |
| 902 |
return __("A patron from library %s").format( |
| 903 |
library.name |
| 904 |
); |
| 905 |
} else { |
| 906 |
return ( |
| 907 |
'<a href="/cgi-bin/koha/members/moremember.pl?borrowernumber=' + |
| 908 |
row.patron.patron_id + |
| 909 |
'">' + |
| 910 |
data + |
| 911 |
"</a>" |
| 912 |
); |
| 913 |
} |
| 914 |
}, |
| 915 |
}, |
| 916 |
{ |
| 917 |
data: "notes", |
| 918 |
orderable: false, |
| 919 |
searchable: false, |
| 920 |
render: function (data, type, row, meta) { |
| 921 |
return data; |
| 922 |
}, |
| 923 |
}, |
| 924 |
{ |
| 925 |
data: "hold_date", |
| 926 |
orderable: false, |
| 927 |
searchable: false, |
| 928 |
render: function (data, type, row, meta) { |
| 929 |
if (AllowHoldDateInFuture) { |
| 930 |
return ( |
| 931 |
'<input type="text" class="holddate" value="' + |
| 932 |
$date(data, { dateformat: "rfc3339" }) + |
| 933 |
'" size="10" name="hold_date" data-id="' + |
| 934 |
row.hold_id + |
| 935 |
'" data-current-date="' + |
| 936 |
data + |
| 937 |
'"/>' |
| 938 |
); |
| 939 |
} else { |
| 940 |
return $date(data); |
| 941 |
} |
| 942 |
}, |
| 943 |
}, |
| 944 |
{ |
| 945 |
data: "expiration_date", |
| 946 |
orderable: false, |
| 947 |
searchable: false, |
| 948 |
render: function (data, type, row, meta) { |
| 949 |
return ( |
| 950 |
'<input type="text" class="expirationdate" value="' + |
| 951 |
$date(data, { dateformat: "rfc3339" }) + |
| 952 |
'" size="10" name="expiration_date" data-id="' + |
| 953 |
row.hold_id + |
| 954 |
'" data-current-date="' + |
| 955 |
data + |
| 956 |
'"/>' |
| 957 |
); |
| 958 |
}, |
| 959 |
}, |
| 960 |
{ |
| 961 |
data: "pickup_library_id", |
| 962 |
orderable: false, |
| 963 |
searchable: false, |
| 964 |
render: function (data, type, row, meta) { |
| 965 |
var branchSelect = |
| 966 |
"<select priority=" + |
| 967 |
row.priority + |
| 968 |
' class="hold_location_select" data-id="' + |
| 969 |
row.hold_id + |
| 970 |
'" reserve_id="' + |
| 971 |
row.hold_id + |
| 972 |
'" name="pick-location" data-pickup-location-source="hold">'; |
| 973 |
var libraryname; |
| 974 |
for (var i = 0; i < libraries.length; i++) { |
| 975 |
var selectedbranch; |
| 976 |
var setbranch; |
| 977 |
if (libraries[i]._id == data) { |
| 978 |
selectedbranch = " selected='selected' "; |
| 979 |
setbranch = __(" (current) "); |
| 980 |
libraryname = libraries[i]._str; |
| 981 |
} else if (libraries[i].pickup_location == false) { |
| 982 |
continue; |
| 983 |
} else { |
| 984 |
selectedbranch = ""; |
| 985 |
setbranch = ""; |
| 986 |
} |
| 987 |
branchSelect += |
| 988 |
'<option value="' + |
| 989 |
libraries[i]._id.escapeHtml() + |
| 990 |
'"' + |
| 991 |
selectedbranch + |
| 992 |
">" + |
| 993 |
libraries[i]._str.escapeHtml() + |
| 994 |
setbranch + |
| 995 |
"</option>"; |
| 996 |
} |
| 997 |
branchSelect += "</select>"; |
| 998 |
if (row.status == "T") { |
| 999 |
return __( |
| 1000 |
"Item being transferred to <strong>%s</strong>" |
| 1001 |
).format(libraryname); |
| 1002 |
} else if (row.status == "P") { |
| 1003 |
return __( |
| 1004 |
"Item being processed at <strong>%s</strong>" |
| 1005 |
).format(libraryname); |
| 1006 |
} else if (row.status == "W") { |
| 1007 |
return __( |
| 1008 |
"Item waiting at <strong>%s</strong> since %s" |
| 1009 |
).format(libraryname, $date(row.waiting_date)); |
| 1010 |
} else { |
| 1011 |
return branchSelect; |
| 1012 |
} |
| 1013 |
}, |
| 1014 |
}, |
| 1015 |
{ |
| 1016 |
data: "", |
| 1017 |
orderable: false, |
| 1018 |
searchable: false, |
| 1019 |
render: function (data, type, row, meta) { |
| 1020 |
if (row.item_id) { |
| 1021 |
return ( |
| 1022 |
'<a href="/cgi-bin/koha/catalogue/moredetail.pl?biblionumber=' + |
| 1023 |
row.biblio_id + |
| 1024 |
"&itemnumber=" + |
| 1025 |
row.item_id + |
| 1026 |
'">' + |
| 1027 |
row.item.external_id + |
| 1028 |
"</a>" |
| 1029 |
); |
| 1030 |
} else if (row.item_group_id) { |
| 1031 |
return __( |
| 1032 |
"Next available item from group <strong>%s</strong>" |
| 1033 |
).format(row.item_group.description); |
| 1034 |
} else { |
| 1035 |
if (row.non_priority) { |
| 1036 |
return ( |
| 1037 |
"<em>" + |
| 1038 |
__("Next available") + |
| 1039 |
"</em><br/><i>" + |
| 1040 |
__("Non priority hold") + |
| 1041 |
"</i>" |
| 1042 |
); |
| 1043 |
} else { |
| 1044 |
return "<em>" + __("Next available") + "</em>"; |
| 1045 |
} |
| 1046 |
} |
| 1047 |
}, |
| 1048 |
}, |
| 1049 |
{ |
| 1050 |
data: "", |
| 1051 |
orderable: false, |
| 1052 |
searchable: false, |
| 1053 |
render: function (data, type, row, meta) { |
| 1054 |
if (row.item_id) { |
| 1055 |
return null; |
| 1056 |
} else { |
| 1057 |
if (row.lowest_priority) { |
| 1058 |
return ( |
| 1059 |
'<a class="hold-arrow toggle-lowest-priority" title="Remove lowest priority" href="#" data-op="cud-setLowestPriority" data-borrowernumber="' + |
| 1060 |
row.patron_id + |
| 1061 |
'" data-biblionumber="' + |
| 1062 |
biblio_id + |
| 1063 |
'" data-reserve_id="' + |
| 1064 |
row.hold_id + |
| 1065 |
'" data-date="' + |
| 1066 |
row.hold_date + |
| 1067 |
'"><i class="fa fa-lg fa-rotate-90 icon-unset-lowest" aria-hidden="true"></i></a>' |
| 1068 |
); |
| 1069 |
} else { |
| 1070 |
return ( |
| 1071 |
'<a class="hold-arrow toggle-lowest-priority" title="Set lowest priority" href="#" data-op="cud-setLowestPriority" data-borrowernumber="' + |
| 1072 |
row.patron_id + |
| 1073 |
'" data-biblionumber="' + |
| 1074 |
biblio_id + |
| 1075 |
'" data-reserve_id="' + |
| 1076 |
row.hold_id + |
| 1077 |
'" data-date="' + |
| 1078 |
row.hold_date + |
| 1079 |
'"><i class="fa fa-lg fa-rotate-90 icon-set-lowest" aria-hidden="true"></i></a>' |
| 1080 |
); |
| 1081 |
} |
| 1082 |
} |
| 1083 |
}, |
| 1084 |
}, |
| 1085 |
{ |
| 1086 |
data: "hold_id", |
| 1087 |
orderable: false, |
| 1088 |
searchable: false, |
| 1089 |
render: function (data, type, row, meta) { |
| 1090 |
return ( |
| 1091 |
'<a class="cancel-hold" title="Cancel hold" reserve_id="' + |
| 1092 |
data + |
| 1093 |
'" href="#"><i class="fa fa-trash" aria-label="Cancel hold"></i></a>' |
| 1094 |
); |
| 1095 |
}, |
| 1096 |
}, |
| 1097 |
{ |
| 1098 |
data: "hold_id", |
| 1099 |
orderable: false, |
| 1100 |
searchable: false, |
| 1101 |
render: function (data, type, row, meta) { |
| 1102 |
if (row.status) { |
| 1103 |
var link_value = |
| 1104 |
row.status == "T" |
| 1105 |
? __("Revert transit status") |
| 1106 |
: __("Revert waiting status"); |
| 1107 |
return ( |
| 1108 |
'<a class="btn btn-default submit-form-link" href="#" id="revert_hold_' + |
| 1109 |
data + |
| 1110 |
'" data-op="cud-move" data-where="down" data-first_priority="1" data-last_priority="' + |
| 1111 |
totalHolds + |
| 1112 |
'" data-prev_priority="0" data-next_priority="1" data-borrowernumber="' + |
| 1113 |
row.patron_id + |
| 1114 |
'" data-biblionumber="' + |
| 1115 |
biblio_id + |
| 1116 |
'" data-itemnumber="' + |
| 1117 |
row.item_id + |
| 1118 |
'" data-reserve_id="' + |
| 1119 |
row.hold_id + |
| 1120 |
'" data-date="' + |
| 1121 |
row.hold_date + |
| 1122 |
'" data-action="request.pl" data-method="post">' + |
| 1123 |
link_value + |
| 1124 |
"</a>" |
| 1125 |
); |
| 1126 |
} else { |
| 1127 |
let td = ""; |
| 1128 |
if (SuspendHoldsIntranet) { |
| 1129 |
td += |
| 1130 |
'<button class="btn btn-default btn-xs toggle-suspend" data-id="' + |
| 1131 |
data + |
| 1132 |
'" data-biblionumber="' + |
| 1133 |
biblio_id + |
| 1134 |
'" data-suspended="' + |
| 1135 |
row.suspended + |
| 1136 |
'">'; |
| 1137 |
if (row.suspended) { |
| 1138 |
td += |
| 1139 |
'<i class="fa fa-play" aria-hidden="true"></i> ' + |
| 1140 |
__("Resume") + |
| 1141 |
"</button>"; |
| 1142 |
} else { |
| 1143 |
td += |
| 1144 |
'<i class="fa fa-pause" aria-hidden="true"></i> ' + |
| 1145 |
__("Suspend") + |
| 1146 |
"</button>"; |
| 1147 |
} |
| 1148 |
if (AutoResumeSuspendedHolds) { |
| 1149 |
if (row.suspended) { |
| 1150 |
td += |
| 1151 |
'<label for="suspend_until_' + |
| 1152 |
data + |
| 1153 |
'">' + |
| 1154 |
__("Suspend on") + |
| 1155 |
" </label>"; |
| 1156 |
} else { |
| 1157 |
td += |
| 1158 |
'<label for="suspend_until_' + |
| 1159 |
data + |
| 1160 |
'">' + |
| 1161 |
__("Suspend until") + |
| 1162 |
" </label>"; |
| 1163 |
} |
| 1164 |
td += |
| 1165 |
'<input type="text" name="suspend_until_' + |
| 1166 |
data + |
| 1167 |
'" data-id="' + |
| 1168 |
data + |
| 1169 |
'" size="10" value="' + |
| 1170 |
$date(row.suspended_until, { |
| 1171 |
dateformat: "rfc3339", |
| 1172 |
}) + |
| 1173 |
'" class="suspenddate" data-flatpickr-futuredate="true" data-suspend-date="' + |
| 1174 |
row.suspended_until + |
| 1175 |
'" />'; |
| 1176 |
} |
| 1177 |
return td; |
| 1178 |
} else { |
| 1179 |
return null; |
| 1180 |
} |
| 1181 |
} |
| 1182 |
}, |
| 1183 |
}, |
| 1184 |
{ |
| 1185 |
data: "hold_id", |
| 1186 |
orderable: false, |
| 1187 |
searchable: false, |
| 1188 |
render: function (data, type, row, meta) { |
| 1189 |
if (row.status == "W" || row.status == "T") { |
| 1190 |
return ( |
| 1191 |
'<a class="btn btn-default btn-xs printholdslip" data-reserve_id="' + |
| 1192 |
data + |
| 1193 |
'">' + |
| 1194 |
__("Print slip") + |
| 1195 |
"</a>" |
| 1196 |
); |
| 1197 |
} else { |
| 1198 |
return ""; |
| 1199 |
} |
| 1200 |
}, |
| 1201 |
}, |
| 1202 |
], |
| 1203 |
}, |
| 1204 |
hold_table_settings |
| 1205 |
); |
| 1206 |
$(table_id).on("draw.dt", function () { |
| 1207 |
// Remove the search box. Don't know why it isn't working in the table settings |
| 1208 |
$(this).parent().find(".pager .table_controls .dt-search").remove(); |
| 1209 |
$(this) |
| 1210 |
.parent() |
| 1211 |
.find(".pager .table_controls .dt-buttons .dt_button_clear_filter") |
| 1212 |
.remove(); |
| 1213 |
var MSG_CANCEL_SELECTED = _("Cancel selected (%s)"); |
| 1214 |
$(".cancel_selected_holds").html( |
| 1215 |
MSG_CANCEL_SELECTED.format( |
| 1216 |
$(".holds_table .select_hold:checked").length |
| 1217 |
) |
| 1218 |
); |
| 1219 |
$(".holds_table .select_hold").each(function () { |
| 1220 |
if ( |
| 1221 |
localStorage.selectedHolds && |
| 1222 |
localStorage.selectedHolds.includes($(this).data("id")) |
| 1223 |
) { |
| 1224 |
$(this).prop("checked", true); |
| 1225 |
} |
| 1226 |
}); |
| 1227 |
$(".holds_table .select_hold_all").on("click", function () { |
| 1228 |
var table = $(this).parents(".holds_table"); |
| 1229 |
var count = $(".select_hold:checked", table).length; |
| 1230 |
$(".select_hold", table).prop("checked", !count); |
| 1231 |
$(this).prop("checked", !count); |
| 1232 |
$(this).parent().parent().toggleClass("selected"); |
| 1233 |
$(".cancel_selected_holds").html( |
| 1234 |
MSG_CANCEL_SELECTED.format( |
| 1235 |
$(".holds_table .select_hold:checked").length |
| 1236 |
) |
| 1237 |
); |
| 1238 |
localStorage.selectedHolds = $(".holds_table .select_hold:checked") |
| 1239 |
.toArray() |
| 1240 |
.map(el => $(el).data("id")); |
| 1241 |
}); |
| 1242 |
$(".holds_table .select_hold").on("click", function () { |
| 1243 |
var table = $(this).parents(".holds_table"); |
| 1244 |
var count = $(".select_hold:not(:checked)", table).length; |
| 1245 |
$(".select_hold_all", table).prop("checked", !count); |
| 1246 |
$(this).parent().parent().toggleClass("selected"); |
| 1247 |
$(".cancel_selected_holds").html( |
| 1248 |
MSG_CANCEL_SELECTED.format( |
| 1249 |
$(".holds_table .select_hold:checked").length |
| 1250 |
) |
| 1251 |
); |
| 1252 |
localStorage.selectedHolds = $(".holds_table .select_hold:checked") |
| 1253 |
.toArray() |
| 1254 |
.map(el => $(el).data("id")); |
| 1255 |
}); |
| 1256 |
$(".cancel-hold").on("click", function (e) { |
| 1257 |
e.preventDefault; |
| 1258 |
var res_id = $(this).attr("reserve_id"); |
| 1259 |
$(".select_hold").prop("checked", false); |
| 1260 |
$(".select_hold_all").prop("checked", false); |
| 1261 |
$(".cancel_selected_holds").html(MSG_CANCEL_SELECTED.format(0)); |
| 1262 |
$("#cancelModal") |
| 1263 |
.modal("show") |
| 1264 |
.find("#cancelModalConfirmBtn") |
| 1265 |
.attr("data-id", res_id); |
| 1266 |
delete localStorage.selectedHolds; |
| 1267 |
}); |
| 1268 |
$(".cancel_selected_holds").on("click", function (e) { |
| 1269 |
e.preventDefault(); |
| 1270 |
if ($(".holds_table .select_hold:checked").length) { |
| 1271 |
delete localStorage.selectedHolds; |
| 1272 |
$("#cancelModal").modal("show"); |
| 1273 |
} |
| 1274 |
return false; |
| 1275 |
}); |
| 1276 |
// Remove any previously attached handlers |
| 1277 |
$("#cancelModalConfirmBtn").off("click"); |
| 1278 |
// Attach the handler to the button |
| 1279 |
$("#cancelModalConfirmBtn").one("click", function (e) { |
| 1280 |
e.preventDefault(); |
| 1281 |
let hold_ids; |
| 1282 |
const hold_id = $("#cancelModal") |
| 1283 |
.modal("show") |
| 1284 |
.find("#cancelModalConfirmBtn") |
| 1285 |
.attr("data-id"); |
| 1286 |
let reason = $("#modal-cancellation-reason").val(); |
| 1287 |
if (hold_id) { |
| 1288 |
hold_ids = [hold_id]; |
| 1289 |
} else { |
| 1290 |
hold_ids = $(".holds_table .select_hold:checked") |
| 1291 |
.toArray() |
| 1292 |
.map(el => $(el).data("id")); |
| 1293 |
} |
| 1294 |
$("#cancelModal") |
| 1295 |
.find(".modal-footer #cancelModalConfirmBtn") |
| 1296 |
.before( |
| 1297 |
'<img src="/intranet-tmpl/prog/img/spinner-small.gif" alt="" style="padding-right: 10px;"/>' |
| 1298 |
); |
| 1299 |
deleteHolds(hold_ids, reason); |
| 1300 |
$("#cancelModal") |
| 1301 |
.modal("show") |
| 1302 |
.find("#cancelModalConfirmBtn") |
| 1303 |
.attr("data-id", ""); |
| 1304 |
}); |
| 1305 |
async function deleteHolds(hold_ids, reason) { |
| 1306 |
for (const hold_id of hold_ids) { |
| 1307 |
await deleteHold(hold_id, reason); |
| 1308 |
$("#cancelModal") |
| 1309 |
.find(".modal-body") |
| 1310 |
.append( |
| 1311 |
'<p class="hold-cancelled">' + |
| 1312 |
__("Hold") + |
| 1313 |
" " + |
| 1314 |
hold_id + |
| 1315 |
" " + |
| 1316 |
__("cancelled") + |
| 1317 |
"</p>" |
| 1318 |
); |
| 1319 |
await new Promise(resolve => setTimeout(resolve, 1000)); |
| 1320 |
} |
| 1321 |
|
| 1322 |
holdsQueueTable.api().ajax.reload(null, false); |
| 1323 |
setTimeout(() => { |
| 1324 |
$("#cancelModal").modal("hide"); |
| 1325 |
$("#cancelModal") |
| 1326 |
.find(".modal-footer #cancelModalConfirmBtn") |
| 1327 |
.prev("img") |
| 1328 |
.remove(); |
| 1329 |
$("#cancelModal") |
| 1330 |
.find(".modal-body") |
| 1331 |
.find(".hold-cancelled") |
| 1332 |
.remove(); |
| 1333 |
}); |
| 1334 |
} |
| 1335 |
async function deleteHold(hold_id, reason) { |
| 1336 |
try { |
| 1337 |
await $.ajax({ |
| 1338 |
method: "DELETE", |
| 1339 |
url: "/api/v1/holds/" + encodeURIComponent(hold_id), |
| 1340 |
data: JSON.stringify(reason), |
| 1341 |
}); |
| 1342 |
} catch (error) { |
| 1343 |
console.error("Error when deleting hold: " + hold_id); |
| 1344 |
} |
| 1345 |
} |
| 1346 |
$(".holddate, .expirationdate").flatpickr({ |
| 1347 |
onReady: function (selectedDates, dateStr, instance) { |
| 1348 |
$(instance.altInput) |
| 1349 |
.wrap("<span class='flatpickr_wrapper'></span>") |
| 1350 |
.after( |
| 1351 |
$("<a/>") |
| 1352 |
.attr("href", "#") |
| 1353 |
.addClass("clear_date") |
| 1354 |
.addClass("fa fa-times") |
| 1355 |
.addClass("ps-2") |
| 1356 |
.on("click", function (e) { |
| 1357 |
e.preventDefault(); |
| 1358 |
instance.clear(); |
| 1359 |
}) |
| 1360 |
.attr("aria-hidden", true) |
| 1361 |
); |
| 1362 |
}, |
| 1363 |
onChange: function (selectedDates, dateStr, instance) { |
| 1364 |
let hold_id = $(instance.input).attr("data-id"); |
| 1365 |
let fieldname = $(instance.input).attr("name"); |
| 1366 |
let current_date = $(instance.input).attr("data-current-date"); |
| 1367 |
dateStr = dateStr ? dateStr : null; |
| 1368 |
let req = |
| 1369 |
fieldname == "hold_date" |
| 1370 |
? { hold_date: dateStr } |
| 1371 |
: { expiration_date: dateStr }; |
| 1372 |
if (current_date != dateStr) { |
| 1373 |
$.ajax({ |
| 1374 |
method: "PATCH", |
| 1375 |
url: "/api/v1/holds/" + encodeURIComponent(hold_id), |
| 1376 |
contentType: "application/json", |
| 1377 |
data: JSON.stringify(req), |
| 1378 |
success: function (data) { |
| 1379 |
holdsQueueTable.api().ajax.reload(null, false); |
| 1380 |
}, |
| 1381 |
error: function (jqXHR, textStatus, errorThrown) { |
| 1382 |
holdsQueueTable.api().ajax.reload(null, false); |
| 1383 |
}, |
| 1384 |
}); |
| 1385 |
} |
| 1386 |
}, |
| 1387 |
}); |
| 1388 |
$(".suspenddate").flatpickr({ |
| 1389 |
onReady: function (selectedDates, dateStr, instance) { |
| 1390 |
$(instance.altInput) |
| 1391 |
.wrap("<span class='flatpickr_wrapper'></span>") |
| 1392 |
.after( |
| 1393 |
$("<a/>") |
| 1394 |
.attr("href", "#") |
| 1395 |
.addClass("clear_date") |
| 1396 |
.addClass("fa fa-times") |
| 1397 |
.addClass("ps-2") |
| 1398 |
.on("click", function (e) { |
| 1399 |
e.preventDefault(); |
| 1400 |
instance.clear(); |
| 1401 |
}) |
| 1402 |
.attr("aria-hidden", true) |
| 1403 |
); |
| 1404 |
}, |
| 1405 |
}); |
| 1406 |
$(".toggle-suspend").one("click", function (e) { |
| 1407 |
e.preventDefault(); |
| 1408 |
const hold_id = $(this).data("id"); |
| 1409 |
const suspended = $(this).attr("data-suspended"); |
| 1410 |
const input = $(`.suspenddate[data-id="${hold_id}"]`); |
| 1411 |
const method = suspended == "true" ? "DELETE" : "POST"; |
| 1412 |
let end_date = input.val() && method == "POST" ? input.val() : null; |
| 1413 |
let params = |
| 1414 |
end_date !== null && end_date !== "" |
| 1415 |
? JSON.stringify({ end_date: end_date }) |
| 1416 |
: null; |
| 1417 |
$.ajax({ |
| 1418 |
method: method, |
| 1419 |
url: |
| 1420 |
"/api/v1/holds/" + |
| 1421 |
encodeURIComponent(hold_id) + |
| 1422 |
"/suspension", |
| 1423 |
contentType: "application/json", |
| 1424 |
data: params, |
| 1425 |
success: function (data) { |
| 1426 |
holdsQueueTable.api().ajax.reload(null, false); |
| 1427 |
}, |
| 1428 |
error: function (jqXHR, textStatus, errorThrown) { |
| 1429 |
holdsQueueTable.api().ajax.reload(null, false); |
| 1430 |
alert( |
| 1431 |
"There was an error:" + textStatus + " " + errorThrown |
| 1432 |
); |
| 1433 |
}, |
| 1434 |
}); |
| 1435 |
}); |
| 1436 |
$(".rank-request").on("change", function (e) { |
| 1437 |
e.preventDefault(); |
| 1438 |
const hold_id = $(this).data("id"); |
| 1439 |
let priority = e.target.value; |
| 1440 |
$.ajax({ |
| 1441 |
method: "PUT", |
| 1442 |
url: |
| 1443 |
"/api/v1/holds/" + |
| 1444 |
encodeURIComponent(hold_id) + |
| 1445 |
"/priority", |
| 1446 |
data: JSON.stringify(priority), |
| 1447 |
success: function (data) { |
| 1448 |
holdsQueueTable.api().ajax.reload(null, false); |
| 1449 |
}, |
| 1450 |
error: function (jqXHR, textStatus, errorThrown) { |
| 1451 |
alert( |
| 1452 |
"There was an error:" + textStatus + " " + errorThrown |
| 1453 |
); |
| 1454 |
}, |
| 1455 |
}); |
| 1456 |
}); |
| 1457 |
$(".move-hold").one("click", function (e) { |
| 1458 |
e.preventDefault(); |
| 1459 |
let toPosition = $(this).attr("data-move-hold"); |
| 1460 |
let priority = $(this).attr("data-priority"); |
| 1461 |
var res_id = $(this).attr("reserve_id"); |
| 1462 |
var moveTo; |
| 1463 |
if (toPosition == "up") { |
| 1464 |
moveTo = parseInt(priority) - 1; |
| 1465 |
} |
| 1466 |
if (toPosition == "down") { |
| 1467 |
moveTo = parseInt(priority) + 1; |
| 1468 |
} |
| 1469 |
if (toPosition == "top") { |
| 1470 |
moveTo = 1; |
| 1471 |
} |
| 1472 |
if (toPosition == "bottom") { |
| 1473 |
moveTo = totalHolds; |
| 1474 |
} |
| 1475 |
$.ajax({ |
| 1476 |
method: "PUT", |
| 1477 |
url: |
| 1478 |
"/api/v1/holds/" + encodeURIComponent(res_id) + "/priority", |
| 1479 |
data: JSON.stringify(moveTo), |
| 1480 |
success: function (data) { |
| 1481 |
holdsQueueTable.api().ajax.reload(null, false); |
| 1482 |
}, |
| 1483 |
error: function (jqXHR, textStatus, errorThrown) { |
| 1484 |
alert( |
| 1485 |
"There was an error:" + textStatus + " " + errorThrown |
| 1486 |
); |
| 1487 |
}, |
| 1488 |
}); |
| 1489 |
}); |
| 1490 |
$(".toggle-lowest-priority").one("click", function (e) { |
| 1491 |
e.preventDefault(); |
| 1492 |
var res_id = $(this).attr("data-reserve_id"); |
| 1493 |
$.ajax({ |
| 1494 |
method: "PUT", |
| 1495 |
url: |
| 1496 |
"/api/v1/holds/" + |
| 1497 |
encodeURIComponent(res_id) + |
| 1498 |
"/lowest_priority", |
| 1499 |
success: function (data) { |
| 1500 |
holdsQueueTable.api().ajax.reload(null, false); |
| 1501 |
}, |
| 1502 |
error: function (jqXHR, textStatus, errorThrown) { |
| 1503 |
alert( |
| 1504 |
"There was an error:" + textStatus + " " + errorThrown |
| 1505 |
); |
| 1506 |
}, |
| 1507 |
}); |
| 1508 |
}); |
| 1509 |
$(".hold_location_select").on("change", function () { |
| 1510 |
$(this).prop("disabled", true); |
| 1511 |
var cur_select = $(this); |
| 1512 |
var res_id = $(this).attr("reserve_id"); |
| 1513 |
$(this).after( |
| 1514 |
'<div id="updating_reserveno' + |
| 1515 |
res_id + |
| 1516 |
'" class="waiting"><img src="/intranet-tmpl/prog/img/spinner-small.gif" alt="" /><span class="waiting_msg"></span></div>' |
| 1517 |
); |
| 1518 |
let api_url = |
| 1519 |
"/api/v1/holds/" + |
| 1520 |
encodeURIComponent(res_id) + |
| 1521 |
"/pickup_location"; |
| 1522 |
$.ajax({ |
| 1523 |
method: "PUT", |
| 1524 |
url: api_url, |
| 1525 |
data: JSON.stringify({ pickup_library_id: $(this).val() }), |
| 1526 |
headers: { "x-koha-override": "any" }, |
| 1527 |
success: function (data) { |
| 1528 |
holdsQueueTable.api().ajax.reload(null, false); |
| 1529 |
}, |
| 1530 |
error: function (jqXHR, textStatus, errorThrown) { |
| 1531 |
alert( |
| 1532 |
"There was an error:" + textStatus + " " + errorThrown |
| 1533 |
); |
| 1534 |
cur_select.prop("disabled", false); |
| 1535 |
$("#updating_reserveno" + res_id).remove(); |
| 1536 |
cur_select.val( |
| 1537 |
cur_select.children('option[selected="selected"]').val() |
| 1538 |
); |
| 1539 |
}, |
| 1540 |
}); |
| 1541 |
}); |
| 1542 |
$(".printholdslip").one("click", function () { |
| 1543 |
var reserve_id = $(this).attr("data-reserve_id"); |
| 1544 |
window.open( |
| 1545 |
"/cgi-bin/koha/circ/hold-transfer-slip.pl?reserve_id=" + |
| 1546 |
reserve_id |
| 1547 |
); |
| 1548 |
return false; |
| 1549 |
}); |
| 1550 |
}); |
| 1551 |
} |