mirror of
https://github.com/EvolutionAPI/evolution-api.git
synced 2025-07-14 01:41:24 -06:00
Merge pull request #374 from judsonjuniorr/proxy-improvements
Proxy improvements
This commit is contained in:
commit
9d685da12d
@ -61,6 +61,7 @@
|
|||||||
"express": "^4.18.2",
|
"express": "^4.18.2",
|
||||||
"express-async-errors": "^3.1.1",
|
"express-async-errors": "^3.1.1",
|
||||||
"hbs": "^4.2.0",
|
"hbs": "^4.2.0",
|
||||||
|
"https-proxy-agent": "^7.0.2",
|
||||||
"jimp": "^0.16.13",
|
"jimp": "^0.16.13",
|
||||||
"join": "^3.0.0",
|
"join": "^3.0.0",
|
||||||
"js-yaml": "^4.1.0",
|
"js-yaml": "^4.1.0",
|
||||||
@ -73,7 +74,6 @@
|
|||||||
"node-mime-types": "^1.1.0",
|
"node-mime-types": "^1.1.0",
|
||||||
"node-windows": "^1.0.0-beta.8",
|
"node-windows": "^1.0.0-beta.8",
|
||||||
"pino": "^8.11.0",
|
"pino": "^8.11.0",
|
||||||
"proxy-agent": "^6.3.0",
|
|
||||||
"qrcode": "^1.5.1",
|
"qrcode": "^1.5.1",
|
||||||
"qrcode-terminal": "^0.12.0",
|
"qrcode-terminal": "^0.12.0",
|
||||||
"redis": "^4.6.5",
|
"redis": "^4.6.5",
|
||||||
|
17
src/utils/makeProxyAgent.ts
Normal file
17
src/utils/makeProxyAgent.ts
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
import { HttpsProxyAgent } from 'https-proxy-agent';
|
||||||
|
|
||||||
|
import { wa } from '../whatsapp/types/wa.types';
|
||||||
|
|
||||||
|
export function makeProxyAgent(proxy: wa.Proxy | string) {
|
||||||
|
if (typeof proxy === 'string') {
|
||||||
|
return new HttpsProxyAgent(proxy);
|
||||||
|
}
|
||||||
|
|
||||||
|
const { host, password, port, protocol, username } = proxy;
|
||||||
|
let proxyUrl = `${protocol}://${host}:${port}`;
|
||||||
|
|
||||||
|
if (username && password) {
|
||||||
|
proxyUrl = `${protocol}://${username}:${password}@${host}:${port}`;
|
||||||
|
}
|
||||||
|
return new HttpsProxyAgent(proxyUrl);
|
||||||
|
}
|
@ -1,19 +1,25 @@
|
|||||||
import axios from 'axios';
|
import axios from 'axios';
|
||||||
|
|
||||||
import { Logger } from '../../config/logger.config';
|
import { Logger } from '../../config/logger.config';
|
||||||
import { BadRequestException } from '../../exceptions';
|
import { BadRequestException, NotFoundException } from '../../exceptions';
|
||||||
|
import { makeProxyAgent } from '../../utils/makeProxyAgent';
|
||||||
import { InstanceDto } from '../dto/instance.dto';
|
import { InstanceDto } from '../dto/instance.dto';
|
||||||
import { ProxyDto } from '../dto/proxy.dto';
|
import { ProxyDto } from '../dto/proxy.dto';
|
||||||
|
import { WAMonitoringService } from '../services/monitor.service';
|
||||||
import { ProxyService } from '../services/proxy.service';
|
import { ProxyService } from '../services/proxy.service';
|
||||||
|
|
||||||
const logger = new Logger('ProxyController');
|
const logger = new Logger('ProxyController');
|
||||||
|
|
||||||
export class ProxyController {
|
export class ProxyController {
|
||||||
constructor(private readonly proxyService: ProxyService) {}
|
constructor(private readonly proxyService: ProxyService, private readonly waMonitor: WAMonitoringService) {}
|
||||||
|
|
||||||
public async createProxy(instance: InstanceDto, data: ProxyDto) {
|
public async createProxy(instance: InstanceDto, data: ProxyDto) {
|
||||||
logger.verbose('requested createProxy from ' + instance.instanceName + ' instance');
|
logger.verbose('requested createProxy from ' + instance.instanceName + ' instance');
|
||||||
|
|
||||||
|
if (!this.waMonitor.waInstances[instance.instanceName]) {
|
||||||
|
throw new NotFoundException(`The "${instance.instanceName}" instance does not exist`);
|
||||||
|
}
|
||||||
|
|
||||||
if (!data.enabled) {
|
if (!data.enabled) {
|
||||||
logger.verbose('proxy disabled');
|
logger.verbose('proxy disabled');
|
||||||
data.proxy = null;
|
data.proxy = null;
|
||||||
@ -21,8 +27,7 @@ export class ProxyController {
|
|||||||
|
|
||||||
if (data.proxy) {
|
if (data.proxy) {
|
||||||
logger.verbose('proxy enabled');
|
logger.verbose('proxy enabled');
|
||||||
const { host, port, protocol, username, password } = data.proxy;
|
const testProxy = await this.testProxy(data.proxy);
|
||||||
const testProxy = await this.testProxy(host, port, protocol, username, password);
|
|
||||||
if (!testProxy) {
|
if (!testProxy) {
|
||||||
throw new BadRequestException('Invalid proxy');
|
throw new BadRequestException('Invalid proxy');
|
||||||
}
|
}
|
||||||
@ -33,37 +38,30 @@ export class ProxyController {
|
|||||||
|
|
||||||
public async findProxy(instance: InstanceDto) {
|
public async findProxy(instance: InstanceDto) {
|
||||||
logger.verbose('requested findProxy from ' + instance.instanceName + ' instance');
|
logger.verbose('requested findProxy from ' + instance.instanceName + ' instance');
|
||||||
|
|
||||||
|
if (!this.waMonitor.waInstances[instance.instanceName]) {
|
||||||
|
throw new NotFoundException(`The "${instance.instanceName}" instance does not exist`);
|
||||||
|
}
|
||||||
|
|
||||||
return this.proxyService.find(instance);
|
return this.proxyService.find(instance);
|
||||||
}
|
}
|
||||||
|
|
||||||
private async testProxy(host: string, port: string, protocol: string, username?: string, password?: string) {
|
private async testProxy(proxy: ProxyDto['proxy']) {
|
||||||
logger.verbose('requested testProxy');
|
logger.verbose('requested testProxy');
|
||||||
try {
|
try {
|
||||||
let proxyConfig: any = {
|
const serverIp = await axios.get('https://icanhazip.com/');
|
||||||
host: host,
|
const response = await axios.get('https://icanhazip.com/', {
|
||||||
port: parseInt(port),
|
httpsAgent: makeProxyAgent(proxy),
|
||||||
protocol: protocol,
|
|
||||||
};
|
|
||||||
|
|
||||||
if (username && password) {
|
|
||||||
proxyConfig = {
|
|
||||||
...proxyConfig,
|
|
||||||
auth: {
|
|
||||||
username: username,
|
|
||||||
password: password,
|
|
||||||
},
|
|
||||||
};
|
|
||||||
}
|
|
||||||
const serverIp = await axios.get('http://meuip.com/api/meuip.php');
|
|
||||||
|
|
||||||
const response = await axios.get('http://meuip.com/api/meuip.php', {
|
|
||||||
proxy: proxyConfig,
|
|
||||||
});
|
});
|
||||||
|
|
||||||
logger.verbose('testProxy response: ' + response.data);
|
logger.verbose('testProxy response: ' + response.data);
|
||||||
return response.data !== serverIp.data;
|
return response.data !== serverIp.data;
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
logger.error('testProxy error: ' + error);
|
let errorMessage = error;
|
||||||
|
if (axios.isAxiosError(error) && error.response.data) {
|
||||||
|
errorMessage = error.response.data;
|
||||||
|
}
|
||||||
|
logger.error('testProxy error: ' + errorMessage);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -45,7 +45,6 @@ import { getMIMEType } from 'node-mime-types';
|
|||||||
import { release } from 'os';
|
import { release } from 'os';
|
||||||
import { join } from 'path';
|
import { join } from 'path';
|
||||||
import P from 'pino';
|
import P from 'pino';
|
||||||
import { ProxyAgent } from 'proxy-agent';
|
|
||||||
import qrcode, { QRCodeToDataURLOptions } from 'qrcode';
|
import qrcode, { QRCodeToDataURLOptions } from 'qrcode';
|
||||||
import qrcodeTerminal from 'qrcode-terminal';
|
import qrcodeTerminal from 'qrcode-terminal';
|
||||||
import sharp from 'sharp';
|
import sharp from 'sharp';
|
||||||
@ -73,6 +72,7 @@ import { dbserver } from '../../libs/db.connect';
|
|||||||
import { RedisCache } from '../../libs/redis.client';
|
import { RedisCache } from '../../libs/redis.client';
|
||||||
import { getIO } from '../../libs/socket.server';
|
import { getIO } from '../../libs/socket.server';
|
||||||
import { getSQS, removeQueues as removeQueuesSQS } from '../../libs/sqs.server';
|
import { getSQS, removeQueues as removeQueuesSQS } from '../../libs/sqs.server';
|
||||||
|
import { makeProxyAgent } from '../../utils/makeProxyAgent';
|
||||||
import { useMultiFileAuthStateDb } from '../../utils/use-multi-file-auth-state-db';
|
import { useMultiFileAuthStateDb } from '../../utils/use-multi-file-auth-state-db';
|
||||||
import { useMultiFileAuthStateRedisDb } from '../../utils/use-multi-file-auth-state-redis-db';
|
import { useMultiFileAuthStateRedisDb } from '../../utils/use-multi-file-auth-state-redis-db';
|
||||||
import {
|
import {
|
||||||
@ -1385,24 +1385,21 @@ export class WAStartupService {
|
|||||||
this.logger.info('Proxy enabled: ' + this.localProxy.proxy);
|
this.logger.info('Proxy enabled: ' + this.localProxy.proxy);
|
||||||
|
|
||||||
if (this.localProxy.proxy.host.includes('proxyscrape')) {
|
if (this.localProxy.proxy.host.includes('proxyscrape')) {
|
||||||
const response = await axios.get(this.localProxy.proxy.host);
|
try {
|
||||||
const text = response.data;
|
const response = await axios.get(this.localProxy.proxy.host);
|
||||||
const proxyUrls = text.split('\r\n');
|
const text = response.data;
|
||||||
const rand = Math.floor(Math.random() * Math.floor(proxyUrls.length));
|
const proxyUrls = text.split('\r\n');
|
||||||
const proxyUrl = 'http://' + proxyUrls[rand];
|
const rand = Math.floor(Math.random() * Math.floor(proxyUrls.length));
|
||||||
options = {
|
const proxyUrl = 'http://' + proxyUrls[rand];
|
||||||
agent: new ProxyAgent(proxyUrl as any),
|
options = {
|
||||||
};
|
agent: makeProxyAgent(proxyUrl),
|
||||||
} else {
|
};
|
||||||
let proxyUri =
|
} catch (error) {
|
||||||
this.localProxy.proxy.protocol + '://' + this.localProxy.proxy.host + ':' + this.localProxy.proxy.port;
|
this.localProxy.enabled = false;
|
||||||
|
|
||||||
if (this.localProxy.proxy.username && this.localProxy.proxy.password) {
|
|
||||||
proxyUri = `${this.localProxy.proxy.username}:${this.localProxy.proxy.password}@${proxyUri}`;
|
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
options = {
|
options = {
|
||||||
agent: new ProxyAgent(proxyUri as any),
|
agent: makeProxyAgent(this.localProxy.proxy),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1489,8 +1486,8 @@ export class WAStartupService {
|
|||||||
if (this.localProxy.enabled) {
|
if (this.localProxy.enabled) {
|
||||||
this.logger.verbose('Proxy enabled');
|
this.logger.verbose('Proxy enabled');
|
||||||
options = {
|
options = {
|
||||||
agent: new ProxyAgent(this.localProxy.proxy as any),
|
agent: makeProxyAgent(this.localProxy.proxy),
|
||||||
fetchAgent: new ProxyAgent(this.localProxy.proxy as any),
|
fetchAgent: makeProxyAgent(this.localProxy.proxy),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -119,7 +119,7 @@ export const websocketController = new WebsocketController(websocketService);
|
|||||||
|
|
||||||
const proxyService = new ProxyService(waMonitor);
|
const proxyService = new ProxyService(waMonitor);
|
||||||
|
|
||||||
export const proxyController = new ProxyController(proxyService);
|
export const proxyController = new ProxyController(proxyService, waMonitor);
|
||||||
|
|
||||||
const chamaaiService = new ChamaaiService(waMonitor, configService);
|
const chamaaiService = new ChamaaiService(waMonitor, configService);
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user