Skip to content

Commit 7a7e728

Browse files
Merge pull request #95 from w3nder/develop
Melhorando o desempenho no carregamento da instância.
2 parents 23534da + cdbe839 commit 7a7e728

1 file changed

Lines changed: 105 additions & 111 deletions

File tree

src/whatsapp/services/monitor.service.ts

Lines changed: 105 additions & 111 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@ import { join } from 'path';
77
import { Auth, ConfigService, Database, DelInstance, HttpServer, Redis } from '../../config/env.config';
88
import { Logger } from '../../config/logger.config';
99
import { INSTANCE_DIR, STORE_DIR } from '../../config/path.config';
10-
import { NotFoundException } from '../../exceptions';
1110
import { dbserver } from '../../libs/db.connect';
1211
import { RedisCache } from '../../libs/redis.client';
1312
import {
@@ -76,77 +75,57 @@ export class WAMonitoringService {
7675

7776
public async instanceInfo(instanceName?: string) {
7877
this.logger.verbose('get instance info');
79-
if (instanceName && !this.waInstances[instanceName]) {
80-
throw new NotFoundException(`Instance "${instanceName}" not found`);
81-
}
82-
83-
const instances: any[] = [];
8478

85-
for await (const [key, value] of Object.entries(this.waInstances)) {
86-
if (value) {
87-
this.logger.verbose('get instance info: ' + key);
88-
let chatwoot: any;
79+
const urlServer = this.configService.get<HttpServer>('SERVER').URL;
8980

90-
const urlServer = this.configService.get<HttpServer>('SERVER').URL;
81+
const instances: any[] = await Promise.all(
82+
Object.entries(this.waInstances).map(async ([key, value]) => {
83+
const status = value?.connectionStatus?.state || 'unknown';
9184

92-
const findChatwoot = await this.waInstances[key].findChatwoot();
93-
94-
if (findChatwoot && findChatwoot.enabled) {
95-
chatwoot = {
96-
...findChatwoot,
97-
webhook_url: `${urlServer}/chatwoot/webhook/${encodeURIComponent(key)}`,
98-
};
85+
if (status === 'unknown') {
86+
return null;
9987
}
10088

101-
if (value.connectionStatus.state === 'open') {
89+
if (status === 'open') {
10290
this.logger.verbose('instance: ' + key + ' - connectionStatus: open');
91+
}
10392

104-
const instanceData = {
105-
instance: {
106-
instanceName: key,
107-
owner: value.wuid,
108-
profileName: (await value.getProfileName()) || 'not loaded',
109-
profilePictureUrl: value.profilePictureUrl,
110-
profileStatus: (await value.getProfileStatus()) || '',
111-
status: value.connectionStatus.state,
112-
},
113-
};
114-
115-
if (this.configService.get<Auth>('AUTHENTICATION').EXPOSE_IN_FETCH_INSTANCES) {
116-
instanceData.instance['serverUrl'] = this.configService.get<HttpServer>('SERVER').URL;
117-
118-
instanceData.instance['apikey'] = (await this.repository.auth.find(key))?.apikey;
119-
120-
instanceData.instance['chatwoot'] = chatwoot;
93+
const instanceData: any = {
94+
instance: {
95+
instanceName: key,
96+
owner: value.wuid,
97+
profileName: (await value.getProfileName()) || 'not loaded',
98+
profilePictureUrl: value.profilePictureUrl,
99+
profileStatus: (await value.getProfileStatus()) || '',
100+
status: status,
101+
},
102+
};
103+
104+
if (this.configService.get<Auth>('AUTHENTICATION').EXPOSE_IN_FETCH_INSTANCES) {
105+
instanceData.instance.serverUrl = urlServer;
106+
instanceData.instance.apikey = (await this.repository.auth.find(key))?.apikey;
107+
108+
const findChatwoot = await this.waInstances[key].findChatwoot();
109+
if (findChatwoot && findChatwoot.enabled) {
110+
instanceData.instance.chatwoot = {
111+
...findChatwoot,
112+
webhook_url: `${urlServer}/chatwoot/webhook/${encodeURIComponent(key)}`,
113+
};
121114
}
115+
}
122116

123-
instances.push(instanceData);
124-
} else {
125-
this.logger.verbose('instance: ' + key + ' - connectionStatus: ' + value.connectionStatus.state);
126-
127-
const instanceData = {
128-
instance: {
129-
instanceName: key,
130-
status: value.connectionStatus.state,
131-
},
132-
};
133-
134-
if (this.configService.get<Auth>('AUTHENTICATION').EXPOSE_IN_FETCH_INSTANCES) {
135-
instanceData.instance['serverUrl'] = this.configService.get<HttpServer>('SERVER').URL;
136-
137-
instanceData.instance['apikey'] = (await this.repository.auth.find(key))?.apikey;
117+
return instanceData;
118+
}),
119+
).then((results) => results.filter((instance) => instance !== null));
138120

139-
instanceData.instance['chatwoot'] = chatwoot;
140-
}
121+
this.logger.verbose('return instance info: ' + instances.length);
141122

142-
instances.push(instanceData);
143-
}
144-
}
123+
if (instanceName) {
124+
const instance = instances.find((i) => i.instance.instanceName === instanceName);
125+
return instance || [];
145126
}
146127

147-
this.logger.verbose('return instance info: ' + instances.length);
148-
149-
return instances.find((i) => i.instance.instanceName === instanceName) ?? instances;
128+
return instances;
150129
}
151130

152131
private delInstanceFiles() {
@@ -199,7 +178,6 @@ export class WAMonitoringService {
199178
this.logger.verbose('cleaning up instance in redis: ' + instanceName);
200179
this.cache.reference = instanceName;
201180
await this.cache.delAll();
202-
this.cache.disconnect();
203181
return;
204182
}
205183

@@ -245,67 +223,83 @@ export class WAMonitoringService {
245223
}
246224

247225
public async loadInstance() {
248-
this.logger.verbose('load instances');
249-
const set = async (name: string) => {
250-
const instance = new WAStartupService(this.configService, this.eventEmitter, this.repository, this.cache);
251-
instance.instanceName = name;
252-
this.logger.verbose('instance loaded: ' + name);
253-
254-
await instance.connectToWhatsapp();
255-
this.logger.verbose('connectToWhatsapp: ' + name);
256-
257-
this.waInstances[name] = instance;
258-
};
226+
this.logger.verbose('Loading instances');
259227

260228
try {
261229
if (this.redis.ENABLED) {
262-
this.logger.verbose('redis enabled');
263-
await this.cache.connect(this.redis as Redis);
264-
const keys = await this.cache.instanceKeys();
265-
if (keys?.length > 0) {
266-
this.logger.verbose('reading instance keys and setting instances');
267-
keys.forEach(async (k) => await set(k.split(':')[1]));
268-
} else {
269-
this.logger.verbose('no instance keys found');
270-
}
271-
this.cache.disconnect();
272-
return;
230+
await this.loadInstancesFromRedis();
231+
} else if (this.db.ENABLED && this.db.SAVE_DATA.INSTANCE) {
232+
await this.loadInstancesFromDatabase();
233+
} else {
234+
await this.loadInstancesFromFiles();
273235
}
236+
} catch (error) {
237+
this.logger.error(error);
238+
}
239+
}
274240

275-
if (this.db.ENABLED && this.db.SAVE_DATA.INSTANCE) {
276-
this.logger.verbose('database enabled');
277-
await this.repository.dbServer.connect();
278-
const collections: any[] = await this.dbInstance.collections();
279-
if (collections.length > 0) {
280-
this.logger.verbose('reading collections and setting instances');
281-
collections.forEach(async (coll) => await set(coll.namespace.replace(/^[\w-]+\./, '')));
282-
} else {
283-
this.logger.verbose('no collections found');
284-
}
285-
return;
241+
private async setInstance(name: string) {
242+
const instance = new WAStartupService(this.configService, this.eventEmitter, this.repository, this.cache);
243+
instance.instanceName = name;
244+
this.logger.verbose('Instance loaded: ' + name);
245+
246+
await instance.connectToWhatsapp();
247+
this.logger.verbose('connectToWhatsapp: ' + name);
248+
249+
this.waInstances[name] = instance;
250+
}
251+
252+
private async loadInstancesFromRedis() {
253+
this.logger.verbose('Redis enabled');
254+
await this.cache.connect(this.redis as Redis);
255+
const keys = await this.cache.instanceKeys();
256+
257+
if (keys?.length > 0) {
258+
this.logger.verbose('Reading instance keys and setting instances');
259+
await Promise.all(keys.map((k) => this.setInstance(k.split(':')[1])));
260+
} else {
261+
this.logger.verbose('No instance keys found');
262+
}
263+
}
264+
265+
private async loadInstancesFromDatabase() {
266+
this.logger.verbose('Database enabled');
267+
await this.repository.dbServer.connect();
268+
const collections: any[] = await this.dbInstance.collections();
269+
270+
if (collections.length > 0) {
271+
this.logger.verbose('Reading collections and setting instances');
272+
await Promise.all(collections.map((coll) => this.setInstance(coll.namespace.replace(/^[\w-]+\./, ''))));
273+
} else {
274+
this.logger.verbose('No collections found');
275+
}
276+
}
277+
278+
private async loadInstancesFromFiles() {
279+
this.logger.verbose('Store in files enabled');
280+
const dir = opendirSync(INSTANCE_DIR, { encoding: 'utf-8' });
281+
const instanceDirs = [];
282+
283+
for await (const dirent of dir) {
284+
if (dirent.isDirectory()) {
285+
instanceDirs.push(dirent.name);
286+
} else {
287+
this.logger.verbose('No instance files found');
286288
}
289+
}
287290

288-
this.logger.verbose('store in files enabled');
289-
const dir = opendirSync(INSTANCE_DIR, { encoding: 'utf-8' });
290-
for await (const dirent of dir) {
291-
if (dirent.isDirectory()) {
292-
this.logger.verbose('reading instance files and setting instances');
293-
const files = readdirSync(join(INSTANCE_DIR, dirent.name), {
294-
encoding: 'utf-8',
295-
});
296-
if (files.length === 0) {
297-
rmSync(join(INSTANCE_DIR, dirent.name), { recursive: true, force: true });
298-
break;
299-
}
291+
await Promise.all(
292+
instanceDirs.map(async (instanceName) => {
293+
this.logger.verbose('Reading instance files and setting instances: ' + instanceName);
294+
const files = readdirSync(join(INSTANCE_DIR, instanceName), { encoding: 'utf-8' });
300295

301-
await set(dirent.name);
296+
if (files.length === 0) {
297+
rmSync(join(INSTANCE_DIR, instanceName), { recursive: true, force: true });
302298
} else {
303-
this.logger.verbose('no instance files found');
299+
await this.setInstance(instanceName);
304300
}
305-
}
306-
} catch (error) {
307-
this.logger.error(error);
308-
}
301+
}),
302+
);
309303
}
310304

311305
private removeInstance() {

0 commit comments

Comments
 (0)