"use strict"; const { Client } = require("../Client"); const { on, register } = require("../WebSocket"); class APNumber { static busyNumbers = new Map(); static lock(client) { let c = 24; while (true) { if (!APNumber.busyNumbers.has(c)) { APNumber.busyNumbers.set(c, client); process.send({ type: 'AP_NUMBER/LOCK', uuid: client.id, value: c }); return c; } c++; } } static release(num) { process.send({ type: 'AP_NUMBER/RELEASE', uuid: APNumber.busyNumbers.get(num).id, value: num }); APNumber.busyNumbers.delete(num); } static whois(num) { return APNumber.busyNumbers.get(num)?.id; } } class APShortCode { static busyCodes = new Map(); static lock(client) { let firstLetter = new ShortCodeLetter(); let secondLetter = new ShortCodeLetter(); let thirdLetter = new ShortCodeLetter(); while (1) { let code = [firstLetter.code, secondLetter.code, thirdLetter.code].join(''); if (!APShortCode.busyCodes.has(code)) { APShortCode.busyCodes.set(code, client); process.send({ type: 'AP_SHORTCODE/LOCK', uuid: APShortCode.busyCodes.get(code).id, value: code }); return code; } if (!thirdLetter.end()) { thirdLetter.next(); } else { thirdLetter.reset(); if (!secondLetter.end()) { secondLetter.next(); } else { secondLetter.reset(); if (!firstLetter.end()) { firstLetter.next(); } else { break; } } } } } static release(code) { if (APShortCode.busyCodes.has(code)) { process.send({ type: 'AP_SHORTCODE/RELEASE', uuid: APShortCode.busyCodes.get(code).id, value: code }); APShortCode.busyCodes.delete(code); } } static whois(num) { return APShortCode.busyCodes.get(num)?.id; } } class ShortCodeLetter { chars = 'ABCDEFGHIKLMNOPRSTVXYZ'.split(''); now = 0; code = 'A'; next() { this.now++; this.code = this.chars.at(this.now); return this.code; } reset() { this.now = 0; this.code = 'A'; } end() { return !this.chars.at(this.now + 1); } } class APIPAddress { static busyIP = new Map(); static lock(client) { let A = 10, B = 0, C = 0, D = 1; while (1) { let code = [A, B, C, D].join('.'); if (!APIPAddress.busyIP.has(code)) { APIPAddress.busyIP.set(code, client); process.send({ type: 'AP_IPADDRESS/LOCK', uuid: APIPAddress.busyIP.get(code).id, value: code }); return code; } if (D != 255) { D++; continue; } D = 0; if (C != 255) { C++; continue; } C = 0; if (B != 255) { B++; continue; } B = 0; if (A != 255) { A++; continue; } return; } } static release(code) { if (APIPAddress.busyIP.has(code)) { process.send({ type: 'AP_IPADDRESS/RELEASE', uuid: APIPAddress.busyIP.get(code).id, value: code }); APIPAddress.busyIP.delete(code); } } static whois(num) { return APIPAddress.busyIP.get(num)?.id; } } exports.APNumber = APNumber; exports.APShortCode = APShortCode; exports.APIPAddress = APIPAddress; register('alloc/APIPAddress', (client, msg) => { if (client.APIPAddress) { return { status: 'success', ip: client.APIPAddress }; } let value = APIPAddress.lock(client); client.APIPAddress = value; return { status: 'success', ip: value }; }); register('alloc/APNumber', (client, msg) => { if (client.APNumber) { return { status: 'success', number: client.APNumber }; } let value = APNumber.lock(client); client.APNumber = value; return { status: 'success', number: value }; }); register('alloc/APShortCode', (client, msg) => { if (client.APShortCode) { return { status: 'success', code: client.APShortCode }; } let value = APShortCode.lock(client); client.APShortCode = value; return { status: 'success', code: value }; }); register('realloc/APIPAddress', (client, msg) => { if (client.APIPAddress == 0) { return { status: 'fail' }; } APIPAddress.release(client.APIPAddress); let value = APIPAddress.lock(client); return { status: 'success', ip: value }; }); register('realloc/APNumber', (client, msg) => { if (client.APNumber == 0) { return { status: 'fail' }; } APNumber.release(client.APNumber); let value = APNumber.lock(client); return { status: 'success', number: value }; }); register('realloc/APShortCode', (client, msg) => { if (client.APShortCode == 0) { return { status: 'fail' }; } APShortCode.release(client.APShortCode); let value = APShortCode.lock(client); return { status: 'success', code: value }; }); register('release/APIPAddress', (client, msg) => { APIPAddress.release(client.APIPAddress); client.APIPAddress = undefined; return { status: 'success' }; }); register('release/APNumber', (client, msg) => { APNumber.release(client.APNumber); client.APNumber = undefined; return { status: 'success' }; }); register('release/APShortCode', (client, msg) => { APShortCode.release(client.APShortCode); client.APShortCode = undefined; return { status: 'success' }; }); register('whois/APIPAddress', (client, msg) => { let socketId = APIPAddress.whois(msg.whois); if (socketId) { return { status: 'success', socket: socketId }; } return { status: 'fail' }; }); register('whois/APNumber', (client, msg) => { let socketId = APNumber.whois(msg.whois); if (socketId) { return { status: 'success', socket: socketId }; } return { status: 'fail' }; }); register('whois/APShortCode', (client, msg) => { let socketId = APShortCode.whois(msg.whois); if (socketId) { return { status: 'success', socket: socketId }; } return { status: 'fail' }; }); on('disconnect', (client) => { if (client.APIPAddress != 0) { APIPAddress.release(client.APIPAddress); } if (client.APNumber != 0) { APNumber.release(client.APNumber); } if (client.APShortCode != 0) { APShortCode.release(client.APShortCode); } });