mirror of
https://github.com/jambonz/jambonz-feature-server.git
synced 2025-12-20 16:50:39 +00:00
remove config in favor of env vars, other major changes
This commit is contained in:
@@ -1,10 +0,0 @@
|
||||
const toBase64 = (str) => Buffer.from(str || '', 'utf8').toString('base64');
|
||||
|
||||
module.exports = (auth) => {
|
||||
if (!auth || !auth.username ||
|
||||
typeof auth.username !== 'string' ||
|
||||
(auth.password && typeof auth.password !== 'string')) return {};
|
||||
const creds = `${auth.username}:${auth.password || ''}`;
|
||||
const header = `Basic ${toBase64(creds)}`;
|
||||
return {Authorization: header};
|
||||
};
|
||||
@@ -1,26 +1,57 @@
|
||||
const config = require('config');
|
||||
const ip = require('ip');
|
||||
const localIp = ip.address();
|
||||
const PORT = process.env.HTTP_PORT || config.get('defaultHttpPort');
|
||||
const PORT = process.env.HTTP_PORT || 3000;
|
||||
|
||||
function installSrfLocals(srf, logger) {
|
||||
if (srf.locals.dbHelpers) return;
|
||||
|
||||
const freeswitch = process.env.JAMBONES_FREESWITCH
|
||||
.split(',')
|
||||
.map((fs) => {
|
||||
const arr = /^(.*):(.*):(.*)/.exec(fs);
|
||||
if (arr) return {address: arr[1], port: arr[2], secret: arr[3]};
|
||||
});
|
||||
logger.info({freeswitch}, 'freeswitch inventory');
|
||||
|
||||
const sbcs = process.env.JAMBONES_SBCS
|
||||
.split(',')
|
||||
.map((sbc) => sbc.trim());
|
||||
logger.info({sbcs}, 'SBC inventory');
|
||||
|
||||
const drachtio = process.env.JAMBONES_FEATURE_SERVERS
|
||||
.split(',')
|
||||
.map((fs) => {
|
||||
const arr = /^(.*):(.*):(.*)/.exec(fs);
|
||||
if (arr) return {host: arr[1], port: arr[2], secret: arr[3]};
|
||||
});
|
||||
logger.info({drachtio}, 'drachtio feature server inventory');
|
||||
|
||||
const {
|
||||
lookupAppByPhoneNumber,
|
||||
lookupApplicationBySid
|
||||
} = require('jambonz-db-helpers')(config.get('mysql'), logger);
|
||||
lookupAppBySid,
|
||||
lookupAppByRealm
|
||||
} = require('jambonz-db-helpers')({
|
||||
host: process.env.JAMBONES_MYSQL_HOST,
|
||||
user: process.env.JAMBONES_MYSQL_USER,
|
||||
password: process.env.JAMBONES_MYSQL_PASSWORD,
|
||||
database: process.env.JAMBONES_MYSQL_DATABASE,
|
||||
connectionLimit: process.env.JAMBONES_MYSQL_CONNECTION_LIMIT || 10
|
||||
}, logger);
|
||||
const {
|
||||
updateCallStatus,
|
||||
retrieveCall,
|
||||
listCalls,
|
||||
deleteCall
|
||||
} = require('jambonz-realtimedb-helpers')(config.get('redis'), logger);
|
||||
} = require('jambonz-realtimedb-helpers')({
|
||||
host: process.env.JAMBONES_REDIS_HOST,
|
||||
port: process.env.JAMBONES_REDIS_PORT || 6379
|
||||
}, logger);
|
||||
|
||||
Object.assign(srf.locals, {
|
||||
dbHelpers: {
|
||||
lookupAppByPhoneNumber,
|
||||
lookupApplicationBySid,
|
||||
lookupAppBySid,
|
||||
lookupAppByRealm,
|
||||
updateCallStatus,
|
||||
retrieveCall,
|
||||
listCalls,
|
||||
@@ -28,7 +59,10 @@ function installSrfLocals(srf, logger) {
|
||||
},
|
||||
parentLogger: logger,
|
||||
ipv4: localIp,
|
||||
serviceUrl: `http://${localIp}:${PORT}`
|
||||
serviceUrl: `http://${localIp}:${PORT}`,
|
||||
freeswitch: freeswitch[0],
|
||||
sbcs,
|
||||
drachtio
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
@@ -233,7 +233,7 @@ class SingleDialer extends Emitter {
|
||||
this.callInfo.updateCallStatus(callStatus, sipStatus);
|
||||
if (typeof duration === 'number') this.callInfo.duration = duration;
|
||||
try {
|
||||
this.notifyHook(this.application.call_status_hook);
|
||||
this.requestor.request(this.application.call_status_hook, this.callInfo.toJSON());
|
||||
} catch (err) {
|
||||
this.logger.info(err, `SingleDialer:_notifyCallStatusChange error sending ${callStatus} ${sipStatus}`);
|
||||
}
|
||||
|
||||
@@ -1,8 +1,16 @@
|
||||
const bent = require('bent');
|
||||
const parseUrl = require('parse-url');
|
||||
const basicAuth = require('./basic-auth');
|
||||
const assert = require('assert');
|
||||
|
||||
const toBase64 = (str) => Buffer.from(str || '', 'utf8').toString('base64');
|
||||
|
||||
function basicAuth(username, password) {
|
||||
if (!username || !password) return {};
|
||||
const creds = `${username}:${password || ''}`;
|
||||
const header = `Basic ${toBase64(creds)}`;
|
||||
return {Authorization: header};
|
||||
}
|
||||
|
||||
function isRelativeUrl(u) {
|
||||
return typeof u === 'string' && u.startsWith('/');
|
||||
}
|
||||
@@ -14,25 +22,22 @@ function isAbsoluteUrl(u) {
|
||||
|
||||
class Requestor {
|
||||
constructor(logger, hook) {
|
||||
assert(typeof hook === 'object');
|
||||
|
||||
this.logger = logger;
|
||||
this.url = hook.url;
|
||||
this.method = hook.method || 'POST';
|
||||
this.authHeader = basicAuth(hook.auth);
|
||||
this.authHeader = basicAuth(hook.username, hook.password);
|
||||
|
||||
const u = parseUrl(this.url);
|
||||
const myPort = u.port ? `:${u.port}` : '';
|
||||
const baseUrl = `${u.protocol}://${u.resource}${myPort}`;
|
||||
|
||||
this.get = bent(baseUrl, 'GET', 'json', 200);
|
||||
this.post = bent(baseUrl, 'POST', 'json', 200);
|
||||
this.get = bent(baseUrl, 'GET', 'buffer', 200);
|
||||
this.post = bent(baseUrl, 'POST', 'buffer', 200);
|
||||
|
||||
assert(isAbsoluteUrl(this.url));
|
||||
assert(['GET', 'POST'].includes(this.method));
|
||||
assert(!this.auth || typeof auth == 'object');
|
||||
}
|
||||
|
||||
get hasAuth() {
|
||||
return 'Authorization' in this.authHeader;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -42,23 +47,36 @@ class Requestor {
|
||||
* @param {object|string} hook - may be a absolute or relative url, or an object
|
||||
* @param {string} [hook.url] - an absolute or relative url
|
||||
* @param {string} [hook.method] - 'GET' or 'POST'
|
||||
* @param {string} [hook.username] - if basic auth is protecting the endpoint
|
||||
* @param {string} [hook.password] - if basic auth is protecting the endpoint
|
||||
* @param {object} [params] - request parameters
|
||||
*/
|
||||
async request(hook, params) {
|
||||
params = params || null;
|
||||
if (isRelativeUrl(hook)) {
|
||||
this.logger.debug({params}, `Requestor:request relative url ${hook}`);
|
||||
return await this.post(hook, params, this.authHeader);
|
||||
}
|
||||
const url = hook.url;
|
||||
const url = hook.url || hook;
|
||||
const method = hook.method || 'POST';
|
||||
const authHeader = isRelativeUrl(url) ? this.authHeader : basicAuth(hook.auth);
|
||||
const {username, password} = typeof hook === 'object' ? hook : {};
|
||||
|
||||
assert(url);
|
||||
assert(['GET', 'POST'].includes(method));
|
||||
return await this[method.toLowerCase()](url, params, authHeader);
|
||||
assert.ok(url, 'Requestor:request url was not provided');
|
||||
assert.ok, (['GET', 'POST'].includes(method), `Requestor:request method must be 'GET' or 'POST' not ${method}`);
|
||||
|
||||
|
||||
this.logger.debug({hook}, `Requestor:request ${method} ${url}`);
|
||||
const buf = isRelativeUrl(url) ?
|
||||
await this.post(url, params, this.authHeader) :
|
||||
await bent(method, 'buffer', 200)(url, params, basicAuth(username, password));
|
||||
//this.logger.debug({body: }, `Requestor:request ${method} ${url} succeeded`);
|
||||
|
||||
if (buf && buf.toString().length > 0) {
|
||||
try {
|
||||
const json = JSON.parse(buf.toString());
|
||||
return json;
|
||||
}
|
||||
catch (err) {
|
||||
this.logger.debug({err, url, method}, `Requestor:request returned non-JSON content: '${buf.toString()}'`);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
module.exports = Requestor;
|
||||
|
||||
Reference in New Issue
Block a user