@7365admin1/core 2.22.0 → 2.23.0
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 +6 -0
- package/dist/index.d.ts +66 -4
- package/dist/index.js +1008 -118
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +1222 -329
- package/dist/index.mjs.map +1 -1
- package/dist/public/handlebars/alert-email.hbs +43 -0
- package/package.json +2 -1
package/dist/index.js
CHANGED
|
@@ -69,6 +69,7 @@ __export(src_exports, {
|
|
|
69
69
|
MManpowerDesignations: () => MManpowerDesignations,
|
|
70
70
|
MManpowerMonitoring: () => MManpowerMonitoring,
|
|
71
71
|
MManpowerRemarks: () => MManpowerRemarks,
|
|
72
|
+
MManpowerSites: () => MManpowerSites,
|
|
72
73
|
MMember: () => MMember,
|
|
73
74
|
MNfcPatrolLog: () => MNfcPatrolLog,
|
|
74
75
|
MNfcPatrolRoute: () => MNfcPatrolRoute,
|
|
@@ -134,6 +135,7 @@ __export(src_exports, {
|
|
|
134
135
|
bulletin_boards_namespace_collection: () => bulletin_boards_namespace_collection,
|
|
135
136
|
calculatePercentage: () => calculatePercentage,
|
|
136
137
|
chatSchema: () => chatSchema,
|
|
138
|
+
createManpowerRemarksDaily: () => createManpowerRemarksDaily,
|
|
137
139
|
customerSchema: () => customerSchema,
|
|
138
140
|
designationsSchema: () => designationsSchema,
|
|
139
141
|
events_namespace_collection: () => events_namespace_collection,
|
|
@@ -148,10 +150,13 @@ __export(src_exports, {
|
|
|
148
150
|
landscapeDashboardCollection: () => landscapeDashboardCollection,
|
|
149
151
|
mAndEDashboardCollection: () => mAndEDashboardCollection,
|
|
150
152
|
manpowerDesignationsSchema: () => manpowerDesignationsSchema,
|
|
153
|
+
manpowerEvents: () => manpowerEvents,
|
|
151
154
|
manpowerMonitoringSchema: () => manpowerMonitoringSchema,
|
|
152
155
|
manpowerRemarksSchema: () => manpowerRemarksSchema,
|
|
156
|
+
manpowerSitesSchema: () => manpowerSitesSchema,
|
|
153
157
|
nfcPatrolSettingsSchema: () => nfcPatrolSettingsSchema,
|
|
154
158
|
nfcPatrolSettingsSchemaUpdate: () => nfcPatrolSettingsSchemaUpdate,
|
|
159
|
+
occurrence_book_namespace_collection: () => occurrence_book_namespace_collection,
|
|
155
160
|
orgSchema: () => orgSchema,
|
|
156
161
|
overnight_parking_requests_namespace_collection: () => overnight_parking_requests_namespace_collection,
|
|
157
162
|
pestDashboardCollection: () => pestDashboardCollection,
|
|
@@ -232,6 +237,8 @@ __export(src_exports, {
|
|
|
232
237
|
siteSchema: () => siteSchema,
|
|
233
238
|
site_people_namespace_collection: () => site_people_namespace_collection,
|
|
234
239
|
tokenSchema: () => tokenSchema,
|
|
240
|
+
updateRemarksStatusEod: () => updateRemarksStatusEod,
|
|
241
|
+
updateRemarksisAcknowledged: () => updateRemarksisAcknowledged,
|
|
235
242
|
updateSiteSchema: () => updateSiteSchema,
|
|
236
243
|
useAccessManagementController: () => useAccessManagementController,
|
|
237
244
|
useAddressRepo: () => useAddressRepo,
|
|
@@ -298,6 +305,9 @@ __export(src_exports, {
|
|
|
298
305
|
useManpowerMonitoringSrvc: () => useManpowerMonitoringSrvc,
|
|
299
306
|
useManpowerRemarkCtrl: () => useManpowerRemarkCtrl,
|
|
300
307
|
useManpowerRemarksRepo: () => useManpowerRemarksRepo,
|
|
308
|
+
useManpowerSitesCtrl: () => useManpowerSitesCtrl,
|
|
309
|
+
useManpowerSitesRepo: () => useManpowerSitesRepo,
|
|
310
|
+
useManpowerSitesSrvc: () => useManpowerSitesSrvc,
|
|
301
311
|
useMemberController: () => useMemberController,
|
|
302
312
|
useMemberRepo: () => useMemberRepo,
|
|
303
313
|
useNewDashboardController: () => useNewDashboardController,
|
|
@@ -12990,7 +13000,8 @@ var schemaPerson = import_joi35.default.object({
|
|
|
12990
13000
|
companyName: import_joi35.default.array().items(import_joi35.default.string()).optional(),
|
|
12991
13001
|
plates: import_joi35.default.array().items(schemaPlate).optional().allow(null),
|
|
12992
13002
|
isOwner: import_joi35.default.boolean().required(),
|
|
12993
|
-
files: import_joi35.default.array().items(schemaFiles).optional().allow(null)
|
|
13003
|
+
files: import_joi35.default.array().items(schemaFiles).optional().allow(null),
|
|
13004
|
+
password: import_joi35.default.string().optional().allow(null, "")
|
|
12994
13005
|
});
|
|
12995
13006
|
var schemaUpdatePerson = import_joi35.default.object({
|
|
12996
13007
|
_id: import_joi35.default.string().hex().required(),
|
|
@@ -13009,7 +13020,8 @@ var schemaUpdatePerson = import_joi35.default.object({
|
|
|
13009
13020
|
companyName: import_joi35.default.array().items(import_joi35.default.string()).optional().allow(null, ""),
|
|
13010
13021
|
plates: import_joi35.default.array().items(schemaFiles).optional().allow(null, ""),
|
|
13011
13022
|
isOwner: import_joi35.default.boolean().optional().allow(null, ""),
|
|
13012
|
-
files: import_joi35.default.array().items(schemaFiles).optional().allow(null)
|
|
13023
|
+
files: import_joi35.default.array().items(schemaFiles).optional().allow(null),
|
|
13024
|
+
password: import_joi35.default.string().optional().allow(null, "")
|
|
13013
13025
|
});
|
|
13014
13026
|
function MPerson(value) {
|
|
13015
13027
|
const { error } = schemaPerson.validate(value);
|
|
@@ -13060,6 +13072,7 @@ function MPerson(value) {
|
|
|
13060
13072
|
end: value.end,
|
|
13061
13073
|
type: value.type,
|
|
13062
13074
|
email: value.email,
|
|
13075
|
+
password: value.password ?? "",
|
|
13063
13076
|
status: value.status ?? "active",
|
|
13064
13077
|
nric: value.nric,
|
|
13065
13078
|
remarks: value.remarks,
|
|
@@ -13609,6 +13622,8 @@ var VehicleSort = /* @__PURE__ */ ((VehicleSort2) => {
|
|
|
13609
13622
|
VehicleSort2["CREATED_AT"] = "createdAt";
|
|
13610
13623
|
VehicleSort2["ID"] = "_id";
|
|
13611
13624
|
VehicleSort2["NAME"] = "name";
|
|
13625
|
+
VehicleSort2["START"] = "start";
|
|
13626
|
+
VehicleSort2["END"] = "end";
|
|
13612
13627
|
return VehicleSort2;
|
|
13613
13628
|
})(VehicleSort || {});
|
|
13614
13629
|
var OrgNature = /* @__PURE__ */ ((OrgNature2) => {
|
|
@@ -13761,6 +13776,7 @@ var import_mongodb41 = require("mongodb");
|
|
|
13761
13776
|
var import_joi38 = __toESM(require("joi"));
|
|
13762
13777
|
var vehicles_namespace_collection = "vehicles";
|
|
13763
13778
|
function useVehicleRepo() {
|
|
13779
|
+
vehicles_namespace_collection;
|
|
13764
13780
|
const db = import_node_server_utils69.useAtlas.getDb();
|
|
13765
13781
|
if (!db) {
|
|
13766
13782
|
throw new import_node_server_utils69.InternalServerError("Unable to connect to server.");
|
|
@@ -18238,11 +18254,13 @@ function useVehicleController() {
|
|
|
18238
18254
|
getAllVehiclesByUnitId: _getAllVehiclesByUnitId
|
|
18239
18255
|
} = useVehicleRepo();
|
|
18240
18256
|
async function add(req, res, next) {
|
|
18241
|
-
const
|
|
18242
|
-
|
|
18257
|
+
const { error, value } = vehicleSchema.validate(req.body, {
|
|
18258
|
+
abortEarly: false
|
|
18259
|
+
});
|
|
18243
18260
|
if (error) {
|
|
18244
|
-
|
|
18245
|
-
|
|
18261
|
+
const messages = error.details.map((d) => d.message).join(", ");
|
|
18262
|
+
import_node_server_utils85.logger.log({ level: "error", message: messages });
|
|
18263
|
+
next(new import_node_server_utils85.BadRequestError(messages));
|
|
18246
18264
|
return;
|
|
18247
18265
|
}
|
|
18248
18266
|
try {
|
|
@@ -18258,40 +18276,29 @@ function useVehicleController() {
|
|
|
18258
18276
|
}
|
|
18259
18277
|
}
|
|
18260
18278
|
async function getVehicles(req, res, next) {
|
|
18261
|
-
const
|
|
18262
|
-
const allowedOrder = ["asc", "desc"];
|
|
18263
|
-
const validation = import_joi46.default.object({
|
|
18279
|
+
const schema2 = import_joi46.default.object({
|
|
18264
18280
|
search: import_joi46.default.string().optional().allow("", null),
|
|
18265
|
-
page: import_joi46.default.number().integer().min(1).
|
|
18266
|
-
limit: import_joi46.default.number().integer().min(1).max(100).
|
|
18267
|
-
sort: import_joi46.default.string().
|
|
18268
|
-
order: import_joi46.default.string().
|
|
18281
|
+
page: import_joi46.default.number().integer().min(1).optional().default(1),
|
|
18282
|
+
limit: import_joi46.default.number().integer().min(1).max(100).optional().default(10),
|
|
18283
|
+
sort: import_joi46.default.string().optional().valid(...Object.values(VehicleSort)),
|
|
18284
|
+
order: import_joi46.default.string().optional().valid(...Object.values(SortOrder)),
|
|
18269
18285
|
type: import_joi46.default.string().optional().valid(...Object.values(VehicleType)).allow(null, ""),
|
|
18270
18286
|
category: import_joi46.default.string().optional().valid(...Object.values(VehicleCategory)).allow(null, ""),
|
|
18271
18287
|
status: import_joi46.default.string().optional().valid(...Object.values(VehicleStatus)).allow(null, "")
|
|
18272
18288
|
});
|
|
18273
|
-
const
|
|
18274
|
-
|
|
18289
|
+
const { error, value } = schema2.validate(req.query, {
|
|
18290
|
+
abortEarly: false
|
|
18291
|
+
});
|
|
18275
18292
|
if (error) {
|
|
18276
|
-
|
|
18277
|
-
|
|
18293
|
+
const messages = error.details.map((d) => d.message).join(", ");
|
|
18294
|
+
import_node_server_utils85.logger.log({ level: "error", message: messages });
|
|
18295
|
+
next(new import_node_server_utils85.BadRequestError(messages));
|
|
18278
18296
|
return;
|
|
18279
18297
|
}
|
|
18280
|
-
const search
|
|
18281
|
-
const
|
|
18282
|
-
|
|
18283
|
-
|
|
18284
|
-
const category = req.query.category ?? "";
|
|
18285
|
-
const status = req.query.status ?? "";
|
|
18286
|
-
const sortObj = {};
|
|
18287
|
-
const sortFields = String(req.query.sort).split(",");
|
|
18288
|
-
const sortOrders = String(req.query.order).split(",");
|
|
18289
|
-
sortFields.forEach((field, index) => {
|
|
18290
|
-
if (allowedFields.includes(field)) {
|
|
18291
|
-
const order = sortOrders[index] === "asc" ? 1 : -1;
|
|
18292
|
-
sortObj[field] = order;
|
|
18293
|
-
}
|
|
18294
|
-
});
|
|
18298
|
+
const { search, page, limit, type, category, status, sort, order } = value;
|
|
18299
|
+
const sortObj = {
|
|
18300
|
+
[sort ? sort : "_id" /* ID */]: order === "asc" /* ASC */ ? 1 : -1
|
|
18301
|
+
};
|
|
18295
18302
|
try {
|
|
18296
18303
|
const data = await _getVehicles({
|
|
18297
18304
|
search,
|
|
@@ -18311,14 +18318,20 @@ function useVehicleController() {
|
|
|
18311
18318
|
}
|
|
18312
18319
|
}
|
|
18313
18320
|
async function getSeasonPassTypes(req, res, next) {
|
|
18314
|
-
const
|
|
18315
|
-
|
|
18316
|
-
|
|
18321
|
+
const schema2 = import_joi46.default.object({
|
|
18322
|
+
site: import_joi46.default.string().hex().length(24).required()
|
|
18323
|
+
});
|
|
18324
|
+
const { error, value } = schema2.validate(
|
|
18325
|
+
{ site: req.params.site },
|
|
18326
|
+
{ abortEarly: false }
|
|
18327
|
+
);
|
|
18317
18328
|
if (error) {
|
|
18318
|
-
|
|
18319
|
-
|
|
18329
|
+
const messages = error.details.map((d) => d.message).join(", ");
|
|
18330
|
+
import_node_server_utils85.logger.log({ level: "error", message: messages });
|
|
18331
|
+
next(new import_node_server_utils85.BadRequestError(messages));
|
|
18320
18332
|
return;
|
|
18321
18333
|
}
|
|
18334
|
+
const { site } = value;
|
|
18322
18335
|
try {
|
|
18323
18336
|
const data = await _getSeasonPassTypes(site);
|
|
18324
18337
|
res.json(data);
|
|
@@ -18330,14 +18343,20 @@ function useVehicleController() {
|
|
|
18330
18343
|
}
|
|
18331
18344
|
}
|
|
18332
18345
|
async function getVehicleById(req, res, next) {
|
|
18333
|
-
const
|
|
18334
|
-
|
|
18335
|
-
|
|
18346
|
+
const schema2 = import_joi46.default.object({
|
|
18347
|
+
_id: import_joi46.default.string().hex().length(24).required()
|
|
18348
|
+
});
|
|
18349
|
+
const { error, value } = schema2.validate(
|
|
18350
|
+
{ _id: req.params.id },
|
|
18351
|
+
{ abortEarly: false }
|
|
18352
|
+
);
|
|
18336
18353
|
if (error) {
|
|
18337
|
-
|
|
18338
|
-
|
|
18354
|
+
const messages = error.details.map((d) => d.message).join(", ");
|
|
18355
|
+
import_node_server_utils85.logger.log({ level: "error", message: messages });
|
|
18356
|
+
next(new import_node_server_utils85.BadRequestError(messages));
|
|
18339
18357
|
return;
|
|
18340
18358
|
}
|
|
18359
|
+
const { _id } = value;
|
|
18341
18360
|
try {
|
|
18342
18361
|
const site = await _getVehicleById(_id);
|
|
18343
18362
|
res.json(site);
|
|
@@ -18350,7 +18369,7 @@ function useVehicleController() {
|
|
|
18350
18369
|
}
|
|
18351
18370
|
async function updateVehicleById(req, res, next) {
|
|
18352
18371
|
try {
|
|
18353
|
-
const
|
|
18372
|
+
const schema2 = import_joi46.default.object({
|
|
18354
18373
|
_id: import_joi46.default.string().hex().length(24).required(),
|
|
18355
18374
|
site: import_joi46.default.string().hex().length(24).required(),
|
|
18356
18375
|
name: import_joi46.default.string().optional().allow("", null),
|
|
@@ -18365,13 +18384,17 @@ function useVehicleController() {
|
|
|
18365
18384
|
recNo: import_joi46.default.string().optional().allow(null, ""),
|
|
18366
18385
|
type: import_joi46.default.string().optional().valid(...Object.values(VehicleType)).allow(null, "")
|
|
18367
18386
|
});
|
|
18368
|
-
const { error, value } =
|
|
18369
|
-
|
|
18370
|
-
|
|
18371
|
-
|
|
18387
|
+
const { error, value } = schema2.validate(
|
|
18388
|
+
{
|
|
18389
|
+
_id: req.params.id,
|
|
18390
|
+
...req.body
|
|
18391
|
+
},
|
|
18392
|
+
{ abortEarly: false }
|
|
18393
|
+
);
|
|
18372
18394
|
if (error) {
|
|
18373
|
-
|
|
18374
|
-
|
|
18395
|
+
const messages = error.details.map((d) => d.message).join(", ");
|
|
18396
|
+
import_node_server_utils85.logger.log({ level: "error", message: messages });
|
|
18397
|
+
next(new import_node_server_utils85.BadRequestError(messages));
|
|
18375
18398
|
return;
|
|
18376
18399
|
}
|
|
18377
18400
|
const { _id, ...rest } = value;
|
|
@@ -18385,21 +18408,24 @@ function useVehicleController() {
|
|
|
18385
18408
|
}
|
|
18386
18409
|
}
|
|
18387
18410
|
async function deleteVehicle(req, res, next) {
|
|
18388
|
-
const _id = req.params.id;
|
|
18389
18411
|
const deleteVehicleSchema = import_joi46.default.object({
|
|
18390
18412
|
_id: import_joi46.default.string().hex().length(24).required(),
|
|
18391
18413
|
recno: import_joi46.default.string().required(),
|
|
18392
18414
|
site: import_joi46.default.string().hex().length(24).required(),
|
|
18393
|
-
type: import_joi46.default.string().valid(
|
|
18415
|
+
type: import_joi46.default.string().valid(...Object.values(VehicleType)).required(),
|
|
18394
18416
|
bypass: import_joi46.default.boolean().optional().default(true)
|
|
18395
18417
|
});
|
|
18396
|
-
const { error, value } = deleteVehicleSchema.validate({
|
|
18418
|
+
const { error, value } = deleteVehicleSchema.validate({
|
|
18419
|
+
_id: req.params.id,
|
|
18420
|
+
...req.body
|
|
18421
|
+
});
|
|
18397
18422
|
if (error) {
|
|
18398
|
-
|
|
18399
|
-
|
|
18423
|
+
const messages = error.details.map((d) => d.message).join(", ");
|
|
18424
|
+
import_node_server_utils85.logger.log({ level: "error", message: messages });
|
|
18425
|
+
next(new import_node_server_utils85.BadRequestError(messages));
|
|
18400
18426
|
return;
|
|
18401
18427
|
}
|
|
18402
|
-
const { recno, site, type, bypass } = value;
|
|
18428
|
+
const { recno, site, type, bypass, _id } = value;
|
|
18403
18429
|
try {
|
|
18404
18430
|
const data = await _deleteVehicle(_id, recno, site, type, bypass);
|
|
18405
18431
|
res.json({
|
|
@@ -21173,9 +21199,19 @@ function usePersonService() {
|
|
|
21173
21199
|
updateById: _updateById
|
|
21174
21200
|
} = usePersonRepo();
|
|
21175
21201
|
const { addPlateNumber: _addPlateNumber } = useDahuaService();
|
|
21202
|
+
const {
|
|
21203
|
+
createUser: addUser,
|
|
21204
|
+
getUserById,
|
|
21205
|
+
getUserByEmail,
|
|
21206
|
+
updatePassword,
|
|
21207
|
+
updateUserFieldById: _updateUserFieldById
|
|
21208
|
+
} = useUserRepo();
|
|
21209
|
+
const { add: addMember } = useMemberRepo();
|
|
21176
21210
|
const { getById: _getUnitById, updateById: updateUnitById } = useBuildingUnitRepo();
|
|
21177
21211
|
const { getAllCameraWithPassword: _getAllSiteCameras } = useSiteCameraRepo();
|
|
21178
21212
|
const { updateStatusById } = useFileRepo();
|
|
21213
|
+
const { getById: getOrgById } = useOrgRepo();
|
|
21214
|
+
const { getSiteById } = useSiteRepo();
|
|
21179
21215
|
async function add(value) {
|
|
21180
21216
|
const session = import_node_server_utils104.useAtlas.getClient()?.startSession();
|
|
21181
21217
|
if (!session) {
|
|
@@ -21196,6 +21232,49 @@ function usePersonService() {
|
|
|
21196
21232
|
}
|
|
21197
21233
|
}
|
|
21198
21234
|
}
|
|
21235
|
+
const isValidType = ["resident" /* RESIDENT */, "tenant" /* TENANT */].includes(
|
|
21236
|
+
value?.type
|
|
21237
|
+
);
|
|
21238
|
+
if (value.email && value.password && value.name && isValidType) {
|
|
21239
|
+
const _user = await getUserByEmail(value.email);
|
|
21240
|
+
if (_user) {
|
|
21241
|
+
throw new import_node_server_utils104.BadRequestError(`User already exists: ${value.email}.`);
|
|
21242
|
+
}
|
|
21243
|
+
const hashedPassword = await (0, import_node_server_utils104.hashPassword)(value.password);
|
|
21244
|
+
const user = {
|
|
21245
|
+
email: value.email,
|
|
21246
|
+
password: hashedPassword,
|
|
21247
|
+
name: value.name,
|
|
21248
|
+
defaultOrg: value.org?.toString() || ""
|
|
21249
|
+
};
|
|
21250
|
+
const userId = await addUser(user, session);
|
|
21251
|
+
let org = null;
|
|
21252
|
+
if (userId) {
|
|
21253
|
+
if (value?.org) {
|
|
21254
|
+
org = await getOrgById(value.org);
|
|
21255
|
+
if (!org) {
|
|
21256
|
+
value.org = "";
|
|
21257
|
+
}
|
|
21258
|
+
}
|
|
21259
|
+
let site;
|
|
21260
|
+
if (value.site) {
|
|
21261
|
+
site = await getSiteById(value.site);
|
|
21262
|
+
}
|
|
21263
|
+
await addMember(
|
|
21264
|
+
{
|
|
21265
|
+
org: value.org?.toString() || "",
|
|
21266
|
+
orgName: org?.name || "",
|
|
21267
|
+
user: userId.toString(),
|
|
21268
|
+
name: value.name,
|
|
21269
|
+
role: "",
|
|
21270
|
+
type: "resident",
|
|
21271
|
+
siteId: value.site?.toString() || "",
|
|
21272
|
+
siteName: site?.name || ""
|
|
21273
|
+
},
|
|
21274
|
+
session
|
|
21275
|
+
);
|
|
21276
|
+
}
|
|
21277
|
+
}
|
|
21199
21278
|
await _add(value, session);
|
|
21200
21279
|
await session.commitTransaction();
|
|
21201
21280
|
return "People added successfully.";
|
|
@@ -25566,14 +25645,17 @@ function useSiteFacilityBookingController() {
|
|
|
25566
25645
|
}
|
|
25567
25646
|
}
|
|
25568
25647
|
async function deleteSiteFacilityBookingById(req, res, next) {
|
|
25569
|
-
const
|
|
25570
|
-
|
|
25571
|
-
|
|
25648
|
+
const schema2 = import_joi72.default.object({
|
|
25649
|
+
_id: import_joi72.default.string().hex().length(24).required()
|
|
25650
|
+
});
|
|
25651
|
+
const { error, value } = schema2.validate({ _id: req.params.id });
|
|
25572
25652
|
if (error) {
|
|
25573
|
-
|
|
25574
|
-
|
|
25653
|
+
const messages = error.details.map((d) => d.message).join(", ");
|
|
25654
|
+
import_node_server_utils128.logger.log({ level: "error", message: messages });
|
|
25655
|
+
next(new import_node_server_utils128.BadRequestError(messages));
|
|
25575
25656
|
return;
|
|
25576
25657
|
}
|
|
25658
|
+
const { _id } = value;
|
|
25577
25659
|
try {
|
|
25578
25660
|
await _deleteSiteFacilityBookingById(_id);
|
|
25579
25661
|
res.status(200).json({ message: "Successfully deleted site facility booking." });
|
|
@@ -29582,6 +29664,7 @@ var import_mongodb84 = require("mongodb");
|
|
|
29582
29664
|
var import_fs2 = __toESM(require("fs"));
|
|
29583
29665
|
var import_path = __toESM(require("path"));
|
|
29584
29666
|
var import_axios = __toESM(require("axios"));
|
|
29667
|
+
var import_xml2js = require("xml2js");
|
|
29585
29668
|
var import_crypto = __toESM(require("crypto"));
|
|
29586
29669
|
var ALGORITHM = "aes-256-gcm";
|
|
29587
29670
|
var SECRET_KEY = import_crypto.default.createSecretKey(
|
|
@@ -29682,9 +29765,39 @@ var formatEntryPassDate = (date) => {
|
|
|
29682
29765
|
const day = String(newDate.getDate()).padStart(2, "0");
|
|
29683
29766
|
return `${year}${month}${day}`;
|
|
29684
29767
|
};
|
|
29768
|
+
async function removeAccessGroup({ cardNo, staffNo, url }) {
|
|
29769
|
+
try {
|
|
29770
|
+
const commands = readTemplate("delete-qr-card", {
|
|
29771
|
+
staffNo,
|
|
29772
|
+
// dateOfJoin: formatEntryPassDate(cardDetails.startDate),
|
|
29773
|
+
// accessLevel: cardDetails.accessLevel,
|
|
29774
|
+
cardNo
|
|
29775
|
+
// pin: cardDetails.pin,
|
|
29776
|
+
// startDate: formatEntryPassDate(cardDetails.startDate),
|
|
29777
|
+
// endDate: formatEntryPassDate(cardDetails.endDate),
|
|
29778
|
+
// cardType: 0,
|
|
29779
|
+
// isActivated: cardDetails.isActivated ? 1 : 0,
|
|
29780
|
+
// isAntiPassBack: cardDetails.isAntiPassBack ? 1 : 0,
|
|
29781
|
+
// isLiftCard: cardDetails.isLiftCard ? 1 : 0,
|
|
29782
|
+
// isLiftActivate: cardDetails.isLiftCard ? 1 : 0,
|
|
29783
|
+
// liftAccessLevel: cardDetails.liftAccessLevel || 1,
|
|
29784
|
+
// liftAccessStartDate: formatEntryPassDate(cardDetails.liftAccessStartDate) || "19770510",
|
|
29785
|
+
// liftAccessEndDate: formatEntryPassDate(cardDetails.liftAccessEndDate) || "19770510",
|
|
29786
|
+
});
|
|
29787
|
+
const response = await sendCommand(commands, url);
|
|
29788
|
+
const result = await (0, import_xml2js.parseStringPromise)(response, { explicitArray: false });
|
|
29789
|
+
console.log(result.RESULT.$.STCODE);
|
|
29790
|
+
console.log(commands);
|
|
29791
|
+
if (result && result.RESULT.$.STCODE !== "0") {
|
|
29792
|
+
throw new Error("Command failed, server error.");
|
|
29793
|
+
}
|
|
29794
|
+
} catch (error) {
|
|
29795
|
+
console.log(error);
|
|
29796
|
+
}
|
|
29797
|
+
}
|
|
29685
29798
|
|
|
29686
29799
|
// src/repositories/access-management.repo.ts
|
|
29687
|
-
var
|
|
29800
|
+
var import_xml2js2 = require("xml2js");
|
|
29688
29801
|
|
|
29689
29802
|
// src/utils/rsa-encryption.ts
|
|
29690
29803
|
var crypto2 = __toESM(require("crypto"));
|
|
@@ -30693,7 +30806,7 @@ function UseAccessManagementRepo() {
|
|
|
30693
30806
|
return readTemplate(`${item.accessLevel !== null ? "add-card" : "add-card-lift"}`, { ...command });
|
|
30694
30807
|
}).flat();
|
|
30695
30808
|
const response = await sendCommand(commands.join("").toString(), params.acm_url);
|
|
30696
|
-
const result = await (0,
|
|
30809
|
+
const result = await (0, import_xml2js2.parseStringPromise)(response, { explicitArray: false });
|
|
30697
30810
|
if (result && result.RESULT.$.STCODE !== "0") {
|
|
30698
30811
|
throw new Error("Command failed, server error.");
|
|
30699
30812
|
}
|
|
@@ -31554,7 +31667,7 @@ function UseAccessManagementRepo() {
|
|
|
31554
31667
|
return readTemplate(`${item.accessLevel !== null ? "add-card" : "add-card-lift"}`, { ...command });
|
|
31555
31668
|
}).flat();
|
|
31556
31669
|
const response = await sendCommand(commands.join("").toString(), acm_url);
|
|
31557
|
-
serverResult = await (0,
|
|
31670
|
+
serverResult = await (0, import_xml2js2.parseStringPromise)(response, { explicitArray: false });
|
|
31558
31671
|
if (result && serverResult.RESULT.$.STCODE !== "0") {
|
|
31559
31672
|
throw new Error("Command failed, server error.");
|
|
31560
31673
|
}
|
|
@@ -31650,7 +31763,7 @@ function UseAccessManagementRepo() {
|
|
|
31650
31763
|
var import_joi85 = __toESM(require("joi"));
|
|
31651
31764
|
|
|
31652
31765
|
// src/services/access-management.service.ts
|
|
31653
|
-
var
|
|
31766
|
+
var import_xml2js3 = require("xml2js");
|
|
31654
31767
|
var import_stream = require("stream");
|
|
31655
31768
|
var xlsx = __toESM(require("xlsx"));
|
|
31656
31769
|
function useAccessManagementSvc() {
|
|
@@ -31713,7 +31826,7 @@ function useAccessManagementSvc() {
|
|
|
31713
31826
|
try {
|
|
31714
31827
|
const command = readTemplate("door-levels");
|
|
31715
31828
|
const response = await sendCommand(command, params.acm_url);
|
|
31716
|
-
const res = await (0,
|
|
31829
|
+
const res = await (0, import_xml2js3.parseStringPromise)(response, { explicitArray: false });
|
|
31717
31830
|
const format = await formatDoorAccessLevels(res);
|
|
31718
31831
|
return format;
|
|
31719
31832
|
} catch (err) {
|
|
@@ -31724,7 +31837,7 @@ function useAccessManagementSvc() {
|
|
|
31724
31837
|
try {
|
|
31725
31838
|
const command = readTemplate("lift-levels");
|
|
31726
31839
|
const response = await sendCommand(command, params.acm_url);
|
|
31727
|
-
const res = await (0,
|
|
31840
|
+
const res = await (0, import_xml2js3.parseStringPromise)(response, { explicitArray: false });
|
|
31728
31841
|
const format = await formatLiftAccessLevels(res);
|
|
31729
31842
|
return format;
|
|
31730
31843
|
} catch (error) {
|
|
@@ -31735,7 +31848,7 @@ function useAccessManagementSvc() {
|
|
|
31735
31848
|
try {
|
|
31736
31849
|
const command = readTemplate("access-group");
|
|
31737
31850
|
const response = await sendCommand(command, params.acm_url);
|
|
31738
|
-
const res = await (0,
|
|
31851
|
+
const res = await (0, import_xml2js3.parseStringPromise)(response, { explicitArray: false });
|
|
31739
31852
|
const format = await formatAccessGroup(res);
|
|
31740
31853
|
return format;
|
|
31741
31854
|
} catch (err) {
|
|
@@ -32781,6 +32894,9 @@ function useAccessManagementController() {
|
|
|
32781
32894
|
});
|
|
32782
32895
|
}
|
|
32783
32896
|
};
|
|
32897
|
+
const removeAccessCard = async ({ cardNo, staffNo, url }) => {
|
|
32898
|
+
return removeAccessGroup({ cardNo, staffNo, url });
|
|
32899
|
+
};
|
|
32784
32900
|
return {
|
|
32785
32901
|
addPhysicalCard,
|
|
32786
32902
|
addNonPhysicalCard,
|
|
@@ -32811,7 +32927,8 @@ function useAccessManagementController() {
|
|
|
32811
32927
|
vmsgenerateQrCodes,
|
|
32812
32928
|
addVisitorAccessCard,
|
|
32813
32929
|
signQrCode,
|
|
32814
|
-
checkoutVisitor
|
|
32930
|
+
checkoutVisitor,
|
|
32931
|
+
removeAccessCard
|
|
32815
32932
|
};
|
|
32816
32933
|
}
|
|
32817
32934
|
|
|
@@ -33326,6 +33443,7 @@ function MOccurrenceBook(value) {
|
|
|
33326
33443
|
// src/repositories/occurrence-book.repo.ts
|
|
33327
33444
|
var import_node_server_utils155 = require("@7365admin1/node-server-utils");
|
|
33328
33445
|
var import_mongodb88 = require("mongodb");
|
|
33446
|
+
var occurrence_book_namespace_collection = "occurrence-books";
|
|
33329
33447
|
function useOccurrenceBookRepo() {
|
|
33330
33448
|
const db = import_node_server_utils155.useAtlas.getDb();
|
|
33331
33449
|
if (!db) {
|
|
@@ -33353,18 +33471,21 @@ function useOccurrenceBookRepo() {
|
|
|
33353
33471
|
);
|
|
33354
33472
|
}
|
|
33355
33473
|
}
|
|
33356
|
-
const
|
|
33357
|
-
const
|
|
33358
|
-
|
|
33474
|
+
const collection = db.collection(occurrence_book_namespace_collection);
|
|
33475
|
+
const { delNamespace, getCache, setCache } = (0, import_node_server_utils155.useCache)(
|
|
33476
|
+
occurrence_book_namespace_collection
|
|
33477
|
+
);
|
|
33359
33478
|
async function add(value, session) {
|
|
33360
33479
|
try {
|
|
33361
33480
|
value = MOccurrenceBook(value);
|
|
33362
33481
|
const res = await collection.insertOne(value, { session });
|
|
33363
33482
|
delNamespace().then(() => {
|
|
33364
|
-
import_node_server_utils155.logger.info(
|
|
33483
|
+
import_node_server_utils155.logger.info(
|
|
33484
|
+
`Cache cleared for namespace: ${occurrence_book_namespace_collection}`
|
|
33485
|
+
);
|
|
33365
33486
|
}).catch((err) => {
|
|
33366
33487
|
import_node_server_utils155.logger.error(
|
|
33367
|
-
`Failed to clear cache for namespace: ${
|
|
33488
|
+
`Failed to clear cache for namespace: ${occurrence_book_namespace_collection}`,
|
|
33368
33489
|
err
|
|
33369
33490
|
);
|
|
33370
33491
|
});
|
|
@@ -33447,7 +33568,10 @@ function useOccurrenceBookRepo() {
|
|
|
33447
33568
|
query.$text = { $search: search };
|
|
33448
33569
|
cacheOptions.search = search;
|
|
33449
33570
|
}
|
|
33450
|
-
const cacheKey = (0, import_node_server_utils155.makeCacheKey)(
|
|
33571
|
+
const cacheKey = (0, import_node_server_utils155.makeCacheKey)(
|
|
33572
|
+
occurrence_book_namespace_collection,
|
|
33573
|
+
cacheOptions
|
|
33574
|
+
);
|
|
33451
33575
|
const cachedData = await getCache(cacheKey);
|
|
33452
33576
|
if (cachedData) {
|
|
33453
33577
|
import_node_server_utils155.logger.info(`Cache hit for key: ${cacheKey}`);
|
|
@@ -33481,7 +33605,9 @@ function useOccurrenceBookRepo() {
|
|
|
33481
33605
|
} catch (error) {
|
|
33482
33606
|
throw new import_node_server_utils155.BadRequestError("Invalid occurrence book ID format.");
|
|
33483
33607
|
}
|
|
33484
|
-
const cacheKey = (0, import_node_server_utils155.makeCacheKey)(
|
|
33608
|
+
const cacheKey = (0, import_node_server_utils155.makeCacheKey)(occurrence_book_namespace_collection, {
|
|
33609
|
+
_id
|
|
33610
|
+
});
|
|
33485
33611
|
const cachedData = await getCache(cacheKey);
|
|
33486
33612
|
if (cachedData) {
|
|
33487
33613
|
import_node_server_utils155.logger.info(`Cache hit for key: ${cacheKey}`);
|
|
@@ -33521,10 +33647,12 @@ function useOccurrenceBookRepo() {
|
|
|
33521
33647
|
);
|
|
33522
33648
|
}
|
|
33523
33649
|
delNamespace().then(() => {
|
|
33524
|
-
import_node_server_utils155.logger.info(
|
|
33650
|
+
import_node_server_utils155.logger.info(
|
|
33651
|
+
`Cache cleared for namespace: ${occurrence_book_namespace_collection}`
|
|
33652
|
+
);
|
|
33525
33653
|
}).catch((err) => {
|
|
33526
33654
|
import_node_server_utils155.logger.error(
|
|
33527
|
-
`Failed to clear cache for namespace: ${
|
|
33655
|
+
`Failed to clear cache for namespace: ${occurrence_book_namespace_collection}`,
|
|
33528
33656
|
err
|
|
33529
33657
|
);
|
|
33530
33658
|
});
|
|
@@ -33550,10 +33678,12 @@ function useOccurrenceBookRepo() {
|
|
|
33550
33678
|
throw new import_node_server_utils155.InternalServerError("Unable to delete occurrence book.");
|
|
33551
33679
|
}
|
|
33552
33680
|
delNamespace().then(() => {
|
|
33553
|
-
import_node_server_utils155.logger.info(
|
|
33681
|
+
import_node_server_utils155.logger.info(
|
|
33682
|
+
`Cache cleared for namespace: ${occurrence_book_namespace_collection}`
|
|
33683
|
+
);
|
|
33554
33684
|
}).catch((err) => {
|
|
33555
33685
|
import_node_server_utils155.logger.error(
|
|
33556
|
-
`Failed to clear cache for namespace: ${
|
|
33686
|
+
`Failed to clear cache for namespace: ${occurrence_book_namespace_collection}`,
|
|
33557
33687
|
err
|
|
33558
33688
|
);
|
|
33559
33689
|
});
|
|
@@ -33575,10 +33705,12 @@ function useOccurrenceBookRepo() {
|
|
|
33575
33705
|
throw new import_node_server_utils155.InternalServerError("Unable to close daily occurrence book.");
|
|
33576
33706
|
}
|
|
33577
33707
|
delNamespace().then(() => {
|
|
33578
|
-
import_node_server_utils155.logger.info(
|
|
33708
|
+
import_node_server_utils155.logger.info(
|
|
33709
|
+
`Cache cleared for namespace: ${occurrence_book_namespace_collection}`
|
|
33710
|
+
);
|
|
33579
33711
|
}).catch((err) => {
|
|
33580
33712
|
import_node_server_utils155.logger.error(
|
|
33581
|
-
`Failed to clear cache for namespace: ${
|
|
33713
|
+
`Failed to clear cache for namespace: ${occurrence_book_namespace_collection}`,
|
|
33582
33714
|
err
|
|
33583
33715
|
);
|
|
33584
33716
|
});
|
|
@@ -33587,6 +33719,47 @@ function useOccurrenceBookRepo() {
|
|
|
33587
33719
|
throw error;
|
|
33588
33720
|
}
|
|
33589
33721
|
}
|
|
33722
|
+
async function bulkCreate(payloads, session) {
|
|
33723
|
+
try {
|
|
33724
|
+
if (!payloads.length) {
|
|
33725
|
+
return { insertedCount: 0 };
|
|
33726
|
+
}
|
|
33727
|
+
const chunkSize = 500;
|
|
33728
|
+
let totalInserted = 0;
|
|
33729
|
+
for (let i = 0; i < payloads.length; i += chunkSize) {
|
|
33730
|
+
const chunk = payloads.slice(i, i + chunkSize);
|
|
33731
|
+
const operations = chunk.map((item) => ({
|
|
33732
|
+
insertOne: {
|
|
33733
|
+
document: {
|
|
33734
|
+
...item,
|
|
33735
|
+
createdAt: (/* @__PURE__ */ new Date()).toISOString(),
|
|
33736
|
+
updatedAt: "",
|
|
33737
|
+
deletedAt: ""
|
|
33738
|
+
}
|
|
33739
|
+
}
|
|
33740
|
+
}));
|
|
33741
|
+
const result = await collection.bulkWrite(operations, { session });
|
|
33742
|
+
totalInserted += result.insertedCount || 0;
|
|
33743
|
+
}
|
|
33744
|
+
import_node_server_utils155.logger.info(
|
|
33745
|
+
`Bulk insert successful: ${totalInserted} occurrence books created.`
|
|
33746
|
+
);
|
|
33747
|
+
delNamespace().then(() => {
|
|
33748
|
+
import_node_server_utils155.logger.info(
|
|
33749
|
+
`Cache cleared for namespace: ${occurrence_book_namespace_collection}`
|
|
33750
|
+
);
|
|
33751
|
+
}).catch((err) => {
|
|
33752
|
+
import_node_server_utils155.logger.error(
|
|
33753
|
+
`Failed to clear cache for namespace: ${occurrence_book_namespace_collection}`,
|
|
33754
|
+
err
|
|
33755
|
+
);
|
|
33756
|
+
});
|
|
33757
|
+
return { insertedCount: totalInserted };
|
|
33758
|
+
} catch (error) {
|
|
33759
|
+
import_node_server_utils155.logger.error("Bulk insert failed for occurrence books", error);
|
|
33760
|
+
throw error;
|
|
33761
|
+
}
|
|
33762
|
+
}
|
|
33590
33763
|
return {
|
|
33591
33764
|
add,
|
|
33592
33765
|
getAll,
|
|
@@ -33595,7 +33768,8 @@ function useOccurrenceBookRepo() {
|
|
|
33595
33768
|
deleteOccurrenceBookById,
|
|
33596
33769
|
closeOccurrenceBooks,
|
|
33597
33770
|
createIndexes,
|
|
33598
|
-
createTextIndex
|
|
33771
|
+
createTextIndex,
|
|
33772
|
+
bulkCreate
|
|
33599
33773
|
};
|
|
33600
33774
|
}
|
|
33601
33775
|
|
|
@@ -33605,14 +33779,18 @@ function useOccurrenceBookService() {
|
|
|
33605
33779
|
const {
|
|
33606
33780
|
add: _add,
|
|
33607
33781
|
updateOccurrenceBookById: _updateOccurrenceBookById,
|
|
33608
|
-
closeOccurrenceBooks: _closeOccurrenceBooks
|
|
33782
|
+
closeOccurrenceBooks: _closeOccurrenceBooks,
|
|
33783
|
+
bulkCreate: _bulkCreate
|
|
33609
33784
|
} = useOccurrenceBookRepo();
|
|
33610
33785
|
const {
|
|
33611
33786
|
add: _addOccurrenceCounter,
|
|
33612
33787
|
incrementByType: _incrementByType,
|
|
33613
33788
|
getByType: _getByType
|
|
33614
33789
|
} = useCounterRepo();
|
|
33615
|
-
const {
|
|
33790
|
+
const {
|
|
33791
|
+
getAllSites: _getAllSites,
|
|
33792
|
+
getAllSitesUnpaginated: _getAllSitesUnpaginated
|
|
33793
|
+
} = useSiteRepo();
|
|
33616
33794
|
async function add(value) {
|
|
33617
33795
|
const session = import_node_server_utils156.useAtlas.getClient()?.startSession();
|
|
33618
33796
|
session?.startTransaction();
|
|
@@ -33650,39 +33828,31 @@ function useOccurrenceBookService() {
|
|
|
33650
33828
|
}
|
|
33651
33829
|
}
|
|
33652
33830
|
async function processCreateDOB() {
|
|
33653
|
-
const limit = 100;
|
|
33654
33831
|
const counterName = "occurrence-book";
|
|
33655
|
-
let page = 1;
|
|
33656
33832
|
let entryCounter = 0;
|
|
33657
33833
|
const session = import_node_server_utils156.useAtlas.getClient()?.startSession();
|
|
33658
|
-
session?.startTransaction();
|
|
33659
|
-
const existingCounter = await _getByType(counterName);
|
|
33660
|
-
if (!existingCounter) {
|
|
33661
|
-
await _addOccurrenceCounter(counterName);
|
|
33662
|
-
} else {
|
|
33663
|
-
await _incrementByType(counterName, session);
|
|
33664
|
-
entryCounter = existingCounter.count + 1;
|
|
33665
|
-
}
|
|
33666
|
-
const baseDate = /* @__PURE__ */ new Date();
|
|
33667
|
-
baseDate.setUTCMinutes(0, 0, 0);
|
|
33668
|
-
const closedAt = new Date(baseDate);
|
|
33669
|
-
closedAt.setUTCDate(closedAt.getUTCDate() + 3);
|
|
33670
33834
|
try {
|
|
33671
|
-
|
|
33672
|
-
|
|
33673
|
-
|
|
33674
|
-
|
|
33675
|
-
|
|
33676
|
-
|
|
33677
|
-
|
|
33678
|
-
|
|
33679
|
-
|
|
33680
|
-
|
|
33681
|
-
|
|
33682
|
-
|
|
33683
|
-
|
|
33684
|
-
|
|
33685
|
-
|
|
33835
|
+
session?.startTransaction();
|
|
33836
|
+
const existingCounter = await _getByType(counterName);
|
|
33837
|
+
if (!existingCounter) {
|
|
33838
|
+
await _addOccurrenceCounter(counterName);
|
|
33839
|
+
entryCounter = 1;
|
|
33840
|
+
} else {
|
|
33841
|
+
entryCounter = existingCounter.count + 1;
|
|
33842
|
+
await _incrementByType(counterName);
|
|
33843
|
+
}
|
|
33844
|
+
const baseDate = /* @__PURE__ */ new Date();
|
|
33845
|
+
baseDate.setUTCMinutes(0, 0, 0);
|
|
33846
|
+
const closedAt = new Date(baseDate);
|
|
33847
|
+
closedAt.setUTCDate(closedAt.getUTCDate() + 3);
|
|
33848
|
+
const sites = await _getAllSitesUnpaginated();
|
|
33849
|
+
const payloads = sites.map((site) => ({
|
|
33850
|
+
site: site._id,
|
|
33851
|
+
date: baseDate.toISOString(),
|
|
33852
|
+
closedAt: closedAt.toISOString(),
|
|
33853
|
+
entryCounter
|
|
33854
|
+
}));
|
|
33855
|
+
await _bulkCreate(payloads, session);
|
|
33686
33856
|
await session?.commitTransaction();
|
|
33687
33857
|
} catch (err) {
|
|
33688
33858
|
await session?.abortTransaction();
|
|
@@ -40658,7 +40828,7 @@ function useManpowerMonitoringRepo() {
|
|
|
40658
40828
|
if (!db) {
|
|
40659
40829
|
throw new Error("Unable to connect to server.");
|
|
40660
40830
|
}
|
|
40661
|
-
const namespace_collection = "manpower-
|
|
40831
|
+
const namespace_collection = "manpower-settings";
|
|
40662
40832
|
const collection = db.collection(namespace_collection);
|
|
40663
40833
|
const serviceProviderCollection = db.collection("site.service-providers");
|
|
40664
40834
|
async function createManpowerMonitoringSettings(value, session) {
|
|
@@ -41601,7 +41771,7 @@ function useOvernightParkingRepo() {
|
|
|
41601
41771
|
try {
|
|
41602
41772
|
const data = await collection.findOne({
|
|
41603
41773
|
site: siteId,
|
|
41604
|
-
deletedAt: null
|
|
41774
|
+
deletedAt: { $nin: ["", null] }
|
|
41605
41775
|
});
|
|
41606
41776
|
setCache(cacheKey, data, 15 * 60).then(() => {
|
|
41607
41777
|
import_node_server_utils200.logger.info(`Cache set for key: ${cacheKey}`);
|
|
@@ -41709,12 +41879,12 @@ var schemaOvernightParkingRequest = import_joi118.default.object({
|
|
|
41709
41879
|
numberOfPassengers: import_joi118.default.number().integer().min(0).optional().default(0),
|
|
41710
41880
|
purposeOfVisit: import_joi118.default.string().optional().allow("", null),
|
|
41711
41881
|
status: import_joi118.default.string().valid(...Object.values(OvernightParkingRequestStatus)).optional().allow(null, "").default("pending" /* PENDING */),
|
|
41712
|
-
|
|
41882
|
+
remarks: import_joi118.default.string().optional().allow(null, "")
|
|
41713
41883
|
});
|
|
41714
41884
|
var schemaUpdateOvernightParkingRequest = import_joi118.default.object({
|
|
41715
41885
|
_id: import_joi118.default.string().hex().length(24).required(),
|
|
41716
41886
|
status: import_joi118.default.string().valid(...Object.values(OvernightParkingRequestStatus)).required(),
|
|
41717
|
-
|
|
41887
|
+
remarks: import_joi118.default.string().optional().allow(null, "")
|
|
41718
41888
|
});
|
|
41719
41889
|
function MOvernightParkingRequest(value) {
|
|
41720
41890
|
const { error } = schemaOvernightParkingRequest.validate(value);
|
|
@@ -41746,6 +41916,30 @@ function useOvernightParkingRequestRepo() {
|
|
|
41746
41916
|
const { delNamespace, getCache, setCache } = (0, import_node_server_utils203.useCache)(
|
|
41747
41917
|
overnight_parking_requests_namespace_collection
|
|
41748
41918
|
);
|
|
41919
|
+
async function createIndexes() {
|
|
41920
|
+
try {
|
|
41921
|
+
const existingIndexes = await collection.indexes();
|
|
41922
|
+
const existingNames = new Set(existingIndexes.map((i) => i.name));
|
|
41923
|
+
const indexesToEnsure = [
|
|
41924
|
+
{
|
|
41925
|
+
key: { site: 1 },
|
|
41926
|
+
name: "site-index"
|
|
41927
|
+
},
|
|
41928
|
+
{
|
|
41929
|
+
key: { status: 1 },
|
|
41930
|
+
name: "status-index"
|
|
41931
|
+
}
|
|
41932
|
+
];
|
|
41933
|
+
const indexesToCreate = indexesToEnsure.filter(
|
|
41934
|
+
(index) => index.name && !existingNames.has(index.name)
|
|
41935
|
+
);
|
|
41936
|
+
if (indexesToCreate.length > 0) {
|
|
41937
|
+
await collection.createIndexes(indexesToCreate);
|
|
41938
|
+
}
|
|
41939
|
+
} catch (error) {
|
|
41940
|
+
throw new import_node_server_utils203.InternalServerError("Failed to create collection indexes.");
|
|
41941
|
+
}
|
|
41942
|
+
}
|
|
41749
41943
|
async function add(value, session) {
|
|
41750
41944
|
try {
|
|
41751
41945
|
value = MOvernightParkingRequest(value);
|
|
@@ -41931,7 +42125,8 @@ function useOvernightParkingRequestRepo() {
|
|
|
41931
42125
|
getOvernightParkingRequestById,
|
|
41932
42126
|
updateOvernightParkingRequestById,
|
|
41933
42127
|
deleteOvernightParkingRequestById,
|
|
41934
|
-
updateExpiredRequests
|
|
42128
|
+
updateExpiredRequests,
|
|
42129
|
+
createIndexes
|
|
41935
42130
|
};
|
|
41936
42131
|
}
|
|
41937
42132
|
|
|
@@ -43068,6 +43263,691 @@ function useManpowerRemarkCtrl() {
|
|
|
43068
43263
|
updateRemarksStatus
|
|
43069
43264
|
};
|
|
43070
43265
|
}
|
|
43266
|
+
|
|
43267
|
+
// src/models/manpower-sites.model.ts
|
|
43268
|
+
var import_joi122 = __toESM(require("joi"));
|
|
43269
|
+
var import_mongodb114 = require("mongodb");
|
|
43270
|
+
var manpowerSitesSchema = import_joi122.default.object({
|
|
43271
|
+
id: import_joi122.default.string().hex().required(),
|
|
43272
|
+
text: import_joi122.default.string().hex().optional().allow("", null),
|
|
43273
|
+
contractID: import_joi122.default.string().optional().allow("", null),
|
|
43274
|
+
contractName: import_joi122.default.string().optional().allow("", null),
|
|
43275
|
+
type: import_joi122.default.string().optional().allow("", null),
|
|
43276
|
+
status: import_joi122.default.number().optional().allow("", null)
|
|
43277
|
+
});
|
|
43278
|
+
var MManpowerSites = class {
|
|
43279
|
+
constructor(data) {
|
|
43280
|
+
this._id = new import_mongodb114.ObjectId();
|
|
43281
|
+
this.id = data.id || "";
|
|
43282
|
+
this.text = data.text || "";
|
|
43283
|
+
this.contractID = data.contractID || "";
|
|
43284
|
+
this.contractName = data.contractName || "";
|
|
43285
|
+
this.type = data.type || "";
|
|
43286
|
+
this.status = data.status || "";
|
|
43287
|
+
}
|
|
43288
|
+
};
|
|
43289
|
+
|
|
43290
|
+
// src/repositories/manpower-sites.repo.ts
|
|
43291
|
+
var import_node_server_utils209 = require("@7365admin1/node-server-utils");
|
|
43292
|
+
function useManpowerSitesRepo() {
|
|
43293
|
+
const db = import_node_server_utils209.useAtlas.getDb();
|
|
43294
|
+
if (!db) {
|
|
43295
|
+
throw new Error("Unable to connect to server.");
|
|
43296
|
+
}
|
|
43297
|
+
const namespace_collection = "manpower-sites";
|
|
43298
|
+
const collection = db.collection(namespace_collection);
|
|
43299
|
+
async function createManpowerSites(value) {
|
|
43300
|
+
try {
|
|
43301
|
+
value = new MManpowerSites(value);
|
|
43302
|
+
const result = await collection.insertOne(value);
|
|
43303
|
+
return result;
|
|
43304
|
+
} catch (error) {
|
|
43305
|
+
throw new Error(error.message || error || "Server Internal Error");
|
|
43306
|
+
}
|
|
43307
|
+
}
|
|
43308
|
+
async function getAllManpowerSites({
|
|
43309
|
+
page = 1,
|
|
43310
|
+
limit = 10,
|
|
43311
|
+
search = ""
|
|
43312
|
+
}) {
|
|
43313
|
+
try {
|
|
43314
|
+
page = page ? page - 1 : 0;
|
|
43315
|
+
limit = limit || 10;
|
|
43316
|
+
const searchQuery = {};
|
|
43317
|
+
if (search) {
|
|
43318
|
+
searchQuery.siteName = { $regex: search, $options: "i" };
|
|
43319
|
+
}
|
|
43320
|
+
const result = await collection.aggregate([
|
|
43321
|
+
{ $match: searchQuery },
|
|
43322
|
+
{
|
|
43323
|
+
$facet: {
|
|
43324
|
+
totalCount: [{ $count: "count" }],
|
|
43325
|
+
items: [
|
|
43326
|
+
{ $sort: { _id: 1 } },
|
|
43327
|
+
{
|
|
43328
|
+
$project: {
|
|
43329
|
+
_id: 0
|
|
43330
|
+
}
|
|
43331
|
+
},
|
|
43332
|
+
{ $skip: page * limit },
|
|
43333
|
+
{ $limit: limit }
|
|
43334
|
+
]
|
|
43335
|
+
}
|
|
43336
|
+
}
|
|
43337
|
+
]).toArray();
|
|
43338
|
+
const items = result[0].items;
|
|
43339
|
+
return items;
|
|
43340
|
+
} catch (error) {
|
|
43341
|
+
throw new Error(error.message || "Server Internal Error");
|
|
43342
|
+
}
|
|
43343
|
+
}
|
|
43344
|
+
async function deleteManpowerSites(siteId) {
|
|
43345
|
+
try {
|
|
43346
|
+
const result = await collection.deleteOne({
|
|
43347
|
+
id: siteId.toString()
|
|
43348
|
+
});
|
|
43349
|
+
return result;
|
|
43350
|
+
} catch (error) {
|
|
43351
|
+
throw new Error(error.message || "Server Internal Error");
|
|
43352
|
+
}
|
|
43353
|
+
}
|
|
43354
|
+
return {
|
|
43355
|
+
createManpowerSites,
|
|
43356
|
+
getAllManpowerSites,
|
|
43357
|
+
deleteManpowerSites
|
|
43358
|
+
};
|
|
43359
|
+
}
|
|
43360
|
+
|
|
43361
|
+
// src/services/manpower-sites.service.ts
|
|
43362
|
+
var import_node_server_utils210 = require("@7365admin1/node-server-utils");
|
|
43363
|
+
function useManpowerSitesSrvc() {
|
|
43364
|
+
const manpowerSitesRepo = useManpowerSitesRepo();
|
|
43365
|
+
const manpowerMonitoringRepo = useManpowerMonitoringRepo();
|
|
43366
|
+
async function createManpowerSites(payload) {
|
|
43367
|
+
const session = import_node_server_utils210.useAtlas.getClient()?.startSession();
|
|
43368
|
+
if (!session) {
|
|
43369
|
+
throw new import_node_server_utils210.BadRequestError("Database session not available.");
|
|
43370
|
+
}
|
|
43371
|
+
await session.startTransaction();
|
|
43372
|
+
try {
|
|
43373
|
+
const manpowerSites = await manpowerMonitoringRepo.getAllSites(payload);
|
|
43374
|
+
for (const site of manpowerSites) {
|
|
43375
|
+
await manpowerSitesRepo.createManpowerSites(site);
|
|
43376
|
+
}
|
|
43377
|
+
await session.commitTransaction();
|
|
43378
|
+
return "Created Succesfully";
|
|
43379
|
+
} catch (error) {
|
|
43380
|
+
await session.abortTransaction();
|
|
43381
|
+
import_node_server_utils210.logger.error(error.message || error);
|
|
43382
|
+
console.error("Error creating monitoring settings:", error);
|
|
43383
|
+
throw new Error(error?.message || "Internal Server Error!");
|
|
43384
|
+
} finally {
|
|
43385
|
+
session.endSession();
|
|
43386
|
+
}
|
|
43387
|
+
}
|
|
43388
|
+
async function checkManpowerSites() {
|
|
43389
|
+
try {
|
|
43390
|
+
const serviceProviderId = "69bb9dbff572cf9d260d7ce3";
|
|
43391
|
+
const hrmLabsSites = await manpowerMonitoringRepo.getAllSites(
|
|
43392
|
+
serviceProviderId
|
|
43393
|
+
);
|
|
43394
|
+
const manpowerSites = await manpowerSitesRepo.getAllManpowerSites({
|
|
43395
|
+
page: 1,
|
|
43396
|
+
limit: 1e3,
|
|
43397
|
+
search: ""
|
|
43398
|
+
});
|
|
43399
|
+
const added = hrmLabsSites.filter(
|
|
43400
|
+
(hrmSite) => !manpowerSites.some((mpSite) => mpSite.id === hrmSite.id)
|
|
43401
|
+
);
|
|
43402
|
+
const deleted = manpowerSites.filter(
|
|
43403
|
+
(mpSite) => !hrmLabsSites.some((hrmSite) => hrmSite.id === mpSite.id)
|
|
43404
|
+
);
|
|
43405
|
+
if (added.length > 0) {
|
|
43406
|
+
await Promise.all(
|
|
43407
|
+
added.map((site) => manpowerSitesRepo.createManpowerSites(site))
|
|
43408
|
+
);
|
|
43409
|
+
}
|
|
43410
|
+
if (deleted.length > 0) {
|
|
43411
|
+
await Promise.all(
|
|
43412
|
+
deleted.map(
|
|
43413
|
+
(site) => manpowerSitesRepo.deleteManpowerSites(site.id)
|
|
43414
|
+
)
|
|
43415
|
+
);
|
|
43416
|
+
}
|
|
43417
|
+
return "Manpower Sites Updated Successfully";
|
|
43418
|
+
} catch (error) {
|
|
43419
|
+
import_node_server_utils210.logger.error(error.message || error);
|
|
43420
|
+
console.error("Error checking manpower sites:", error);
|
|
43421
|
+
throw new Error(error?.message || "Internal Server Error!");
|
|
43422
|
+
}
|
|
43423
|
+
}
|
|
43424
|
+
return {
|
|
43425
|
+
createManpowerSites,
|
|
43426
|
+
checkManpowerSites
|
|
43427
|
+
};
|
|
43428
|
+
}
|
|
43429
|
+
|
|
43430
|
+
// src/controllers/manpower-sites.controller.ts
|
|
43431
|
+
var import_node_server_utils211 = require("@7365admin1/node-server-utils");
|
|
43432
|
+
var import_joi123 = __toESM(require("joi"));
|
|
43433
|
+
function useManpowerSitesCtrl() {
|
|
43434
|
+
const { createManpowerSites: _createManpowerSites } = useManpowerSitesSrvc();
|
|
43435
|
+
const { getAllManpowerSites: _getAllManpowerSites } = useManpowerSitesRepo();
|
|
43436
|
+
async function createManpowerSites(req, res, next) {
|
|
43437
|
+
try {
|
|
43438
|
+
const payload = req.query.serviceProviderId;
|
|
43439
|
+
const schema2 = import_joi123.default.object({
|
|
43440
|
+
serviceProviderId: import_joi123.default.string().hex().required()
|
|
43441
|
+
});
|
|
43442
|
+
const { error } = schema2.validate({
|
|
43443
|
+
serviceProviderId: payload
|
|
43444
|
+
});
|
|
43445
|
+
if (error) {
|
|
43446
|
+
next(new import_node_server_utils211.BadRequestError(error.message));
|
|
43447
|
+
return;
|
|
43448
|
+
}
|
|
43449
|
+
const result = await _createManpowerSites(payload);
|
|
43450
|
+
return res.json(result);
|
|
43451
|
+
} catch (error) {
|
|
43452
|
+
import_node_server_utils211.logger.log({ level: "error", message: error.message });
|
|
43453
|
+
next(error);
|
|
43454
|
+
return;
|
|
43455
|
+
}
|
|
43456
|
+
}
|
|
43457
|
+
async function getAllManpowerSites(req, res, next) {
|
|
43458
|
+
try {
|
|
43459
|
+
const { page, search, limit } = req.query;
|
|
43460
|
+
const schema2 = import_joi123.default.object({
|
|
43461
|
+
page: import_joi123.default.number().optional().allow("", null),
|
|
43462
|
+
limit: import_joi123.default.number().optional().allow("", null),
|
|
43463
|
+
search: import_joi123.default.string().optional().allow("", null)
|
|
43464
|
+
});
|
|
43465
|
+
const { error } = schema2.validate({ page, search, limit });
|
|
43466
|
+
if (error) {
|
|
43467
|
+
next(new import_node_server_utils211.BadRequestError(error.message));
|
|
43468
|
+
return;
|
|
43469
|
+
}
|
|
43470
|
+
const result = await _getAllManpowerSites({
|
|
43471
|
+
page: Number(page),
|
|
43472
|
+
limit: Number(limit),
|
|
43473
|
+
search
|
|
43474
|
+
});
|
|
43475
|
+
return res.json(result);
|
|
43476
|
+
} catch (error) {
|
|
43477
|
+
import_node_server_utils211.logger.log({ level: "error", message: error.message });
|
|
43478
|
+
next(error);
|
|
43479
|
+
return;
|
|
43480
|
+
}
|
|
43481
|
+
}
|
|
43482
|
+
return {
|
|
43483
|
+
createManpowerSites,
|
|
43484
|
+
getAllManpowerSites
|
|
43485
|
+
};
|
|
43486
|
+
}
|
|
43487
|
+
|
|
43488
|
+
// src/utils/cron.util.ts
|
|
43489
|
+
var import_node_server_utils212 = require("@7365admin1/node-server-utils");
|
|
43490
|
+
var import_mongodb115 = require("mongodb");
|
|
43491
|
+
var import_moment_timezone4 = __toESM(require("moment-timezone"));
|
|
43492
|
+
var createManpowerRemarksDaily = async () => {
|
|
43493
|
+
const db = import_node_server_utils212.useAtlas.getDb();
|
|
43494
|
+
if (!db) {
|
|
43495
|
+
throw new Error("Unable to connect to server.");
|
|
43496
|
+
}
|
|
43497
|
+
const namespace_collection = "manpower-settings";
|
|
43498
|
+
const settings = db.collection(namespace_collection);
|
|
43499
|
+
const remarks = db.collection("manpower-remarks");
|
|
43500
|
+
const serviceProviders = db.collection("site.service-providers");
|
|
43501
|
+
const items = [];
|
|
43502
|
+
const yesterday = (0, import_moment_timezone4.default)().tz("Asia/Singapore").subtract(1, "days").format("DD-MM-YYYY");
|
|
43503
|
+
try {
|
|
43504
|
+
const nowSGT = (0, import_moment_timezone4.default)().tz("Asia/Singapore");
|
|
43505
|
+
const servideProvider = await serviceProviders.findOne({
|
|
43506
|
+
name: { $regex: process.env.HRMLABS_DOMAIN, $options: "i" }
|
|
43507
|
+
});
|
|
43508
|
+
if (!servideProvider) {
|
|
43509
|
+
throw new Error("Servide Provider not found.");
|
|
43510
|
+
}
|
|
43511
|
+
const remark = await remarks.find({
|
|
43512
|
+
createdAtSGT: yesterday,
|
|
43513
|
+
serviceProviderId: servideProvider._id,
|
|
43514
|
+
status: "active"
|
|
43515
|
+
}).toArray();
|
|
43516
|
+
for (const site of remark) {
|
|
43517
|
+
const existingRemark = await settings.findOne({
|
|
43518
|
+
siteId: site.siteId,
|
|
43519
|
+
enabled: true
|
|
43520
|
+
});
|
|
43521
|
+
if (existingRemark) {
|
|
43522
|
+
const setting = await settings.findOne({
|
|
43523
|
+
siteId: site.siteId,
|
|
43524
|
+
enabled: true
|
|
43525
|
+
});
|
|
43526
|
+
const shiftType = setting?.shiftType;
|
|
43527
|
+
const morningCheckInTime = setting?.shifts?.[shiftType][0]?.checkIn;
|
|
43528
|
+
const afternoonCheckInTime = shiftType == "3-shifts" ? setting?.shifts?.[shiftType][1]?.checkIn : null;
|
|
43529
|
+
const nightCheckInTime = shiftType == "3-shifts" ? setting?.shifts?.[shiftType][2]?.checkIn : setting?.shifts?.[shiftType][1]?.checkIn;
|
|
43530
|
+
const morningAlertFrequencyMins = setting?.shifts?.[shiftType][0]?.alertFrequencyMins;
|
|
43531
|
+
const afternoonAlertFrequencyMins = shiftType == "3-shifts" ? setting?.shifts?.[shiftType][1]?.alertFrequencyMins : null;
|
|
43532
|
+
const nightAlertFrequencyMins = shiftType == "3-shifts" ? setting?.shifts?.[shiftType][2]?.alertFrequencyMins : setting?.shifts?.[shiftType][1]?.alertFrequencyMins;
|
|
43533
|
+
const morningAlertTime = import_moment_timezone4.default.tz(morningCheckInTime, "HH:mm", "Asia/Singapore").add(morningAlertFrequencyMins, "minutes").format("HH:mm");
|
|
43534
|
+
const afternoonAlertTime = afternoonCheckInTime ? import_moment_timezone4.default.tz(afternoonCheckInTime, "HH:mm", "Asia/Singapore").add(afternoonAlertFrequencyMins, "minutes").format("HH:mm") : "";
|
|
43535
|
+
const nightAlertTime = import_moment_timezone4.default.tz(nightCheckInTime, "HH:mm", "Asia/Singapore").add(nightAlertFrequencyMins, "minutes").format("HH:mm");
|
|
43536
|
+
const remark2 = {
|
|
43537
|
+
siteId: site.siteId,
|
|
43538
|
+
siteName: site.siteName,
|
|
43539
|
+
serviceProviderId: servideProvider._id,
|
|
43540
|
+
remarks: [
|
|
43541
|
+
{
|
|
43542
|
+
name: "Morning Shift",
|
|
43543
|
+
remark: {
|
|
43544
|
+
isAcknowledged: true,
|
|
43545
|
+
status: "",
|
|
43546
|
+
acknowledgementRemarks: "",
|
|
43547
|
+
acknowledgedAt: ""
|
|
43548
|
+
}
|
|
43549
|
+
},
|
|
43550
|
+
{
|
|
43551
|
+
name: "Afternoon Shift",
|
|
43552
|
+
remark: {
|
|
43553
|
+
isAcknowledged: true,
|
|
43554
|
+
status: "",
|
|
43555
|
+
acknowledgementRemarks: "",
|
|
43556
|
+
acknowledgedAt: ""
|
|
43557
|
+
}
|
|
43558
|
+
},
|
|
43559
|
+
{
|
|
43560
|
+
name: "Night Shift",
|
|
43561
|
+
remark: {
|
|
43562
|
+
isAcknowledged: true,
|
|
43563
|
+
status: "",
|
|
43564
|
+
acknowledgementRemarks: "",
|
|
43565
|
+
acknowledgedAt: ""
|
|
43566
|
+
}
|
|
43567
|
+
}
|
|
43568
|
+
],
|
|
43569
|
+
createdBy: "",
|
|
43570
|
+
createdByName: "",
|
|
43571
|
+
morningAlertTime,
|
|
43572
|
+
afternoonAlertTime,
|
|
43573
|
+
nightAlertTime,
|
|
43574
|
+
createdAt: /* @__PURE__ */ new Date(),
|
|
43575
|
+
createdAtSGT: nowSGT.format("DD-MM-YYYY"),
|
|
43576
|
+
updatedAt: "",
|
|
43577
|
+
status: "active"
|
|
43578
|
+
};
|
|
43579
|
+
items.push(remark2);
|
|
43580
|
+
}
|
|
43581
|
+
}
|
|
43582
|
+
if (items.length > 0) {
|
|
43583
|
+
await remarks.insertMany(items);
|
|
43584
|
+
}
|
|
43585
|
+
console.log("Daily manpower remarks created successfully.");
|
|
43586
|
+
} catch (error) {
|
|
43587
|
+
console.error("Error creating daily manpower remarks:", error);
|
|
43588
|
+
}
|
|
43589
|
+
};
|
|
43590
|
+
var updateRemarksisAcknowledged = async () => {
|
|
43591
|
+
const { getAttendanceDataCount: _getAttendanceDataCount } = useHrmLabsAttendanceSrvc();
|
|
43592
|
+
const nowSGT = (0, import_moment_timezone4.default)().tz("Asia/Singapore").format("DD-MM-YYYY");
|
|
43593
|
+
const db = import_node_server_utils212.useAtlas.getDb();
|
|
43594
|
+
if (!db) {
|
|
43595
|
+
throw new Error("Unable to connect to server.");
|
|
43596
|
+
}
|
|
43597
|
+
const namespace_collection = "manpower-remarks";
|
|
43598
|
+
const remarks = db.collection(namespace_collection);
|
|
43599
|
+
const timeNow = (0, import_moment_timezone4.default)().tz("Asia/Singapore").format("HH:mm");
|
|
43600
|
+
const settings = db.collection("manpower-settings");
|
|
43601
|
+
try {
|
|
43602
|
+
const matchingDocs = await remarks.find({
|
|
43603
|
+
createdAtSGT: nowSGT,
|
|
43604
|
+
$or: [
|
|
43605
|
+
{
|
|
43606
|
+
morningAlertTime: timeNow,
|
|
43607
|
+
"remarks.0.remark.isAcknowledged": true
|
|
43608
|
+
},
|
|
43609
|
+
{
|
|
43610
|
+
afternoonAlertTime: timeNow,
|
|
43611
|
+
"remarks.1.remark.isAcknowledged": true
|
|
43612
|
+
},
|
|
43613
|
+
{ nightAlertTime: timeNow, "remarks.2.remark.isAcknowledged": true }
|
|
43614
|
+
]
|
|
43615
|
+
}).project({ _id: 1 }).toArray();
|
|
43616
|
+
if (matchingDocs.length === 0) {
|
|
43617
|
+
return;
|
|
43618
|
+
}
|
|
43619
|
+
const updatedIds = matchingDocs.map((doc) => doc._id);
|
|
43620
|
+
await remarks.updateMany(
|
|
43621
|
+
{
|
|
43622
|
+
_id: { $in: updatedIds },
|
|
43623
|
+
morningAlertTime: timeNow,
|
|
43624
|
+
createdAtSGT: nowSGT,
|
|
43625
|
+
"remarks.0.remark.isAcknowledged": true
|
|
43626
|
+
},
|
|
43627
|
+
{ $set: { "remarks.0.remark.isAcknowledged": false } }
|
|
43628
|
+
);
|
|
43629
|
+
await remarks.updateMany(
|
|
43630
|
+
{
|
|
43631
|
+
_id: { $in: updatedIds },
|
|
43632
|
+
afternoonAlertTime: timeNow,
|
|
43633
|
+
createdAtSGT: nowSGT,
|
|
43634
|
+
"remarks.1.remark.isAcknowledged": true
|
|
43635
|
+
},
|
|
43636
|
+
{ $set: { "remarks.1.remark.isAcknowledged": false } }
|
|
43637
|
+
);
|
|
43638
|
+
await remarks.updateMany(
|
|
43639
|
+
{
|
|
43640
|
+
_id: { $in: updatedIds },
|
|
43641
|
+
nightAlertTime: timeNow,
|
|
43642
|
+
createdAtSGT: nowSGT,
|
|
43643
|
+
"remarks.2.remark.isAcknowledged": true
|
|
43644
|
+
},
|
|
43645
|
+
{ $set: { "remarks.2.remark.isAcknowledged": false } }
|
|
43646
|
+
);
|
|
43647
|
+
for (const id of updatedIds) {
|
|
43648
|
+
const doc = await remarks.findOne({ _id: id });
|
|
43649
|
+
const setting = await settings.findOne(
|
|
43650
|
+
{ siteId: new import_mongodb115.ObjectId(doc?.siteId) },
|
|
43651
|
+
{ projection: { emails: 1 } }
|
|
43652
|
+
);
|
|
43653
|
+
const payload = {
|
|
43654
|
+
startDate: doc?.createdAtSGT,
|
|
43655
|
+
endDate: doc?.createdAtSGT,
|
|
43656
|
+
siteName: doc?.siteName,
|
|
43657
|
+
siteId: doc?.siteId.toString(),
|
|
43658
|
+
serviceProviderId: doc?.serviceProviderId.toString()
|
|
43659
|
+
};
|
|
43660
|
+
const result = await _getAttendanceDataCount(payload);
|
|
43661
|
+
const shifts = [
|
|
43662
|
+
{ key: "dayShift", alertTime: doc?.morningAlertTime },
|
|
43663
|
+
{ key: "afternoonShift", alertTime: doc?.afternoonAlertTime },
|
|
43664
|
+
{ key: "nightShift", alertTime: doc?.nightAlertTime }
|
|
43665
|
+
];
|
|
43666
|
+
let shiftType;
|
|
43667
|
+
let actual = 0;
|
|
43668
|
+
let expected = 0;
|
|
43669
|
+
for (const shift of shifts) {
|
|
43670
|
+
if (shift.alertTime && isWithinHour(shift.alertTime, timeNow)) {
|
|
43671
|
+
shiftType = shift.key;
|
|
43672
|
+
actual = result?.totalCount?.[shift.key]?.actual || 0;
|
|
43673
|
+
expected = result?.totalCount?.[shift.key]?.expected || 0;
|
|
43674
|
+
break;
|
|
43675
|
+
}
|
|
43676
|
+
}
|
|
43677
|
+
let newStatus = "Normal";
|
|
43678
|
+
if (actual > expected)
|
|
43679
|
+
newStatus = "Over";
|
|
43680
|
+
else if (actual < expected)
|
|
43681
|
+
newStatus = "Under";
|
|
43682
|
+
sendEmailWithAttachmentsTo({
|
|
43683
|
+
email: setting?.emails,
|
|
43684
|
+
subject: "Manpower Alert",
|
|
43685
|
+
message: "",
|
|
43686
|
+
siteName: doc?.siteName || "",
|
|
43687
|
+
handlebar: "alert-email",
|
|
43688
|
+
date: nowSGT,
|
|
43689
|
+
actual,
|
|
43690
|
+
expected,
|
|
43691
|
+
status: newStatus
|
|
43692
|
+
});
|
|
43693
|
+
}
|
|
43694
|
+
} catch (error) {
|
|
43695
|
+
console.error("Error updating remarks:", error);
|
|
43696
|
+
}
|
|
43697
|
+
};
|
|
43698
|
+
var updateRemarksStatusEod = async () => {
|
|
43699
|
+
const { getAttendanceDataCount: _getAttendanceDataCount } = useHrmLabsAttendanceSrvc();
|
|
43700
|
+
const db = import_node_server_utils212.useAtlas.getDb();
|
|
43701
|
+
if (!db) {
|
|
43702
|
+
throw new Error("Unable to connect to server.");
|
|
43703
|
+
}
|
|
43704
|
+
const remarks = db.collection("manpower-remarks");
|
|
43705
|
+
const settings = db.collection("manpower-settings");
|
|
43706
|
+
const nowSGT = (0, import_moment_timezone4.default)().tz("Asia/Singapore").format("DD-MM-YYYY");
|
|
43707
|
+
const yesterdaySGT = (0, import_moment_timezone4.default)().tz("Asia/Singapore").subtract(1, "days").format("DD-MM-YYYY");
|
|
43708
|
+
const timeNow = (0, import_moment_timezone4.default)().tz("Asia/Singapore").format("HH:mm");
|
|
43709
|
+
const docs = await remarks.find({
|
|
43710
|
+
$or: [
|
|
43711
|
+
// Morning & Afternoon from today
|
|
43712
|
+
{
|
|
43713
|
+
createdAtSGT: nowSGT,
|
|
43714
|
+
$or: [
|
|
43715
|
+
{
|
|
43716
|
+
"remarks.0.remark.status": "",
|
|
43717
|
+
"remarks.0.remark.isAcknowledged": false
|
|
43718
|
+
},
|
|
43719
|
+
{
|
|
43720
|
+
"remarks.1.remark.status": "",
|
|
43721
|
+
"remarks.1.remark.isAcknowledged": false
|
|
43722
|
+
}
|
|
43723
|
+
]
|
|
43724
|
+
},
|
|
43725
|
+
// Night shift from yesterday
|
|
43726
|
+
{
|
|
43727
|
+
createdAtSGT: yesterdaySGT,
|
|
43728
|
+
"remarks.2.remark.status": "",
|
|
43729
|
+
"remarks.2.remark.isAcknowledged": false
|
|
43730
|
+
}
|
|
43731
|
+
]
|
|
43732
|
+
}).toArray();
|
|
43733
|
+
for (const doc of docs) {
|
|
43734
|
+
let shiftsToCheck = [];
|
|
43735
|
+
const endShiftTime = await settings.findOne(
|
|
43736
|
+
{ siteId: new import_mongodb115.ObjectId(doc.siteId) },
|
|
43737
|
+
{ projection: { shifts: 1, shiftType: 1 } }
|
|
43738
|
+
);
|
|
43739
|
+
if (doc.createdAtSGT === nowSGT) {
|
|
43740
|
+
const shiftType = endShiftTime?.shiftType || "2-shifts";
|
|
43741
|
+
if (timeNow >= endShiftTime?.shifts[shiftType][0]?.checkOut)
|
|
43742
|
+
shiftsToCheck.push({ index: 0, key: "dayShift" });
|
|
43743
|
+
if (shiftType == "3-shifts" && timeNow >= endShiftTime?.shifts[shiftType][1]?.checkOut)
|
|
43744
|
+
shiftsToCheck.push({ index: 1, key: "afternoonShift" });
|
|
43745
|
+
}
|
|
43746
|
+
if (doc.createdAtSGT === yesterdaySGT) {
|
|
43747
|
+
const index = endShiftTime?.shiftType === "2-shifts" ? 1 : 2;
|
|
43748
|
+
if (timeNow >= endShiftTime?.shifts[endShiftTime?.shiftType][index]?.checkOut)
|
|
43749
|
+
shiftsToCheck.push({ index: 2, key: "nightShift" });
|
|
43750
|
+
}
|
|
43751
|
+
if (shiftsToCheck.length === 0)
|
|
43752
|
+
continue;
|
|
43753
|
+
const payload = {
|
|
43754
|
+
startDate: doc.createdAtSGT,
|
|
43755
|
+
endDate: doc.createdAtSGT,
|
|
43756
|
+
siteName: doc.siteName,
|
|
43757
|
+
siteId: doc.siteId.toString(),
|
|
43758
|
+
serviceProviderId: doc.serviceProviderId.toString()
|
|
43759
|
+
};
|
|
43760
|
+
const result = await _getAttendanceDataCount(payload);
|
|
43761
|
+
if (!result?.totalCount) {
|
|
43762
|
+
continue;
|
|
43763
|
+
}
|
|
43764
|
+
for (const shift of shiftsToCheck) {
|
|
43765
|
+
const actual = result?.totalCount[shift?.key]?.actual || 0;
|
|
43766
|
+
const expected = result?.totalCount[shift?.key]?.expected || 0;
|
|
43767
|
+
if (doc.remarks[shift.index].remark.status === "") {
|
|
43768
|
+
let newStatus = "Normal";
|
|
43769
|
+
if (actual > expected)
|
|
43770
|
+
newStatus = "Over";
|
|
43771
|
+
else if (actual < expected)
|
|
43772
|
+
newStatus = "Under";
|
|
43773
|
+
await remarks.updateOne(
|
|
43774
|
+
{ _id: doc._id },
|
|
43775
|
+
{
|
|
43776
|
+
$set: {
|
|
43777
|
+
[`remarks.${shift.index}.remark.status`]: newStatus,
|
|
43778
|
+
[`remarks.${shift.index}.remark.isAcknowledged`]: true,
|
|
43779
|
+
[`remarks.${shift.index}.remark.acknowledgedAt`]: (/* @__PURE__ */ new Date()).toISOString()
|
|
43780
|
+
}
|
|
43781
|
+
}
|
|
43782
|
+
);
|
|
43783
|
+
}
|
|
43784
|
+
}
|
|
43785
|
+
}
|
|
43786
|
+
};
|
|
43787
|
+
function sendEmailWithAttachmentsTo({
|
|
43788
|
+
email = "",
|
|
43789
|
+
subject = "",
|
|
43790
|
+
message = "",
|
|
43791
|
+
siteName = "",
|
|
43792
|
+
handlebar = "",
|
|
43793
|
+
date = "",
|
|
43794
|
+
actual = 0,
|
|
43795
|
+
expected = 0,
|
|
43796
|
+
status = ""
|
|
43797
|
+
}) {
|
|
43798
|
+
const MailerConfig = {
|
|
43799
|
+
host: MAILER_TRANSPORT_HOST,
|
|
43800
|
+
port: MAILER_TRANSPORT_PORT,
|
|
43801
|
+
secure: MAILER_TRANSPORT_SECURE,
|
|
43802
|
+
email: MAILER_EMAIL,
|
|
43803
|
+
password: MAILER_PASSWORD
|
|
43804
|
+
};
|
|
43805
|
+
const mailer = new import_node_server_utils212.useMailer(MailerConfig);
|
|
43806
|
+
const dir = __dirname;
|
|
43807
|
+
const type = "alert-email";
|
|
43808
|
+
const filePath = (0, import_node_server_utils212.getDirectory)(dir, `./public/handlebars/${type}`);
|
|
43809
|
+
const emailContent = (0, import_node_server_utils212.compileHandlebar)({
|
|
43810
|
+
context: {
|
|
43811
|
+
siteName,
|
|
43812
|
+
date,
|
|
43813
|
+
actual,
|
|
43814
|
+
expected,
|
|
43815
|
+
status
|
|
43816
|
+
},
|
|
43817
|
+
filePath
|
|
43818
|
+
});
|
|
43819
|
+
mailer.sendMail({
|
|
43820
|
+
to: email,
|
|
43821
|
+
subject,
|
|
43822
|
+
html: emailContent,
|
|
43823
|
+
sender: "iService365"
|
|
43824
|
+
}).catch((error) => {
|
|
43825
|
+
import_node_server_utils212.logger.log({
|
|
43826
|
+
level: "error",
|
|
43827
|
+
message: `Error sending user ${type} email: ${error}`
|
|
43828
|
+
});
|
|
43829
|
+
});
|
|
43830
|
+
return { message };
|
|
43831
|
+
}
|
|
43832
|
+
var isWithinHour = (alertTime, timeNow) => {
|
|
43833
|
+
const [ah, am] = alertTime.split(":").map(Number);
|
|
43834
|
+
const [nh, nm] = timeNow.split(":").map(Number);
|
|
43835
|
+
const alertMinutes = ah * 60 + am;
|
|
43836
|
+
const nowMinutes = nh * 60 + nm;
|
|
43837
|
+
return nowMinutes >= alertMinutes && nowMinutes <= alertMinutes + 60;
|
|
43838
|
+
};
|
|
43839
|
+
|
|
43840
|
+
// src/events/manpower.event.ts
|
|
43841
|
+
var import_node_server_utils213 = require("@7365admin1/node-server-utils");
|
|
43842
|
+
var import_mongodb116 = require("mongodb");
|
|
43843
|
+
var import_moment_timezone5 = __toESM(require("moment-timezone"));
|
|
43844
|
+
async function manpowerEvents(io) {
|
|
43845
|
+
console.log("Manpower events initialized");
|
|
43846
|
+
let intervalId = null;
|
|
43847
|
+
let activeConnections = 0;
|
|
43848
|
+
const { getAttendanceDataCount: _getAttendanceDataCount } = useHrmLabsAttendanceSrvc();
|
|
43849
|
+
const updateRemarksStatus = async (date) => {
|
|
43850
|
+
const db = import_node_server_utils213.useAtlas.getDb();
|
|
43851
|
+
if (!db) {
|
|
43852
|
+
throw new Error("Unable to connect to server.");
|
|
43853
|
+
}
|
|
43854
|
+
const remarks = db.collection("manpower-remarks");
|
|
43855
|
+
const settings = db.collection("manpower-settings");
|
|
43856
|
+
const selectedDateMoment = import_moment_timezone5.default.tz(date, "DD-MM-YYYY", "Asia/Singapore");
|
|
43857
|
+
const selectedDateSGT = selectedDateMoment.format("DD-MM-YYYY");
|
|
43858
|
+
const currentSGT = (0, import_moment_timezone5.default)().tz("Asia/Singapore");
|
|
43859
|
+
const docs = await remarks.find({
|
|
43860
|
+
createdAtSGT: selectedDateSGT,
|
|
43861
|
+
$or: [
|
|
43862
|
+
{ "remarks.0.remark.status": "" },
|
|
43863
|
+
{ "remarks.1.remark.status": "" },
|
|
43864
|
+
{ "remarks.2.remark.status": "" }
|
|
43865
|
+
]
|
|
43866
|
+
}).toArray();
|
|
43867
|
+
for (const doc of docs) {
|
|
43868
|
+
const siteSettings = await settings.findOne(
|
|
43869
|
+
{ siteId: new import_mongodb116.ObjectId(doc.siteId), enabled: true },
|
|
43870
|
+
{ projection: { shifts: 1, shiftType: 1 } }
|
|
43871
|
+
);
|
|
43872
|
+
const shiftType = siteSettings?.shiftType || "2-shifts";
|
|
43873
|
+
const shiftsToCheck = [];
|
|
43874
|
+
shiftsToCheck.push({ index: 0, key: "dayShift" });
|
|
43875
|
+
if (shiftType === "3-shifts") {
|
|
43876
|
+
shiftsToCheck.push({ index: 1, key: "afternoonShift" });
|
|
43877
|
+
}
|
|
43878
|
+
if (currentSGT.isSame(selectedDateMoment, "day")) {
|
|
43879
|
+
if (currentSGT.isSameOrAfter(
|
|
43880
|
+
import_moment_timezone5.default.tz("19:55", "HH:mm", "Asia/Singapore")
|
|
43881
|
+
)) {
|
|
43882
|
+
shiftsToCheck.push({ index: 2, key: "nightShift" });
|
|
43883
|
+
}
|
|
43884
|
+
} else if (currentSGT.isAfter(selectedDateMoment, "day")) {
|
|
43885
|
+
shiftsToCheck.push({ index: 2, key: "nightShift" });
|
|
43886
|
+
}
|
|
43887
|
+
if (shiftsToCheck.length === 0)
|
|
43888
|
+
continue;
|
|
43889
|
+
const payload = {
|
|
43890
|
+
startDate: doc.createdAtSGT,
|
|
43891
|
+
endDate: doc.createdAtSGT,
|
|
43892
|
+
siteName: doc.siteName,
|
|
43893
|
+
siteId: doc.siteId.toString(),
|
|
43894
|
+
serviceProviderId: doc.serviceProviderId.toString()
|
|
43895
|
+
};
|
|
43896
|
+
const result = await _getAttendanceDataCount(payload);
|
|
43897
|
+
for (const shift of shiftsToCheck) {
|
|
43898
|
+
const actual = result?.totalCount?.[shift.key]?.actual || 0;
|
|
43899
|
+
const expected = result?.totalCount?.[shift.key]?.expected || 0;
|
|
43900
|
+
let newStatus = "Normal";
|
|
43901
|
+
if (actual > expected)
|
|
43902
|
+
newStatus = "Over";
|
|
43903
|
+
else if (actual < expected)
|
|
43904
|
+
newStatus = "Under";
|
|
43905
|
+
const namespace = `/manpower`;
|
|
43906
|
+
io.of(namespace).emit("manpower-status-update", {
|
|
43907
|
+
siteId: doc.siteId,
|
|
43908
|
+
siteName: doc.siteName,
|
|
43909
|
+
shift: shift.key,
|
|
43910
|
+
status: newStatus,
|
|
43911
|
+
actual,
|
|
43912
|
+
expected,
|
|
43913
|
+
selectedDateSGT
|
|
43914
|
+
});
|
|
43915
|
+
}
|
|
43916
|
+
}
|
|
43917
|
+
};
|
|
43918
|
+
const startInterval = (date) => {
|
|
43919
|
+
if (!intervalId) {
|
|
43920
|
+
intervalId = setInterval(
|
|
43921
|
+
() => updateRemarksStatus(date?.toString() || ""),
|
|
43922
|
+
15 * 1e3
|
|
43923
|
+
);
|
|
43924
|
+
console.log(" Interval started.");
|
|
43925
|
+
}
|
|
43926
|
+
};
|
|
43927
|
+
const stopInterval = () => {
|
|
43928
|
+
if (intervalId) {
|
|
43929
|
+
clearInterval(intervalId);
|
|
43930
|
+
intervalId = null;
|
|
43931
|
+
console.log(" Interval stopped.");
|
|
43932
|
+
}
|
|
43933
|
+
};
|
|
43934
|
+
io.of("/manpower").on("connection", (socket) => {
|
|
43935
|
+
activeConnections += 1;
|
|
43936
|
+
const date = socket.handshake.query.date;
|
|
43937
|
+
if (activeConnections === 1) {
|
|
43938
|
+
startInterval(date?.toString() || "");
|
|
43939
|
+
}
|
|
43940
|
+
updateRemarksStatus(date?.toString() || "");
|
|
43941
|
+
socket.on("disconnect", () => {
|
|
43942
|
+
activeConnections -= 1;
|
|
43943
|
+
console.log(`Client disconnected: ${socket.id}`);
|
|
43944
|
+
console.log(`Total active connections: ${activeConnections}`);
|
|
43945
|
+
if (activeConnections === 0) {
|
|
43946
|
+
stopInterval();
|
|
43947
|
+
}
|
|
43948
|
+
});
|
|
43949
|
+
});
|
|
43950
|
+
}
|
|
43071
43951
|
// Annotate the CommonJS export names for ESM import in node:
|
|
43072
43952
|
0 && (module.exports = {
|
|
43073
43953
|
ANPRMode,
|
|
@@ -43109,6 +43989,7 @@ function useManpowerRemarkCtrl() {
|
|
|
43109
43989
|
MManpowerDesignations,
|
|
43110
43990
|
MManpowerMonitoring,
|
|
43111
43991
|
MManpowerRemarks,
|
|
43992
|
+
MManpowerSites,
|
|
43112
43993
|
MMember,
|
|
43113
43994
|
MNfcPatrolLog,
|
|
43114
43995
|
MNfcPatrolRoute,
|
|
@@ -43174,6 +44055,7 @@ function useManpowerRemarkCtrl() {
|
|
|
43174
44055
|
bulletin_boards_namespace_collection,
|
|
43175
44056
|
calculatePercentage,
|
|
43176
44057
|
chatSchema,
|
|
44058
|
+
createManpowerRemarksDaily,
|
|
43177
44059
|
customerSchema,
|
|
43178
44060
|
designationsSchema,
|
|
43179
44061
|
events_namespace_collection,
|
|
@@ -43188,10 +44070,13 @@ function useManpowerRemarkCtrl() {
|
|
|
43188
44070
|
landscapeDashboardCollection,
|
|
43189
44071
|
mAndEDashboardCollection,
|
|
43190
44072
|
manpowerDesignationsSchema,
|
|
44073
|
+
manpowerEvents,
|
|
43191
44074
|
manpowerMonitoringSchema,
|
|
43192
44075
|
manpowerRemarksSchema,
|
|
44076
|
+
manpowerSitesSchema,
|
|
43193
44077
|
nfcPatrolSettingsSchema,
|
|
43194
44078
|
nfcPatrolSettingsSchemaUpdate,
|
|
44079
|
+
occurrence_book_namespace_collection,
|
|
43195
44080
|
orgSchema,
|
|
43196
44081
|
overnight_parking_requests_namespace_collection,
|
|
43197
44082
|
pestDashboardCollection,
|
|
@@ -43272,6 +44157,8 @@ function useManpowerRemarkCtrl() {
|
|
|
43272
44157
|
siteSchema,
|
|
43273
44158
|
site_people_namespace_collection,
|
|
43274
44159
|
tokenSchema,
|
|
44160
|
+
updateRemarksStatusEod,
|
|
44161
|
+
updateRemarksisAcknowledged,
|
|
43275
44162
|
updateSiteSchema,
|
|
43276
44163
|
useAccessManagementController,
|
|
43277
44164
|
useAddressRepo,
|
|
@@ -43338,6 +44225,9 @@ function useManpowerRemarkCtrl() {
|
|
|
43338
44225
|
useManpowerMonitoringSrvc,
|
|
43339
44226
|
useManpowerRemarkCtrl,
|
|
43340
44227
|
useManpowerRemarksRepo,
|
|
44228
|
+
useManpowerSitesCtrl,
|
|
44229
|
+
useManpowerSitesRepo,
|
|
44230
|
+
useManpowerSitesSrvc,
|
|
43341
44231
|
useMemberController,
|
|
43342
44232
|
useMemberRepo,
|
|
43343
44233
|
useNewDashboardController,
|