@7365admin1/layer-common 1.11.12 → 1.11.14
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +12 -0
- package/components/AttendanceCheckInOutDialog.vue +5 -0
- package/components/AttendanceDetailsDialog.vue +1 -0
- package/components/AttendanceSettingsDialog.vue +1 -1
- package/components/MyAttendanceMain.vue +4 -0
- package/components/QrTemplate/PrintDialog.vue +56 -56
- package/components/VehicleForm.vue +12 -5
- package/components/VehicleManagement.vue +14 -7
- package/composables/useAttendance.ts +4 -3
- package/composables/useVehicle.ts +1 -1
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -162,6 +162,7 @@ const emit = defineEmits(["saved", "close"]);
|
|
|
162
162
|
|
|
163
163
|
const props = defineProps({
|
|
164
164
|
action: { type: String, default: "checkIn" }, // "checkIn" or "checkOut"
|
|
165
|
+
serviceType: { type: String, default: "" },
|
|
165
166
|
});
|
|
166
167
|
|
|
167
168
|
const formRef = ref<any>(null);
|
|
@@ -386,6 +387,10 @@ const submit = async () => {
|
|
|
386
387
|
payload[props.action].img = imageId;
|
|
387
388
|
}
|
|
388
389
|
|
|
390
|
+
if (props.serviceType) {
|
|
391
|
+
payload[props.action].serviceType = props.serviceType;
|
|
392
|
+
}
|
|
393
|
+
|
|
389
394
|
emit("saved", payload);
|
|
390
395
|
|
|
391
396
|
close();
|
|
@@ -365,7 +365,7 @@ const onSubmit = async () => {
|
|
|
365
365
|
payload.isGeofencingEnabled = false;
|
|
366
366
|
}
|
|
367
367
|
|
|
368
|
-
await updateAttendanceSettings(props.site, payload);
|
|
368
|
+
await updateAttendanceSettings(props.site, payload, props.serviceType);
|
|
369
369
|
await getAttendanceSettingsRefresh();
|
|
370
370
|
|
|
371
371
|
showSnackbar("Settings updated successfully");
|
|
@@ -62,6 +62,7 @@
|
|
|
62
62
|
<AttendanceCheckInOutDialog
|
|
63
63
|
v-model="dialogShowForm"
|
|
64
64
|
:action="currentAction"
|
|
65
|
+
:serviceType="props.serviceType"
|
|
65
66
|
@saved="onAttendanceSaved"
|
|
66
67
|
@close="dialogShowForm = false"
|
|
67
68
|
/>
|
|
@@ -69,6 +70,7 @@
|
|
|
69
70
|
<AttendanceDetailsDialog
|
|
70
71
|
v-model="dialogShowMoreActions"
|
|
71
72
|
:attendance-id="selectedAttendanceId"
|
|
73
|
+
:serviceType="props.serviceType"
|
|
72
74
|
@close="dialogShowMoreActions = false"
|
|
73
75
|
/>
|
|
74
76
|
|
|
@@ -82,6 +84,7 @@ import { useAttendancePermission } from "../composables/useAttendancePermission"
|
|
|
82
84
|
const props = defineProps({
|
|
83
85
|
orgId: { type: String, default: "" },
|
|
84
86
|
site: { type: String, default: "" },
|
|
87
|
+
serviceType: { type: String, default: "" },
|
|
85
88
|
});
|
|
86
89
|
|
|
87
90
|
const { canViewOwnAttendance, canCheckInOut, canViewAttendanceDetails } =
|
|
@@ -151,6 +154,7 @@ const {
|
|
|
151
154
|
page: page.value,
|
|
152
155
|
search: searchInput.value,
|
|
153
156
|
site: props.site,
|
|
157
|
+
serviceType: props.serviceType,
|
|
154
158
|
}),
|
|
155
159
|
{
|
|
156
160
|
watch: [page, searchInput, () => props.site],
|
|
@@ -53,7 +53,7 @@
|
|
|
53
53
|
<v-autocomplete
|
|
54
54
|
:items="
|
|
55
55
|
localTemplateList.filter(
|
|
56
|
-
(item) => !['All', 'Manually Added'].includes(item.name)
|
|
56
|
+
(item) => !['All', 'Manually Added'].includes(item.name)
|
|
57
57
|
)
|
|
58
58
|
"
|
|
59
59
|
item-title="name"
|
|
@@ -69,9 +69,9 @@
|
|
|
69
69
|
Select template
|
|
70
70
|
<span class="text-red font-weight-bold">*</span>
|
|
71
71
|
</template>
|
|
72
|
-
<template v-slot:append-item>
|
|
72
|
+
<!-- <template v-slot:append-item>
|
|
73
73
|
<div v-intersect="endIntersectTemplateList" />
|
|
74
|
-
</template>
|
|
74
|
+
</template> -->
|
|
75
75
|
</v-autocomplete>
|
|
76
76
|
</v-col>
|
|
77
77
|
</v-row>
|
|
@@ -833,57 +833,57 @@ watch(
|
|
|
833
833
|
() => props.templateList,
|
|
834
834
|
(newVal) => {
|
|
835
835
|
localTemplateList.value = newVal;
|
|
836
|
-
}
|
|
836
|
+
}
|
|
837
837
|
);
|
|
838
838
|
|
|
839
839
|
// interset start
|
|
840
840
|
|
|
841
841
|
// const page = ref(1); // replace with your actual page value
|
|
842
|
-
const totalNumberOfPagesTemplateList = ref(1); // replace with your actual total number of pages value
|
|
843
|
-
|
|
844
|
-
const endIntersectTemplateList = async (isIntersecting) => {
|
|
845
|
-
|
|
846
|
-
|
|
847
|
-
|
|
848
|
-
|
|
849
|
-
|
|
850
|
-
};
|
|
851
|
-
|
|
852
|
-
const getTemplateNameLists = async (page = 1, query = "") => {
|
|
853
|
-
|
|
854
|
-
|
|
855
|
-
|
|
856
|
-
|
|
857
|
-
|
|
858
|
-
|
|
859
|
-
|
|
860
|
-
|
|
861
|
-
|
|
862
|
-
|
|
863
|
-
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
|
|
869
|
-
|
|
870
|
-
|
|
871
|
-
|
|
872
|
-
|
|
873
|
-
|
|
874
|
-
|
|
875
|
-
|
|
876
|
-
|
|
877
|
-
|
|
878
|
-
|
|
879
|
-
|
|
880
|
-
|
|
881
|
-
|
|
882
|
-
|
|
883
|
-
|
|
884
|
-
|
|
885
|
-
|
|
886
|
-
};
|
|
842
|
+
// const totalNumberOfPagesTemplateList = ref(1); // replace with your actual total number of pages value
|
|
843
|
+
|
|
844
|
+
// const endIntersectTemplateList = async (isIntersecting) => {
|
|
845
|
+
// await getTemplateNameLists(page.value);
|
|
846
|
+
// if (isIntersecting && !isFetchingTemplates.value) {
|
|
847
|
+
// page.value += 1;
|
|
848
|
+
// await getTemplateNameLists(page.value);
|
|
849
|
+
// }
|
|
850
|
+
// };
|
|
851
|
+
|
|
852
|
+
// const getTemplateNameLists = async (page = 1, query = "") => {
|
|
853
|
+
// isFetchingTemplates.value = true;
|
|
854
|
+
|
|
855
|
+
// const result = await getTemplatesByPageSearch({
|
|
856
|
+
// sites: [route.params.site as string],
|
|
857
|
+
// limit: 10,
|
|
858
|
+
// page: page,
|
|
859
|
+
// statuses: ["active"],
|
|
860
|
+
// search: query,
|
|
861
|
+
// });
|
|
862
|
+
|
|
863
|
+
// totalNumberOfPagesTemplateList.value = result?.pages;
|
|
864
|
+
// if (result?.items.length) {
|
|
865
|
+
// const newItems = result?.items.map((item) => ({
|
|
866
|
+
// _id: item._id,
|
|
867
|
+
// name: item.name,
|
|
868
|
+
// prefixPass: item.prefixPass,
|
|
869
|
+
// prefixKey: item.prefixKey,
|
|
870
|
+
// }));
|
|
871
|
+
|
|
872
|
+
// if (page === 1) {
|
|
873
|
+
// newItems.unshift({ _id: null, name: "All" });
|
|
874
|
+
// newItems.push({ _id: "Manually Added", name: "Manually Added" });
|
|
875
|
+
// }
|
|
876
|
+
|
|
877
|
+
// // Only add new items if they don't already exist in the list
|
|
878
|
+
// newItems.forEach((newItem) => {
|
|
879
|
+
// if (!localTemplateList.value.find((item) => item._id === newItem._id)) {
|
|
880
|
+
// localTemplateList.value.push(newItem);
|
|
881
|
+
// }
|
|
882
|
+
// });
|
|
883
|
+
// }
|
|
884
|
+
|
|
885
|
+
// isFetchingTemplates.value = false;
|
|
886
|
+
// };
|
|
887
887
|
|
|
888
888
|
const searchTemplate = async (query) => {
|
|
889
889
|
isFetchingTemplates.value = true;
|
|
@@ -999,7 +999,7 @@ watch(
|
|
|
999
999
|
}
|
|
1000
1000
|
}
|
|
1001
1001
|
},
|
|
1002
|
-
{ immediate: true }
|
|
1002
|
+
{ immediate: true }
|
|
1003
1003
|
);
|
|
1004
1004
|
|
|
1005
1005
|
const router = useRouter();
|
|
@@ -1031,7 +1031,7 @@ const printContent = () => {
|
|
|
1031
1031
|
if (printOrientation == "KeyCard") {
|
|
1032
1032
|
localStorage.setItem(
|
|
1033
1033
|
"selectedKeysToPrint",
|
|
1034
|
-
JSON.stringify(selectedKeysToPrint.value)
|
|
1034
|
+
JSON.stringify(selectedKeysToPrint.value)
|
|
1035
1035
|
);
|
|
1036
1036
|
}
|
|
1037
1037
|
|
|
@@ -1083,14 +1083,14 @@ watch(selectedChoicePaperSizeOrientation, async (newVal: any) => {
|
|
|
1083
1083
|
resultKeys2.value.sort(
|
|
1084
1084
|
(firstItem: { value: string }, secondItem: { value: string }) => {
|
|
1085
1085
|
const numericValueOfFirstItem = Number(
|
|
1086
|
-
firstItem.value.replace(/\D/g, "")
|
|
1086
|
+
firstItem.value.replace(/\D/g, "")
|
|
1087
1087
|
);
|
|
1088
1088
|
const numericValueOfSecondItem = Number(
|
|
1089
|
-
secondItem.value.replace(/\D/g, "")
|
|
1089
|
+
secondItem.value.replace(/\D/g, "")
|
|
1090
1090
|
);
|
|
1091
1091
|
|
|
1092
1092
|
return numericValueOfFirstItem - numericValueOfSecondItem;
|
|
1093
|
-
}
|
|
1093
|
+
}
|
|
1094
1094
|
);
|
|
1095
1095
|
|
|
1096
1096
|
startRange.value = props.start.toString();
|
|
@@ -1107,7 +1107,7 @@ watch(startRange, (newVal: any, oldVal: any) => {
|
|
|
1107
1107
|
|
|
1108
1108
|
const endRangeKeys = computed(() => {
|
|
1109
1109
|
return resultKeys2.value.filter(
|
|
1110
|
-
(item: any) => item.value >= startRange.value
|
|
1110
|
+
(item: any) => item.value >= startRange.value
|
|
1111
1111
|
);
|
|
1112
1112
|
});
|
|
1113
1113
|
const message = ref("");
|
|
@@ -1127,7 +1127,7 @@ const showSnackbarEndRange = () => {
|
|
|
1127
1127
|
? "Please select a start range first."
|
|
1128
1128
|
: `No ${tab.value == "key" ? "Key" : "Pass"} found. Please try to
|
|
1129
1129
|
generate first.`,
|
|
1130
|
-
"error"
|
|
1130
|
+
"error"
|
|
1131
1131
|
);
|
|
1132
1132
|
}
|
|
1133
1133
|
};
|
|
@@ -54,7 +54,7 @@
|
|
|
54
54
|
|
|
55
55
|
<v-col v-if="shouldShowField('nric')" cols="12">
|
|
56
56
|
<InputLabel class="text-capitalize" title="NRIC" required />
|
|
57
|
-
<InputNRICNumber v-model="vehicle.nric" density="comfortable" :rules="[requiredRule]" :disabled="disablePrefilledInputs" />
|
|
57
|
+
<InputNRICNumber v-model="vehicle.nric" density="comfortable" :rules="[requiredRule]" :disabled="disablePrefilledInputs && type !== 'blocklist'" />
|
|
58
58
|
</v-col>
|
|
59
59
|
|
|
60
60
|
<v-col v-if="shouldShowField('name')" cols="12">
|
|
@@ -184,7 +184,7 @@
|
|
|
184
184
|
</v-toolbar>
|
|
185
185
|
|
|
186
186
|
<v-dialog v-model="showMatchingPeopleDialog" max-width="700" persistent>
|
|
187
|
-
<v-card :loading="
|
|
187
|
+
<v-card :loading="checkingUnit">
|
|
188
188
|
<v-toolbar>
|
|
189
189
|
<v-toolbar-title>
|
|
190
190
|
<v-row no-gutters class="d-flex align-center justify-space-between">
|
|
@@ -192,14 +192,14 @@
|
|
|
192
192
|
Matching Records for "{{ searchUnitName ?? "-" }}"
|
|
193
193
|
</span>
|
|
194
194
|
<span>
|
|
195
|
-
<v-btn
|
|
196
|
-
@click="
|
|
195
|
+
<v-btn icon="mdi-close" variant="text"
|
|
196
|
+
@click="handleCloseMatchDialog" />
|
|
197
197
|
</span>
|
|
198
198
|
</v-row>
|
|
199
199
|
</v-toolbar-title>
|
|
200
200
|
</v-toolbar>
|
|
201
201
|
|
|
202
|
-
<v-card-text>
|
|
202
|
+
<v-card-text max-height="400" style="overflow-y: auto">
|
|
203
203
|
|
|
204
204
|
<v-list lines="three">
|
|
205
205
|
<v-list-item v-if="matchingPeople.length > 0 || checkingUnit" v-for="v in matchingPeople" :key="v._id"
|
|
@@ -743,6 +743,13 @@ const resetVehicleDetails = () => {
|
|
|
743
743
|
}
|
|
744
744
|
|
|
745
745
|
|
|
746
|
+
function handleCloseMatchDialog() {
|
|
747
|
+
showMatchingPeopleDialog.value = false;
|
|
748
|
+
if(matchingPeople.value.length > 0) {
|
|
749
|
+
vehicle.unit = null
|
|
750
|
+
}
|
|
751
|
+
}
|
|
752
|
+
|
|
746
753
|
|
|
747
754
|
|
|
748
755
|
|
|
@@ -89,17 +89,18 @@
|
|
|
89
89
|
</DialogUpdateMoreAction>
|
|
90
90
|
</v-dialog>
|
|
91
91
|
<v-dialog v-model="dialog.deleteVehicle" persistent width="540">
|
|
92
|
-
<DialogDeleteConfirmation :
|
|
92
|
+
<DialogDeleteConfirmation :loading="deletingVehicle" :prompt-title="`Are you sure want to delete this vehicle - ${selectedPlateNumberObject?.plateNumber}?`"
|
|
93
93
|
@delete="submitDelete" @close="closeDeleteDialog" />
|
|
94
94
|
</v-dialog>
|
|
95
95
|
<v-dialog v-model="dialog.approveVehicle" persistent width="540">
|
|
96
|
-
<DialogReusablePrompt :
|
|
96
|
+
<DialogReusablePrompt :loading="approvingVehicle" :prompt-title="`Are you sure want to approve this vehicle - ${selectedPlateNumberObject?.plateNumber}?`"
|
|
97
97
|
@approve="submitApprove" @close="dialog.approveVehicle = false" />
|
|
98
98
|
</v-dialog>
|
|
99
99
|
<v-dialog v-model="dialog.restoreVehicle" persistent width="540">
|
|
100
|
-
<DialogReusablePrompt :
|
|
101
|
-
@
|
|
100
|
+
<DialogReusablePrompt :loading="restoringVehicle" :prompt-title="`Are you sure want to restore this vehicle - ${selectedPlateNumberObject?.plateNumber}?`"
|
|
101
|
+
@proceed="submitRestore" @close="dialog.restoreVehicle = false" />
|
|
102
102
|
</v-dialog>
|
|
103
|
+
<Snackbar v-model="messageSnackbar" :text="message" :color="messageColor" />
|
|
103
104
|
</v-row>
|
|
104
105
|
</template>
|
|
105
106
|
|
|
@@ -199,7 +200,7 @@ const formattedFields: Partial<Record<keyof TVehicle, string>> = {
|
|
|
199
200
|
nric: "NRIC",
|
|
200
201
|
block: "Block",
|
|
201
202
|
level: "Level",
|
|
202
|
-
|
|
203
|
+
unitName: "Unit",
|
|
203
204
|
start: "Start",
|
|
204
205
|
end: "End",
|
|
205
206
|
category: "Category",
|
|
@@ -365,7 +366,10 @@ async function submitDelete() {
|
|
|
365
366
|
|
|
366
367
|
async function submitRestore() {
|
|
367
368
|
|
|
369
|
+
console.log("Submitting restore for plate number ID:", selectedPlateNumberObject.value);
|
|
368
370
|
const plateNumberId = selectedPlateNumberObject.value?._id;
|
|
371
|
+
|
|
372
|
+
|
|
369
373
|
if (!plateNumberId) {
|
|
370
374
|
showMessage("Invalid plate number selected for restoration.", "error");
|
|
371
375
|
return;
|
|
@@ -382,7 +386,9 @@ async function submitRestore() {
|
|
|
382
386
|
getVehiclesRefresh();
|
|
383
387
|
} catch (error: any) {
|
|
384
388
|
console.error("Error restoring vehicle:", error);
|
|
385
|
-
|
|
389
|
+
const errMessage = error?.response?._data?.message || "Failed to restore vehicle";
|
|
390
|
+
showMessage(errMessage, "error");
|
|
391
|
+
// message.value = error.response._data.message;
|
|
386
392
|
} finally {
|
|
387
393
|
restoringVehicle.value = false;
|
|
388
394
|
}
|
|
@@ -408,7 +414,8 @@ async function submitApprove() {
|
|
|
408
414
|
getVehiclesRefresh();
|
|
409
415
|
} catch (error: any) {
|
|
410
416
|
console.error("Error approving vehicle:", error);
|
|
411
|
-
|
|
417
|
+
const errMessage = error?.response?._data?.message || "Failed to approve vehicle";
|
|
418
|
+
showMessage(errMessage, "error");
|
|
412
419
|
} finally {
|
|
413
420
|
approvingVehicle.value = false;
|
|
414
421
|
}
|
|
@@ -57,7 +57,7 @@ export default function useAttendance() {
|
|
|
57
57
|
);
|
|
58
58
|
}
|
|
59
59
|
|
|
60
|
-
function getAttendanceSettings(site: string, serviceType: string) {
|
|
60
|
+
function getAttendanceSettings(site: string, serviceType: string = "") {
|
|
61
61
|
return useNuxtApp().$api<TAttendanceSettings>(
|
|
62
62
|
`/api/attendance-settings/site/${site}`,
|
|
63
63
|
{
|
|
@@ -69,13 +69,14 @@ export default function useAttendance() {
|
|
|
69
69
|
|
|
70
70
|
function updateAttendanceSettings(
|
|
71
71
|
site: string,
|
|
72
|
-
payload: TAttendanceSettings
|
|
72
|
+
payload: TAttendanceSettings,
|
|
73
|
+
serviceType: string = ""
|
|
73
74
|
) {
|
|
74
75
|
return useNuxtApp().$api<Record<string, any>>(
|
|
75
76
|
`/api/attendance-settings/site/${site}`,
|
|
76
77
|
{
|
|
77
78
|
method: "PUT",
|
|
78
|
-
body: payload,
|
|
79
|
+
body: { ...payload, serviceType },
|
|
79
80
|
}
|
|
80
81
|
);
|
|
81
82
|
}
|
|
@@ -75,7 +75,7 @@ export default function useVehicle() {
|
|
|
75
75
|
|
|
76
76
|
async function approveVehicle({ site, org, id }: { site: string, org: string, id: string}){
|
|
77
77
|
return await useNuxtApp().$api<Record<string, any>>(
|
|
78
|
-
`/api/vehicles/approve
|
|
78
|
+
`/api/vehicles/approve/${id}`,
|
|
79
79
|
{
|
|
80
80
|
method: "PUT",
|
|
81
81
|
body: {
|