dt-common-device 9.1.6 → 9.1.8

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 (29) hide show
  1. package/dist/alerts/alert.types.d.ts +2 -1
  2. package/dist/alerts/alert.types.js +1 -0
  3. package/dist/copilotQueue/index.d.ts +4 -0
  4. package/dist/copilotQueue/index.js +21 -0
  5. package/dist/copilotQueue/interfaces/ICopilotQueueRequest.d.ts +27 -0
  6. package/dist/copilotQueue/interfaces/ICopilotQueueRequest.js +2 -0
  7. package/dist/copilotQueue/interfaces/ICopilotQueueService.d.ts +24 -0
  8. package/dist/copilotQueue/interfaces/ICopilotQueueService.js +2 -0
  9. package/dist/copilotQueue/interfaces/index.d.ts +2 -0
  10. package/dist/copilotQueue/interfaces/index.js +18 -0
  11. package/dist/copilotQueue/services/CopilotQueue.service.d.ts +13 -0
  12. package/dist/copilotQueue/services/CopilotQueue.service.js +196 -0
  13. package/dist/copilotQueue/services/index.d.ts +1 -0
  14. package/dist/copilotQueue/services/index.js +17 -0
  15. package/dist/copilotQueue/types/copilot.types.d.ts +13 -0
  16. package/dist/copilotQueue/types/copilot.types.js +2 -0
  17. package/dist/copilotQueue/types/index.d.ts +1 -0
  18. package/dist/copilotQueue/types/index.js +17 -0
  19. package/dist/copilotQueue/utils/index.d.ts +1 -0
  20. package/dist/copilotQueue/utils/index.js +17 -0
  21. package/dist/copilotQueue/utils/queueManager.d.ts +31 -0
  22. package/dist/copilotQueue/utils/queueManager.js +156 -0
  23. package/dist/cronicle/Cronicle.service.js +3 -2
  24. package/dist/cronicle/ICronicle.interface.d.ts +2 -1
  25. package/dist/index.d.ts +1 -0
  26. package/dist/index.js +2 -0
  27. package/dist/issues/issue.types.d.ts +3 -1
  28. package/dist/issues/issue.types.js +2 -0
  29. package/package.json +1 -1
@@ -25,7 +25,8 @@ export declare enum AlertType {
25
25
  GUEST_LOCK_FIRST_ACCESS = "GUEST_LOCK_FIRST_ACCESS",
26
26
  DEVICE_ONLINE = "DEVICE_ONLINE",
27
27
  ZONE_NOT_MAPPED_TO_ACCESS_GROUP = "ZONE_NOT_MAPPED_TO_ACCESS_GROUP",
28
- INCORRECT_CODE_USED = "INCORRECT_CODE_USED"
28
+ INCORRECT_CODE_USED = "INCORRECT_CODE_USED",
29
+ LOW_GUEST_CODES = "LOW_GUEST_CODES"
29
30
  }
30
31
  export interface AlertDocument {
31
32
  _id: string;
@@ -31,6 +31,7 @@ var AlertType;
31
31
  AlertType["DEVICE_ONLINE"] = "DEVICE_ONLINE";
32
32
  AlertType["ZONE_NOT_MAPPED_TO_ACCESS_GROUP"] = "ZONE_NOT_MAPPED_TO_ACCESS_GROUP";
33
33
  AlertType["INCORRECT_CODE_USED"] = "INCORRECT_CODE_USED";
34
+ AlertType["LOW_GUEST_CODES"] = "LOW_GUEST_CODES";
34
35
  })(AlertType || (exports.AlertType = AlertType = {}));
35
36
  // Re-export EntityType from issue.types.ts to avoid duplication
36
37
  var issue_types_1 = require("../issues/issue.types");
@@ -0,0 +1,4 @@
1
+ export * from "./interfaces";
2
+ export * from "./services";
3
+ export * from "./types";
4
+ export * from "./utils";
@@ -0,0 +1,21 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __exportStar = (this && this.__exportStar) || function(m, exports) {
14
+ for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
15
+ };
16
+ Object.defineProperty(exports, "__esModule", { value: true });
17
+ // Main copilot queue exports
18
+ __exportStar(require("./interfaces"), exports);
19
+ __exportStar(require("./services"), exports);
20
+ __exportStar(require("./types"), exports);
21
+ __exportStar(require("./utils"), exports);
@@ -0,0 +1,27 @@
1
+ export interface ICopilotQueueRequest {
2
+ url: string;
3
+ method: "GET" | "POST" | "PUT" | "DELETE";
4
+ headers?: Record<string, string>;
5
+ params?: Record<string, string>;
6
+ query?: Record<string, string>;
7
+ body: any;
8
+ timestamp?: number;
9
+ jobId?: string;
10
+ }
11
+ export interface ICopilotQueueResponse {
12
+ success: boolean;
13
+ data?: any;
14
+ error?: string;
15
+ jobId: string;
16
+ propertyId: string;
17
+ processingTime?: number;
18
+ }
19
+ export interface ICopilotQueueOptions {
20
+ delay?: number;
21
+ priority?: number;
22
+ attempts?: number;
23
+ backoff?: {
24
+ type: "fixed" | "exponential";
25
+ delay: number;
26
+ };
27
+ }
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,24 @@
1
+ import { ICopilotQueueRequest, ICopilotQueueOptions } from "./ICopilotQueueRequest";
2
+ export interface ICopilotQueueService {
3
+ /**
4
+ * Add a request to the queue for processing
5
+ * @param request - The request data including URL, method, headers, and body (with propertyId)
6
+ * @param options - Optional queue configuration
7
+ * @returns Promise with job ID and queue response
8
+ */
9
+ addQueueRequest(request: ICopilotQueueRequest, options?: ICopilotQueueOptions): Promise<{
10
+ jobId: string;
11
+ queued: boolean;
12
+ }>;
13
+ /**
14
+ * Get the status of a queued job
15
+ * @param jobId - The job ID to check
16
+ * @returns Promise with job status
17
+ */
18
+ getJobStatus(jobId: string): Promise<any>;
19
+ /**
20
+ * Shutdown the queue service
21
+ * @returns Promise that resolves when shutdown is complete
22
+ */
23
+ shutdown(): Promise<void>;
24
+ }
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,2 @@
1
+ export * from "./ICopilotQueueRequest";
2
+ export * from "./ICopilotQueueService";
@@ -0,0 +1,18 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __exportStar = (this && this.__exportStar) || function(m, exports) {
14
+ for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
15
+ };
16
+ Object.defineProperty(exports, "__esModule", { value: true });
17
+ __exportStar(require("./ICopilotQueueRequest"), exports);
18
+ __exportStar(require("./ICopilotQueueService"), exports);
@@ -0,0 +1,13 @@
1
+ import { ICopilotQueueService, ICopilotQueueRequest, ICopilotQueueOptions } from "../interfaces";
2
+ export declare class CopilotQueueService implements ICopilotQueueService {
3
+ private readonly copilotQueues;
4
+ private readonly workers;
5
+ constructor();
6
+ private processRequest;
7
+ addQueueRequest(request: ICopilotQueueRequest, options?: ICopilotQueueOptions): Promise<{
8
+ jobId: string;
9
+ queued: boolean;
10
+ }>;
11
+ getJobStatus(jobId: string): Promise<any>;
12
+ shutdown(): Promise<void>;
13
+ }
@@ -0,0 +1,196 @@
1
+ "use strict";
2
+ var __esDecorate = (this && this.__esDecorate) || function (ctor, descriptorIn, decorators, contextIn, initializers, extraInitializers) {
3
+ function accept(f) { if (f !== void 0 && typeof f !== "function") throw new TypeError("Function expected"); return f; }
4
+ var kind = contextIn.kind, key = kind === "getter" ? "get" : kind === "setter" ? "set" : "value";
5
+ var target = !descriptorIn && ctor ? contextIn["static"] ? ctor : ctor.prototype : null;
6
+ var descriptor = descriptorIn || (target ? Object.getOwnPropertyDescriptor(target, contextIn.name) : {});
7
+ var _, done = false;
8
+ for (var i = decorators.length - 1; i >= 0; i--) {
9
+ var context = {};
10
+ for (var p in contextIn) context[p] = p === "access" ? {} : contextIn[p];
11
+ for (var p in contextIn.access) context.access[p] = contextIn.access[p];
12
+ context.addInitializer = function (f) { if (done) throw new TypeError("Cannot add initializers after decoration has completed"); extraInitializers.push(accept(f || null)); };
13
+ var result = (0, decorators[i])(kind === "accessor" ? { get: descriptor.get, set: descriptor.set } : descriptor[key], context);
14
+ if (kind === "accessor") {
15
+ if (result === void 0) continue;
16
+ if (result === null || typeof result !== "object") throw new TypeError("Object expected");
17
+ if (_ = accept(result.get)) descriptor.get = _;
18
+ if (_ = accept(result.set)) descriptor.set = _;
19
+ if (_ = accept(result.init)) initializers.unshift(_);
20
+ }
21
+ else if (_ = accept(result)) {
22
+ if (kind === "field") initializers.unshift(_);
23
+ else descriptor[key] = _;
24
+ }
25
+ }
26
+ if (target) Object.defineProperty(target, contextIn.name, descriptor);
27
+ done = true;
28
+ };
29
+ var __runInitializers = (this && this.__runInitializers) || function (thisArg, initializers, value) {
30
+ var useValue = arguments.length > 2;
31
+ for (var i = 0; i < initializers.length; i++) {
32
+ value = useValue ? initializers[i].call(thisArg, value) : initializers[i].call(thisArg);
33
+ }
34
+ return useValue ? value : void 0;
35
+ };
36
+ var __setFunctionName = (this && this.__setFunctionName) || function (f, name, prefix) {
37
+ if (typeof name === "symbol") name = name.description ? "[".concat(name.description, "]") : "";
38
+ return Object.defineProperty(f, "name", { configurable: true, value: prefix ? "".concat(prefix, " ", name) : name });
39
+ };
40
+ var __importDefault = (this && this.__importDefault) || function (mod) {
41
+ return (mod && mod.__esModule) ? mod : { "default": mod };
42
+ };
43
+ Object.defineProperty(exports, "__esModule", { value: true });
44
+ exports.CopilotQueueService = void 0;
45
+ const typedi_1 = require("typedi");
46
+ const axios_1 = __importDefault(require("axios"));
47
+ const config_1 = require("../../config/config");
48
+ const utils_1 = require("../utils");
49
+ let CopilotQueueService = (() => {
50
+ let _classDecorators = [(0, typedi_1.Service)()];
51
+ let _classDescriptor;
52
+ let _classExtraInitializers = [];
53
+ let _classThis;
54
+ var CopilotQueueService = _classThis = class {
55
+ constructor() {
56
+ this.copilotQueues = new Map(); // BullMQ Queue instances
57
+ this.workers = new Map(); // BullMQ Worker instances
58
+ }
59
+ async processRequest(job) {
60
+ const { url, method, headers, body } = job.data;
61
+ const propertyId = body?.propertyId;
62
+ const startTime = Date.now();
63
+ try {
64
+ (0, config_1.getConfig)().LOGGER.info(`Processing request for property ${propertyId}: ${method} ${url}`);
65
+ // Prepare axios request configuration
66
+ const axiosConfig = {
67
+ method: method.toLowerCase(),
68
+ url,
69
+ headers: {
70
+ "Content-Type": "application/json",
71
+ ...headers,
72
+ },
73
+ timeout: 30000, // 30 second timeout
74
+ };
75
+ // Add body for POST, PUT, PATCH requests
76
+ if (body && ["post", "put", "patch"].includes(method.toLowerCase())) {
77
+ axiosConfig.data = body;
78
+ }
79
+ // Execute the HTTP request (fire and forget - no response processing)
80
+ await (0, axios_1.default)(axiosConfig);
81
+ const responseTime = Date.now() - startTime;
82
+ (0, config_1.getConfig)().LOGGER.info(`Request executed for property ${propertyId}: ${method} ${url} (${responseTime}ms)`);
83
+ return {
84
+ success: true,
85
+ responseTime,
86
+ };
87
+ }
88
+ catch (error) {
89
+ const responseTime = Date.now() - startTime;
90
+ const errorMessage = error.response?.data?.message || error.message || "Unknown error";
91
+ (0, config_1.getConfig)().LOGGER.error(`Request failed for property ${propertyId}: ${errorMessage} (${responseTime}ms)`);
92
+ return {
93
+ success: false,
94
+ error: errorMessage,
95
+ statusCode: error.response?.status || 500,
96
+ responseTime,
97
+ };
98
+ }
99
+ }
100
+ async addQueueRequest(request, options) {
101
+ try {
102
+ // Validate required fields
103
+ if (!request.url ||
104
+ !request.method ||
105
+ !request.body ||
106
+ !request.body.propertyId) {
107
+ throw new Error("Missing required fields: url, method, and body with propertyId are required");
108
+ }
109
+ const propertyId = request.body.propertyId;
110
+ const queueName = utils_1.QueueManager.generateQueueName(propertyId);
111
+ // Get or create queue and worker using the QueueManager
112
+ const queue = await utils_1.QueueManager.getOrCreateQueue(queueName, this.copilotQueues);
113
+ // Create worker for this queue if it doesn't exist
114
+ await utils_1.QueueManager.getOrCreateWorker(queueName, this.workers, this.copilotQueues, this.processRequest.bind(this));
115
+ // Prepare job data
116
+ const jobData = {
117
+ url: request.url,
118
+ method: request.method,
119
+ headers: request.headers,
120
+ body: request.body,
121
+ timestamp: Date.now(),
122
+ };
123
+ // Add job to queue with TTL (similar to WebhookQueueService)
124
+ const job = await queue.add("copilot-request", jobData, {
125
+ removeOnComplete: { age: 5 * 60 }, // Remove after 5 minutes
126
+ removeOnFail: { age: 10 * 60 }, // Remove failed jobs after 10 minutes
127
+ attempts: 1, // No retries - execute only once
128
+ delay: options?.delay || 0,
129
+ priority: options?.priority || 0,
130
+ // Use propertyId as job group to ensure FIFO ordering per property
131
+ jobId: utils_1.QueueManager.generateJobId(propertyId),
132
+ });
133
+ (0, config_1.getConfig)().LOGGER.info(`Request queued for property ${propertyId}: ${request.method} ${request.url} (Job ID: ${job.id})`);
134
+ return {
135
+ jobId: job.id,
136
+ queued: true,
137
+ };
138
+ }
139
+ catch (error) {
140
+ (0, config_1.getConfig)().LOGGER.error("Failed to add request to queue:", error.message);
141
+ throw error;
142
+ }
143
+ }
144
+ async getJobStatus(jobId) {
145
+ try {
146
+ // Extract propertyId from jobId (format: propertyId-timestamp-random)
147
+ const propertyId = utils_1.QueueManager.extractPropertyIdFromJobId(jobId);
148
+ const queueName = utils_1.QueueManager.generateQueueName(propertyId);
149
+ // Get or create queue
150
+ const queue = await utils_1.QueueManager.getOrCreateQueue(queueName, this.copilotQueues);
151
+ const job = await queue.getJob(jobId);
152
+ if (!job) {
153
+ return { exists: false };
154
+ }
155
+ const state = await job.getState();
156
+ return {
157
+ exists: true,
158
+ id: job.id,
159
+ state,
160
+ data: job.data,
161
+ progress: job.progress,
162
+ returnvalue: job.returnvalue,
163
+ failedReason: job.failedReason,
164
+ processedOn: job.processedOn,
165
+ finishedOn: job.finishedOn,
166
+ };
167
+ }
168
+ catch (error) {
169
+ (0, config_1.getConfig)().LOGGER.error(`Failed to get job status for ${jobId}:`, error.message);
170
+ throw error;
171
+ }
172
+ }
173
+ async shutdown() {
174
+ try {
175
+ (0, config_1.getConfig)().LOGGER.info("Shutting down CopilotQueue service...");
176
+ // Close all workers and queues using QueueManager
177
+ await utils_1.QueueManager.closeAllWorkersAndQueues(this.workers, this.copilotQueues);
178
+ (0, config_1.getConfig)().LOGGER.info("CopilotQueue service shutdown complete");
179
+ }
180
+ catch (error) {
181
+ (0, config_1.getConfig)().LOGGER.error("Error during CopilotQueue shutdown:", error.message);
182
+ throw error;
183
+ }
184
+ }
185
+ };
186
+ __setFunctionName(_classThis, "CopilotQueueService");
187
+ (() => {
188
+ const _metadata = typeof Symbol === "function" && Symbol.metadata ? Object.create(null) : void 0;
189
+ __esDecorate(null, _classDescriptor = { value: _classThis }, _classDecorators, { kind: "class", name: _classThis.name, metadata: _metadata }, null, _classExtraInitializers);
190
+ CopilotQueueService = _classThis = _classDescriptor.value;
191
+ if (_metadata) Object.defineProperty(_classThis, Symbol.metadata, { enumerable: true, configurable: true, writable: true, value: _metadata });
192
+ __runInitializers(_classThis, _classExtraInitializers);
193
+ })();
194
+ return CopilotQueueService = _classThis;
195
+ })();
196
+ exports.CopilotQueueService = CopilotQueueService;
@@ -0,0 +1 @@
1
+ export * from "./CopilotQueue.service";
@@ -0,0 +1,17 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __exportStar = (this && this.__exportStar) || function(m, exports) {
14
+ for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
15
+ };
16
+ Object.defineProperty(exports, "__esModule", { value: true });
17
+ __exportStar(require("./CopilotQueue.service"), exports);
@@ -0,0 +1,13 @@
1
+ import { Job, Queue, Worker } from "bullmq";
2
+ export interface CopilotJobData {
3
+ url: string;
4
+ method: "GET" | "POST" | "PUT" | "DELETE";
5
+ params?: Record<string, string>;
6
+ query?: Record<string, string>;
7
+ headers?: Record<string, string>;
8
+ body: any;
9
+ timestamp?: number;
10
+ }
11
+ export type CopilotQueue = Queue<CopilotJobData>;
12
+ export type CopilotWorker = Worker<CopilotJobData>;
13
+ export type CopilotJob = Job<CopilotJobData>;
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1 @@
1
+ export * from "./copilot.types";
@@ -0,0 +1,17 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __exportStar = (this && this.__exportStar) || function(m, exports) {
14
+ for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
15
+ };
16
+ Object.defineProperty(exports, "__esModule", { value: true });
17
+ __exportStar(require("./copilot.types"), exports);
@@ -0,0 +1 @@
1
+ export * from "./queueManager";
@@ -0,0 +1,17 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __exportStar = (this && this.__exportStar) || function(m, exports) {
14
+ for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
15
+ };
16
+ Object.defineProperty(exports, "__esModule", { value: true });
17
+ __exportStar(require("./queueManager"), exports);
@@ -0,0 +1,31 @@
1
+ import { Job } from "bullmq";
2
+ export declare class QueueManager {
3
+ /**
4
+ * Get or create a BullMQ queue
5
+ */
6
+ static getOrCreateQueue(queueKey: string, queues: Map<string, any>): Promise<any>;
7
+ /**
8
+ * Get or create a BullMQ worker
9
+ */
10
+ static getOrCreateWorker(queueKey: string, workers: Map<string, any>, queues: Map<string, any>, processor: (job: Job) => Promise<any>): Promise<any>;
11
+ /**
12
+ * Check if queue is empty and cleanup worker if no jobs are pending
13
+ */
14
+ static checkAndCleanupWorker(queueKey: string, workers: Map<string, any>, queues: Map<string, any>): Promise<void>;
15
+ /**
16
+ * Close all workers and queues
17
+ */
18
+ static closeAllWorkersAndQueues(workers: Map<string, any>, queues: Map<string, any>): Promise<void>;
19
+ /**
20
+ * Generate queue name for a property
21
+ */
22
+ static generateQueueName(propertyId: string): string;
23
+ /**
24
+ * Extract property ID from job ID
25
+ */
26
+ static extractPropertyIdFromJobId(jobId: string): string;
27
+ /**
28
+ * Generate unique job ID
29
+ */
30
+ static generateJobId(propertyId: string): string;
31
+ }
@@ -0,0 +1,156 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ Object.defineProperty(exports, "__esModule", { value: true });
36
+ exports.QueueManager = void 0;
37
+ const redis_1 = require("../../db/redis");
38
+ const config_1 = require("../../config/config");
39
+ class QueueManager {
40
+ /**
41
+ * Get or create a BullMQ queue
42
+ */
43
+ static async getOrCreateQueue(queueKey, queues) {
44
+ if (queues.has(queueKey)) {
45
+ return queues.get(queueKey);
46
+ }
47
+ const { Queue } = await Promise.resolve().then(() => __importStar(require("bullmq")));
48
+ const queue = new Queue(queueKey, {
49
+ connection: (0, redis_1.getRedisClient)(),
50
+ });
51
+ queues.set(queueKey, queue);
52
+ return queue;
53
+ }
54
+ /**
55
+ * Get or create a BullMQ worker
56
+ */
57
+ static async getOrCreateWorker(queueKey, workers, queues, processor) {
58
+ if (workers.has(queueKey)) {
59
+ return workers.get(queueKey);
60
+ }
61
+ const { Worker } = await Promise.resolve().then(() => __importStar(require("bullmq")));
62
+ const worker = new Worker(queueKey, processor, {
63
+ connection: (0, redis_1.getRedisClient)(),
64
+ concurrency: 1, // Process one job at a time for FIFO ordering
65
+ });
66
+ // Setup event listeners
67
+ worker.on("completed", async (job) => {
68
+ const propertyId = job.data.body?.propertyId || "unknown";
69
+ (0, config_1.getConfig)().LOGGER.info(`Job ${job.id} completed for property ${propertyId}`);
70
+ // Check if queue is empty and cleanup worker
71
+ await QueueManager.checkAndCleanupWorker(queueKey, workers, queues);
72
+ });
73
+ worker.on("failed", async (job, err) => {
74
+ const propertyId = job?.data?.body?.propertyId || "unknown";
75
+ (0, config_1.getConfig)().LOGGER.error(`Job ${job?.id} failed for property ${propertyId}:`, err.message);
76
+ // Check if queue is empty and cleanup worker
77
+ await QueueManager.checkAndCleanupWorker(queueKey, workers, queues);
78
+ });
79
+ worker.on("error", (err) => {
80
+ (0, config_1.getConfig)().LOGGER.error("Worker error:", err.message);
81
+ });
82
+ workers.set(queueKey, worker);
83
+ return worker;
84
+ }
85
+ /**
86
+ * Check if queue is empty and cleanup worker if no jobs are pending
87
+ */
88
+ static async checkAndCleanupWorker(queueKey, workers, queues) {
89
+ try {
90
+ const queue = queues.get(queueKey);
91
+ if (!queue)
92
+ return;
93
+ // Check if queue has any waiting, active, or delayed jobs
94
+ const [waiting, active, delayed] = await Promise.all([
95
+ queue.getWaiting(),
96
+ queue.getActive(),
97
+ queue.getDelayed(),
98
+ ]);
99
+ const totalJobs = waiting.length + active.length + delayed.length;
100
+ // If no jobs are pending, cleanup the worker
101
+ if (totalJobs === 0) {
102
+ const worker = workers.get(queueKey);
103
+ if (worker) {
104
+ await worker.close();
105
+ workers.delete(queueKey);
106
+ // Extract propertyId from queueKey (format: propertyId_copilot)
107
+ const propertyId = queueKey.replace("_copilot", "");
108
+ (0, config_1.getConfig)().LOGGER.info(`Worker cleaned up for property ${propertyId} - no pending jobs`);
109
+ }
110
+ }
111
+ }
112
+ catch (error) {
113
+ (0, config_1.getConfig)().LOGGER.error(`Error during worker cleanup for ${queueKey}:`, error.message);
114
+ }
115
+ }
116
+ /**
117
+ * Close all workers and queues
118
+ */
119
+ static async closeAllWorkersAndQueues(workers, queues) {
120
+ try {
121
+ // Close all workers and queues
122
+ await Promise.all([
123
+ ...Array.from(workers.values()).map((worker) => worker.close()),
124
+ ...Array.from(queues.values()).map((queue) => queue.close()),
125
+ ]);
126
+ workers.clear();
127
+ queues.clear();
128
+ (0, config_1.getConfig)().LOGGER.info("All workers and queues closed successfully");
129
+ }
130
+ catch (error) {
131
+ (0, config_1.getConfig)().LOGGER.error("Error closing workers and queues:", error.message);
132
+ throw error;
133
+ }
134
+ }
135
+ /**
136
+ * Generate queue name for a property
137
+ */
138
+ static generateQueueName(propertyId) {
139
+ return `${propertyId}_copilot`;
140
+ }
141
+ /**
142
+ * Extract property ID from job ID
143
+ */
144
+ static extractPropertyIdFromJobId(jobId) {
145
+ return jobId.split("-")[0];
146
+ }
147
+ /**
148
+ * Generate unique job ID
149
+ */
150
+ static generateJobId(propertyId) {
151
+ return `${propertyId}-${Date.now()}-${Math.random()
152
+ .toString(36)
153
+ .substr(2, 9)}`;
154
+ }
155
+ }
156
+ exports.QueueManager = QueueManager;
@@ -12,14 +12,14 @@ class CronicleService {
12
12
  this.cronicleApiKey = process.env.CRONICLE_API_KEY || "";
13
13
  }
14
14
  async registerJob(payload) {
15
- const { name, apiUrl, method, schedule, cronJobId, target, category } = payload;
15
+ const { name, apiUrl, method, schedule, cronJobId, target, category, timezone, } = payload;
16
16
  try {
17
17
  await axios_1.default.post(`${this.cronicleEndpoint}/create_event/v1`, {
18
18
  id: cronJobId,
19
19
  title: name,
20
20
  category: "general",
21
21
  plugin: "urlplug",
22
- timeZone: "UTC",
22
+ timeZone: timezone || "UTC",
23
23
  enabled: 1,
24
24
  target: target,
25
25
  api_key: this.cronicleApiKey,
@@ -40,6 +40,7 @@ class CronicleService {
40
40
  hours: schedule.hours,
41
41
  minutes: schedule.minutes,
42
42
  },
43
+ timeout: 120,
43
44
  });
44
45
  }
45
46
  catch (error) {
@@ -1,7 +1,7 @@
1
1
  export interface ICronicle {
2
2
  name: string;
3
3
  cronJobId: string;
4
- category?: "heartbeat" | "replenish_codes" | "sync_schedules" | "delete_schedules" | "deliver_codes" | "daily_summary" | "battery_report" | "deactivate_alerts" | "activate_alerts";
4
+ category?: "heartbeat" | "replenish_codes" | "sync_schedules" | "delete_schedules" | "deliver_codes" | "daily_summary" | "battery_report" | "replenish_alerts";
5
5
  apiUrl: string;
6
6
  method: "POST";
7
7
  target: string;
@@ -13,4 +13,5 @@ export interface ICronicle {
13
13
  hours?: number[];
14
14
  minutes?: number[];
15
15
  };
16
+ timezone?: string;
16
17
  }
package/dist/index.d.ts CHANGED
@@ -18,3 +18,4 @@ export * from "./entities/pms";
18
18
  export * from "./audit";
19
19
  export { initialize, getConfig, shutdown } from "./config/config";
20
20
  export * from "./webhookQueue";
21
+ export * from "./copilotQueue";
package/dist/index.js CHANGED
@@ -61,3 +61,5 @@ Object.defineProperty(exports, "getConfig", { enumerable: true, get: function ()
61
61
  Object.defineProperty(exports, "shutdown", { enumerable: true, get: function () { return config_1.shutdown; } });
62
62
  //Export PMS Webhook Queue
63
63
  __exportStar(require("./webhookQueue"), exports);
64
+ //Export Copilot Queue
65
+ __exportStar(require("./copilotQueue"), exports);
@@ -70,7 +70,9 @@ export declare enum IssueType {
70
70
  ACCOUNT_UNAUTHORIZED = "ACCOUNT_UNAUTHORIZED",
71
71
  ACCOUNT_MISSING_DEVICE = "ACCOUNT_MISSING_DEVICE",
72
72
  LOCK_JAMMED = "LOCK_JAMMED",
73
- DEVICE_MALFUNCTION = "DEVICE_MALFUNCTION"
73
+ DEVICE_MALFUNCTION = "DEVICE_MALFUNCTION",
74
+ NO_GUEST_CODES = "NO_GUEST_CODES",
75
+ JUST_ENOUGH_GUEST_CODES = "JUST_ENOUGH_GUEST_CODES"
74
76
  }
75
77
  export interface IssueDocument {
76
78
  id: string;
@@ -76,4 +76,6 @@ var IssueType;
76
76
  IssueType["ACCOUNT_MISSING_DEVICE"] = "ACCOUNT_MISSING_DEVICE";
77
77
  IssueType["LOCK_JAMMED"] = "LOCK_JAMMED";
78
78
  IssueType["DEVICE_MALFUNCTION"] = "DEVICE_MALFUNCTION";
79
+ IssueType["NO_GUEST_CODES"] = "NO_GUEST_CODES";
80
+ IssueType["JUST_ENOUGH_GUEST_CODES"] = "JUST_ENOUGH_GUEST_CODES";
79
81
  })(IssueType || (exports.IssueType = IssueType = {}));
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "dt-common-device",
3
- "version": "9.1.6",
3
+ "version": "9.1.8",
4
4
  "main": "dist/index.js",
5
5
  "types": "dist/index.d.ts",
6
6
  "files": [