payservedb 8.4.5 → 8.4.6

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.
Files changed (180) hide show
  1. package/.env +2 -2
  2. package/ZOHO_INTEGRATION_SCHEMA.md +644 -644
  3. package/index.js +312 -310
  4. package/package.json +17 -17
  5. package/src/models/account.js +52 -52
  6. package/src/models/agent_departments.js +59 -59
  7. package/src/models/agent_notifications.js +53 -53
  8. package/src/models/agent_performance.js +127 -127
  9. package/src/models/agent_roles.js +77 -77
  10. package/src/models/agents.js +154 -154
  11. package/src/models/apilog.js +18 -18
  12. package/src/models/approvalsWorkflows.js +49 -49
  13. package/src/models/archivedapilog.js +18 -18
  14. package/src/models/asset.js +92 -92
  15. package/src/models/assetsAssignment.js +64 -64
  16. package/src/models/auditTrail.js +346 -346
  17. package/src/models/bankdetails.js +47 -47
  18. package/src/models/billerAddress.js +124 -124
  19. package/src/models/booking_invoice.js +165 -165
  20. package/src/models/bookinganalytics.js +63 -63
  21. package/src/models/bookingconfig.js +45 -45
  22. package/src/models/bookingproperty.js +173 -173
  23. package/src/models/bookingreservation.js +209 -209
  24. package/src/models/bookingrevenuerecord.js +84 -84
  25. package/src/models/budget.js +95 -95
  26. package/src/models/budgetCategory.js +19 -19
  27. package/src/models/campaigns.js +108 -108
  28. package/src/models/cashpayment.js +264 -264
  29. package/src/models/combinedUnits.js +62 -62
  30. package/src/models/common_area_electricity.js +38 -38
  31. package/src/models/common_area_generator.js +41 -41
  32. package/src/models/common_area_utility_alert.js +37 -37
  33. package/src/models/common_area_water.js +39 -39
  34. package/src/models/communication_status.js +33 -33
  35. package/src/models/communication_user_opt.js +32 -32
  36. package/src/models/community_guidelines.js +24 -24
  37. package/src/models/company.js +53 -53
  38. package/src/models/coreBaseSettings.js +16 -16
  39. package/src/models/coreInvoiceSettings.js +100 -100
  40. package/src/models/counter_schema.js +21 -21
  41. package/src/models/country_tax.js +42 -42
  42. package/src/models/currency_settings.js +39 -39
  43. package/src/models/customer.js +210 -210
  44. package/src/models/customer_satisfaction_survey.js +278 -278
  45. package/src/models/customer_surveys.js +139 -139
  46. package/src/models/customer_tickets.js +239 -239
  47. package/src/models/dailyChecklist.js +312 -312
  48. package/src/models/default_payment_details.js +17 -17
  49. package/src/models/deliveryTimeMarks.js +18 -18
  50. package/src/models/document_type.js +19 -19
  51. package/src/models/dutyRosterChecklist.js +250 -250
  52. package/src/models/dutyroster.js +136 -136
  53. package/src/models/email.js +37 -37
  54. package/src/models/email_sms_queue.js +61 -61
  55. package/src/models/entry_exit.js +53 -53
  56. package/src/models/expense.js +99 -99
  57. package/src/models/expense_category.js +45 -45
  58. package/src/models/facility.js +71 -63
  59. package/src/models/facilityBillingPrices.js +29 -29
  60. package/src/models/facilityInvoice.js +240 -240
  61. package/src/models/facilityInvoicePayment.js +52 -52
  62. package/src/models/facilityInvoiceRecipient.js +32 -32
  63. package/src/models/facilityWalletTransactionsMetadata.js +236 -236
  64. package/src/models/facility_departements.js +20 -20
  65. package/src/models/facility_payment_details.js +20 -20
  66. package/src/models/facilityasset.js +25 -25
  67. package/src/models/faq.js +14 -14
  68. package/src/models/gl_account_double_entries.js +25 -25
  69. package/src/models/gl_accounts.js +56 -56
  70. package/src/models/gl_entries.js +49 -49
  71. package/src/models/goodsReceivedNotes.js +115 -115
  72. package/src/models/guard.js +47 -47
  73. package/src/models/handover.js +247 -247
  74. package/src/models/inspection_category.js +38 -38
  75. package/src/models/invoice.js +480 -388
  76. package/src/models/invoicing_schedule.js +36 -36
  77. package/src/models/item_inspection.js +96 -96
  78. package/src/models/knowledge_base.js +109 -109
  79. package/src/models/knowledge_base_rating.js +44 -44
  80. package/src/models/leaseagreement.js +236 -236
  81. package/src/models/leasetemplate.js +17 -17
  82. package/src/models/levy.js +223 -223
  83. package/src/models/levy_invoice_settings.js +26 -26
  84. package/src/models/levycontract.js +177 -177
  85. package/src/models/levytype.js +23 -23
  86. package/src/models/maintenance_service_vendor.js +38 -38
  87. package/src/models/maintenance_services.js +17 -17
  88. package/src/models/maintenancerequisition.js +31 -31
  89. package/src/models/master_workplan.js +32 -32
  90. package/src/models/master_workplan_child.js +34 -34
  91. package/src/models/message.js +38 -38
  92. package/src/models/module.js +21 -21
  93. package/src/models/notification.js +44 -44
  94. package/src/models/paymentTermsMarks.js +19 -19
  95. package/src/models/penalty.js +76 -76
  96. package/src/models/pendingCredentials.js +32 -32
  97. package/src/models/powerMeterCommunicationProtocol.js +17 -17
  98. package/src/models/powerMeterCustomerAccount.js +78 -78
  99. package/src/models/powerMeterCustomerBand.js +14 -14
  100. package/src/models/powerMeterDailyReading.js +30 -30
  101. package/src/models/powerMeterGateways.js +40 -40
  102. package/src/models/powerMeterMonthlyReading.js +34 -34
  103. package/src/models/powerMeterPowerCharges.js +85 -85
  104. package/src/models/powerMeterSettings.js +159 -159
  105. package/src/models/powerMeterSingleDayReading.js +32 -32
  106. package/src/models/powerMeters.js +116 -116
  107. package/src/models/powerMetersManufacturer.js +14 -14
  108. package/src/models/power_meter_account.js +81 -81
  109. package/src/models/power_meter_command_logs.js +30 -30
  110. package/src/models/power_meter_command_queue.js +33 -33
  111. package/src/models/power_meter_negative_balance.js +44 -44
  112. package/src/models/power_prepaid_credits.js +47 -47
  113. package/src/models/power_prepaid_debits.js +53 -53
  114. package/src/models/power_prepaid_orders.js +78 -78
  115. package/src/models/power_sms_notification.js +26 -26
  116. package/src/models/privacy_policy.js +19 -19
  117. package/src/models/propertyManagerContract.js +556 -556
  118. package/src/models/propertyManagerRevenue.js +195 -195
  119. package/src/models/purchaseOrderInvoice.js +74 -74
  120. package/src/models/purchase_order.js +213 -213
  121. package/src/models/purchase_request.js +110 -110
  122. package/src/models/refresh_token.js +23 -23
  123. package/src/models/reminder.js +197 -197
  124. package/src/models/report.js +13 -13
  125. package/src/models/resident.js +121 -121
  126. package/src/models/rfq_details.js +131 -131
  127. package/src/models/rfq_response.js +153 -153
  128. package/src/models/service_charge_invoice_upload.js +42 -42
  129. package/src/models/service_charge_payments.js +27 -27
  130. package/src/models/servicerequest.js +55 -55
  131. package/src/models/settings.js +62 -62
  132. package/src/models/short_urls.js +21 -21
  133. package/src/models/smart_meter_daily_consumption.js +44 -44
  134. package/src/models/sms_africastalking.js +20 -20
  135. package/src/models/sms_balance_notification.js +26 -26
  136. package/src/models/sms_meliora.js +20 -20
  137. package/src/models/staff.js +36 -36
  138. package/src/models/stocksandspare.js +161 -161
  139. package/src/models/suppliers.js +74 -74
  140. package/src/models/terms_and_conditions.js +19 -19
  141. package/src/models/tickets.js +186 -186
  142. package/src/models/tickets_category.js +72 -72
  143. package/src/models/unitManagementTemplate.js +44 -44
  144. package/src/models/unitasset.js +25 -25
  145. package/src/models/units.js +118 -118
  146. package/src/models/user.js +186 -186
  147. package/src/models/valueaddedservices.js +79 -79
  148. package/src/models/vas_invoices_upload.js +50 -50
  149. package/src/models/vas_payments.js +24 -24
  150. package/src/models/vasinvoice.js +192 -192
  151. package/src/models/vasvendor.js +57 -57
  152. package/src/models/visitLog.js +95 -95
  153. package/src/models/visitor.js +67 -67
  154. package/src/models/waitlist.js +45 -45
  155. package/src/models/wallet.js +44 -44
  156. package/src/models/wallet_transactions.js +50 -50
  157. package/src/models/water_invoice.js +351 -351
  158. package/src/models/water_meter_Command_Queue.js +33 -33
  159. package/src/models/water_meter_account.js +87 -87
  160. package/src/models/water_meter_billing.js +58 -58
  161. package/src/models/water_meter_communication.js +17 -17
  162. package/src/models/water_meter_communication_logs.js +39 -39
  163. package/src/models/water_meter_concentrator.js +70 -70
  164. package/src/models/water_meter_daily_history.js +32 -32
  165. package/src/models/water_meter_high_risk.js +36 -36
  166. package/src/models/water_meter_iot_cards.js +34 -34
  167. package/src/models/water_meter_manufacturer.js +35 -35
  168. package/src/models/water_meter_monthly_history.js +36 -36
  169. package/src/models/water_meter_negative_amounts.js +44 -44
  170. package/src/models/water_meter_settings.js +287 -287
  171. package/src/models/water_meter_single_day_history.js +34 -34
  172. package/src/models/water_meter_size.js +15 -15
  173. package/src/models/water_meters.js +133 -133
  174. package/src/models/water_meters_delivery.js +76 -76
  175. package/src/models/water_prepaid_credit.js +47 -47
  176. package/src/models/water_prepaid_debit.js +50 -50
  177. package/src/models/workorder.js +49 -49
  178. package/src/models/zohoAccount.js +453 -0
  179. package/src/models/zohoIntegration.js +262 -262
  180. package/src/models/zohoItem.js +504 -0
@@ -1,312 +1,312 @@
1
- const mongoose = require("mongoose");
2
-
3
- // Reading entry schema - each individual reading with metadata
4
- const readingEntrySchema = new mongoose.Schema(
5
- {
6
- value: {
7
- type: mongoose.Schema.Types.Mixed, // String, Boolean, or Number
8
- required: true,
9
- },
10
- date: {
11
- type: Date,
12
- required: true,
13
- },
14
- recordedBy: {
15
- type: String,
16
- required: false, // User ID who recorded this reading
17
- },
18
- notes: {
19
- type: String,
20
- required: false, // Optional notes for this reading
21
- },
22
- isActive: {
23
- type: Boolean,
24
- default: true, // Allow soft deletion of readings
25
- },
26
- },
27
- { _id: true, timestamps: true }, // Keep _id for individual readings and timestamps
28
- );
29
-
30
- // Child property schema with historical readings
31
- const childPropertySchema = new mongoose.Schema(
32
- {
33
- name: {
34
- type: String,
35
- required: true, // Child property name (e.g., "fuel_level")
36
- },
37
- currentValue: {
38
- type: mongoose.Schema.Types.Mixed, // Latest value for quick access
39
- required: false,
40
- },
41
- currentDate: {
42
- type: Date,
43
- required: false, // Date of latest reading
44
- },
45
- unit: {
46
- type: String,
47
- required: false, // Unit of measurement (e.g., "%", "°C", "bar")
48
- },
49
- readings: {
50
- type: [readingEntrySchema], // Array of all historical readings
51
- default: [],
52
- },
53
- },
54
- { _id: true },
55
- );
56
-
57
- // Main facilities monitoring schema
58
- const dailyChecklistSchema = new mongoose.Schema(
59
- {
60
- facilityId: {
61
- type: String,
62
- required: true,
63
- },
64
- // Dynamic parent-child structure with historical readings
65
- // Parent_name -> [child_properties with readings]
66
- data: {
67
- type: Map,
68
- of: [childPropertySchema], // Array of child properties for each parent
69
- default: new Map(),
70
- },
71
- },
72
- {
73
- timestamps: true,
74
- },
75
- );
76
-
77
- // Helper methods
78
- dailyChecklistSchema.methods.addReading = function (
79
- parentName,
80
- childName,
81
- value,
82
- date = new Date(),
83
- metadata = {},
84
- ) {
85
- if (!this.data.has(parentName)) {
86
- this.data.set(parentName, []);
87
- }
88
-
89
- const parent = this.data.get(parentName);
90
- let childProperty = parent.find((child) => child.name === childName);
91
-
92
- if (!childProperty) {
93
- // Create new child property
94
- childProperty = {
95
- name: childName,
96
- currentValue: value,
97
- currentDate: date,
98
- unit: metadata.unit || null,
99
- readings: [],
100
- };
101
- parent.push(childProperty);
102
- }
103
-
104
- // Add new reading
105
- const newReading = {
106
- value: value,
107
- date: date,
108
- recordedBy: metadata.recordedBy || null,
109
- notes: metadata.notes || null,
110
- isActive: true,
111
- };
112
-
113
- childProperty.readings.push(newReading);
114
-
115
- // Update current values
116
- childProperty.currentValue = value;
117
- childProperty.currentDate = date;
118
-
119
- // Sort readings by date (newest first)
120
- childProperty.readings.sort((a, b) => new Date(b.date) - new Date(a.date));
121
-
122
- this.markModified("data");
123
- };
124
-
125
- dailyChecklistSchema.methods.getCurrentValue = function (
126
- parentName,
127
- childName,
128
- ) {
129
- const parent = this.data.get(parentName);
130
- if (parent) {
131
- const child = parent.find((c) => c.name === childName);
132
- return child ? child.currentValue : null;
133
- }
134
- return null;
135
- };
136
-
137
- dailyChecklistSchema.methods.getReadingHistory = function (
138
- parentName,
139
- childName,
140
- limit = null,
141
- ) {
142
- const parent = this.data.get(parentName);
143
- if (parent) {
144
- const child = parent.find((c) => c.name === childName);
145
- if (child) {
146
- const activeReadings = child.readings.filter((r) => r.isActive);
147
- return limit ? activeReadings.slice(0, limit) : activeReadings;
148
- }
149
- }
150
- return [];
151
- };
152
-
153
- dailyChecklistSchema.methods.getLatestReading = function (
154
- parentName,
155
- childName,
156
- ) {
157
- const parent = this.data.get(parentName);
158
- if (parent) {
159
- const child = parent.find((c) => c.name === childName);
160
- if (child && child.readings.length > 0) {
161
- return child.readings.find((r) => r.isActive) || null;
162
- }
163
- }
164
- return null;
165
- };
166
-
167
- dailyChecklistSchema.methods.updateReading = function (
168
- parentName,
169
- childName,
170
- readingId,
171
- updates,
172
- ) {
173
- const parent = this.data.get(parentName);
174
- if (parent) {
175
- const child = parent.find((c) => c.name === childName);
176
- if (child) {
177
- const reading = child.readings.id(readingId);
178
- if (reading) {
179
- Object.assign(reading, updates);
180
-
181
- // If this was the latest reading, update current values
182
- const latestReading = child.readings.find((r) => r.isActive);
183
- if (latestReading && latestReading._id.equals(readingId)) {
184
- child.currentValue = reading.value;
185
- child.currentDate = reading.date;
186
- }
187
-
188
- this.markModified("data");
189
- return true;
190
- }
191
- }
192
- }
193
- return false;
194
- };
195
-
196
- dailyChecklistSchema.methods.deleteReading = function (
197
- parentName,
198
- childName,
199
- readingId,
200
- ) {
201
- const parent = this.data.get(parentName);
202
- if (parent) {
203
- const child = parent.find((c) => c.name === childName);
204
- if (child) {
205
- const reading = child.readings.id(readingId);
206
- if (reading) {
207
- reading.isActive = false; // Soft delete
208
-
209
- // Update current values to next active reading
210
- const latestActiveReading = child.readings.find((r) => r.isActive);
211
- if (latestActiveReading) {
212
- child.currentValue = latestActiveReading.value;
213
- child.currentDate = latestActiveReading.date;
214
- } else {
215
- child.currentValue = null;
216
- child.currentDate = null;
217
- }
218
-
219
- this.markModified("data");
220
- return true;
221
- }
222
- }
223
- }
224
- return false;
225
- };
226
-
227
- dailyChecklistSchema.methods.createParent = function (parentName) {
228
- if (!this.data.has(parentName)) {
229
- this.data.set(parentName, []);
230
- this.markModified("data");
231
- }
232
- };
233
-
234
- dailyChecklistSchema.methods.hasParent = function (parentName) {
235
- return this.data.has(parentName);
236
- };
237
-
238
- dailyChecklistSchema.methods.getParentNames = function () {
239
- return Array.from(this.data.keys());
240
- };
241
-
242
- dailyChecklistSchema.methods.getChildNames = function (parentName) {
243
- const parent = this.data.get(parentName);
244
- return parent ? parent.map((child) => child.name) : [];
245
- };
246
-
247
- dailyChecklistSchema.methods.getChildProperty = function (
248
- parentName,
249
- childName,
250
- ) {
251
- const parent = this.data.get(parentName);
252
- if (parent) {
253
- return parent.find((child) => child.name === childName) || null;
254
- }
255
- return null;
256
- };
257
-
258
- // Get readings within a date range
259
- dailyChecklistSchema.methods.getReadingsByDateRange = function (
260
- parentName,
261
- childName,
262
- startDate,
263
- endDate,
264
- ) {
265
- const parent = this.data.get(parentName);
266
- if (parent) {
267
- const child = parent.find((c) => c.name === childName);
268
- if (child) {
269
- return child.readings.filter((reading) => {
270
- const readingDate = new Date(reading.date);
271
- return (
272
- reading.isActive &&
273
- readingDate >= new Date(startDate) &&
274
- readingDate <= new Date(endDate)
275
- );
276
- });
277
- }
278
- }
279
- return [];
280
- };
281
-
282
- // Get statistics for a child property
283
- dailyChecklistSchema.methods.getChildStatistics = function (
284
- parentName,
285
- childName,
286
- ) {
287
- const readings = this.getReadingHistory(parentName, childName);
288
- if (readings.length === 0) return null;
289
-
290
- const numericReadings = readings
291
- .map((r) => r.value)
292
- .filter((v) => typeof v === "number");
293
-
294
- if (numericReadings.length === 0) {
295
- return {
296
- totalReadings: readings.length,
297
- type: "non-numeric",
298
- };
299
- }
300
-
301
- return {
302
- totalReadings: readings.length,
303
- type: "numeric",
304
- min: Math.min(...numericReadings),
305
- max: Math.max(...numericReadings),
306
- average:
307
- numericReadings.reduce((a, b) => a + b, 0) / numericReadings.length,
308
- latest: readings[0].value,
309
- };
310
- };
311
-
312
- module.exports = mongoose.model("DailyChecklist", dailyChecklistSchema);
1
+ const mongoose = require("mongoose");
2
+
3
+ // Reading entry schema - each individual reading with metadata
4
+ const readingEntrySchema = new mongoose.Schema(
5
+ {
6
+ value: {
7
+ type: mongoose.Schema.Types.Mixed, // String, Boolean, or Number
8
+ required: true,
9
+ },
10
+ date: {
11
+ type: Date,
12
+ required: true,
13
+ },
14
+ recordedBy: {
15
+ type: String,
16
+ required: false, // User ID who recorded this reading
17
+ },
18
+ notes: {
19
+ type: String,
20
+ required: false, // Optional notes for this reading
21
+ },
22
+ isActive: {
23
+ type: Boolean,
24
+ default: true, // Allow soft deletion of readings
25
+ },
26
+ },
27
+ { _id: true, timestamps: true }, // Keep _id for individual readings and timestamps
28
+ );
29
+
30
+ // Child property schema with historical readings
31
+ const childPropertySchema = new mongoose.Schema(
32
+ {
33
+ name: {
34
+ type: String,
35
+ required: true, // Child property name (e.g., "fuel_level")
36
+ },
37
+ currentValue: {
38
+ type: mongoose.Schema.Types.Mixed, // Latest value for quick access
39
+ required: false,
40
+ },
41
+ currentDate: {
42
+ type: Date,
43
+ required: false, // Date of latest reading
44
+ },
45
+ unit: {
46
+ type: String,
47
+ required: false, // Unit of measurement (e.g., "%", "°C", "bar")
48
+ },
49
+ readings: {
50
+ type: [readingEntrySchema], // Array of all historical readings
51
+ default: [],
52
+ },
53
+ },
54
+ { _id: true },
55
+ );
56
+
57
+ // Main facilities monitoring schema
58
+ const dailyChecklistSchema = new mongoose.Schema(
59
+ {
60
+ facilityId: {
61
+ type: String,
62
+ required: true,
63
+ },
64
+ // Dynamic parent-child structure with historical readings
65
+ // Parent_name -> [child_properties with readings]
66
+ data: {
67
+ type: Map,
68
+ of: [childPropertySchema], // Array of child properties for each parent
69
+ default: new Map(),
70
+ },
71
+ },
72
+ {
73
+ timestamps: true,
74
+ },
75
+ );
76
+
77
+ // Helper methods
78
+ dailyChecklistSchema.methods.addReading = function (
79
+ parentName,
80
+ childName,
81
+ value,
82
+ date = new Date(),
83
+ metadata = {},
84
+ ) {
85
+ if (!this.data.has(parentName)) {
86
+ this.data.set(parentName, []);
87
+ }
88
+
89
+ const parent = this.data.get(parentName);
90
+ let childProperty = parent.find((child) => child.name === childName);
91
+
92
+ if (!childProperty) {
93
+ // Create new child property
94
+ childProperty = {
95
+ name: childName,
96
+ currentValue: value,
97
+ currentDate: date,
98
+ unit: metadata.unit || null,
99
+ readings: [],
100
+ };
101
+ parent.push(childProperty);
102
+ }
103
+
104
+ // Add new reading
105
+ const newReading = {
106
+ value: value,
107
+ date: date,
108
+ recordedBy: metadata.recordedBy || null,
109
+ notes: metadata.notes || null,
110
+ isActive: true,
111
+ };
112
+
113
+ childProperty.readings.push(newReading);
114
+
115
+ // Update current values
116
+ childProperty.currentValue = value;
117
+ childProperty.currentDate = date;
118
+
119
+ // Sort readings by date (newest first)
120
+ childProperty.readings.sort((a, b) => new Date(b.date) - new Date(a.date));
121
+
122
+ this.markModified("data");
123
+ };
124
+
125
+ dailyChecklistSchema.methods.getCurrentValue = function (
126
+ parentName,
127
+ childName,
128
+ ) {
129
+ const parent = this.data.get(parentName);
130
+ if (parent) {
131
+ const child = parent.find((c) => c.name === childName);
132
+ return child ? child.currentValue : null;
133
+ }
134
+ return null;
135
+ };
136
+
137
+ dailyChecklistSchema.methods.getReadingHistory = function (
138
+ parentName,
139
+ childName,
140
+ limit = null,
141
+ ) {
142
+ const parent = this.data.get(parentName);
143
+ if (parent) {
144
+ const child = parent.find((c) => c.name === childName);
145
+ if (child) {
146
+ const activeReadings = child.readings.filter((r) => r.isActive);
147
+ return limit ? activeReadings.slice(0, limit) : activeReadings;
148
+ }
149
+ }
150
+ return [];
151
+ };
152
+
153
+ dailyChecklistSchema.methods.getLatestReading = function (
154
+ parentName,
155
+ childName,
156
+ ) {
157
+ const parent = this.data.get(parentName);
158
+ if (parent) {
159
+ const child = parent.find((c) => c.name === childName);
160
+ if (child && child.readings.length > 0) {
161
+ return child.readings.find((r) => r.isActive) || null;
162
+ }
163
+ }
164
+ return null;
165
+ };
166
+
167
+ dailyChecklistSchema.methods.updateReading = function (
168
+ parentName,
169
+ childName,
170
+ readingId,
171
+ updates,
172
+ ) {
173
+ const parent = this.data.get(parentName);
174
+ if (parent) {
175
+ const child = parent.find((c) => c.name === childName);
176
+ if (child) {
177
+ const reading = child.readings.id(readingId);
178
+ if (reading) {
179
+ Object.assign(reading, updates);
180
+
181
+ // If this was the latest reading, update current values
182
+ const latestReading = child.readings.find((r) => r.isActive);
183
+ if (latestReading && latestReading._id.equals(readingId)) {
184
+ child.currentValue = reading.value;
185
+ child.currentDate = reading.date;
186
+ }
187
+
188
+ this.markModified("data");
189
+ return true;
190
+ }
191
+ }
192
+ }
193
+ return false;
194
+ };
195
+
196
+ dailyChecklistSchema.methods.deleteReading = function (
197
+ parentName,
198
+ childName,
199
+ readingId,
200
+ ) {
201
+ const parent = this.data.get(parentName);
202
+ if (parent) {
203
+ const child = parent.find((c) => c.name === childName);
204
+ if (child) {
205
+ const reading = child.readings.id(readingId);
206
+ if (reading) {
207
+ reading.isActive = false; // Soft delete
208
+
209
+ // Update current values to next active reading
210
+ const latestActiveReading = child.readings.find((r) => r.isActive);
211
+ if (latestActiveReading) {
212
+ child.currentValue = latestActiveReading.value;
213
+ child.currentDate = latestActiveReading.date;
214
+ } else {
215
+ child.currentValue = null;
216
+ child.currentDate = null;
217
+ }
218
+
219
+ this.markModified("data");
220
+ return true;
221
+ }
222
+ }
223
+ }
224
+ return false;
225
+ };
226
+
227
+ dailyChecklistSchema.methods.createParent = function (parentName) {
228
+ if (!this.data.has(parentName)) {
229
+ this.data.set(parentName, []);
230
+ this.markModified("data");
231
+ }
232
+ };
233
+
234
+ dailyChecklistSchema.methods.hasParent = function (parentName) {
235
+ return this.data.has(parentName);
236
+ };
237
+
238
+ dailyChecklistSchema.methods.getParentNames = function () {
239
+ return Array.from(this.data.keys());
240
+ };
241
+
242
+ dailyChecklistSchema.methods.getChildNames = function (parentName) {
243
+ const parent = this.data.get(parentName);
244
+ return parent ? parent.map((child) => child.name) : [];
245
+ };
246
+
247
+ dailyChecklistSchema.methods.getChildProperty = function (
248
+ parentName,
249
+ childName,
250
+ ) {
251
+ const parent = this.data.get(parentName);
252
+ if (parent) {
253
+ return parent.find((child) => child.name === childName) || null;
254
+ }
255
+ return null;
256
+ };
257
+
258
+ // Get readings within a date range
259
+ dailyChecklistSchema.methods.getReadingsByDateRange = function (
260
+ parentName,
261
+ childName,
262
+ startDate,
263
+ endDate,
264
+ ) {
265
+ const parent = this.data.get(parentName);
266
+ if (parent) {
267
+ const child = parent.find((c) => c.name === childName);
268
+ if (child) {
269
+ return child.readings.filter((reading) => {
270
+ const readingDate = new Date(reading.date);
271
+ return (
272
+ reading.isActive &&
273
+ readingDate >= new Date(startDate) &&
274
+ readingDate <= new Date(endDate)
275
+ );
276
+ });
277
+ }
278
+ }
279
+ return [];
280
+ };
281
+
282
+ // Get statistics for a child property
283
+ dailyChecklistSchema.methods.getChildStatistics = function (
284
+ parentName,
285
+ childName,
286
+ ) {
287
+ const readings = this.getReadingHistory(parentName, childName);
288
+ if (readings.length === 0) return null;
289
+
290
+ const numericReadings = readings
291
+ .map((r) => r.value)
292
+ .filter((v) => typeof v === "number");
293
+
294
+ if (numericReadings.length === 0) {
295
+ return {
296
+ totalReadings: readings.length,
297
+ type: "non-numeric",
298
+ };
299
+ }
300
+
301
+ return {
302
+ totalReadings: readings.length,
303
+ type: "numeric",
304
+ min: Math.min(...numericReadings),
305
+ max: Math.max(...numericReadings),
306
+ average:
307
+ numericReadings.reduce((a, b) => a + b, 0) / numericReadings.length,
308
+ latest: readings[0].value,
309
+ };
310
+ };
311
+
312
+ module.exports = mongoose.model("DailyChecklist", dailyChecklistSchema);
@@ -1,18 +1,18 @@
1
- const mongoose = require("mongoose");
2
-
3
- const defaultPaymentDetailsSchema = new mongoose.Schema({
4
- shortCode: { type: String },
5
- passkey: { type: String },
6
- authorizationKey: {
7
- type: String,
8
- },
9
- module: {
10
- type: String,
11
- enum: ["All", "Water", "Electricity", "Levy","Lease"],
12
- default: "All"
13
- },
14
- });
15
-
16
- const DefaultPaymentDetails = mongoose.model('DefaultPaymentDetails', defaultPaymentDetailsSchema);
17
-
1
+ const mongoose = require("mongoose");
2
+
3
+ const defaultPaymentDetailsSchema = new mongoose.Schema({
4
+ shortCode: { type: String },
5
+ passkey: { type: String },
6
+ authorizationKey: {
7
+ type: String,
8
+ },
9
+ module: {
10
+ type: String,
11
+ enum: ["All", "Water", "Electricity", "Levy","Lease"],
12
+ default: "All"
13
+ },
14
+ });
15
+
16
+ const DefaultPaymentDetails = mongoose.model('DefaultPaymentDetails', defaultPaymentDetailsSchema);
17
+
18
18
  module.exports = DefaultPaymentDetails;