'use strict'; const Boom = require('@hapi/boom'); const Joi = require('joi'); const Rfr = require('rfr'); const AMI = Rfr('/server/ami'); const ComSrv = Rfr('/server/comsrv'); const originateCall = (from, to) => { return new Promise((resolve, reject) => { ComSrv.debug('AMI originate: ' + from + ' -> ' + to + ' with context \'' + process.env.ORIGINATE_CONTEXT + '\''); AMI.action({ 'action': 'originate', 'priority': 1, 'timeout': process.env.ORIGINATE_TIMEOUT * 1000, 'channel': process.env.ORIGINATE_TECHNOLOGY + '/' + from, 'context': process.env.ORIGINATE_CONTEXT, 'callerid': from, 'exten': to }, (err, res) => { if (err) { ComSrv.debug('AMI originate failed' + (err.message ? (': ' + err.message) : '')); return reject({ ok: false, message: (err.message || "Unknown error") }); } else { ComSrv.debug('AMI originate successful' + (res.message ? (': ' + res.message) : '')); return resolve({ ok: true, id: (res.actionid || 0), message: (res.message || "") }); } }); }); }; const originateHandler = async (request, h) => { if (!process.env.ORIGINATE_ENABLE || !process.env.AMI_ENABLE) { return Boom.serverUnavailable('This API has been disabled'); } try { return { statusCode: 200, ...(await originateCall(request.query.from, request.query.to)) }; } catch (e) { if (e.ok === false) { return h.response({statusCode: 200, ok: false, error: e.message}).code(200); } else { console.error('API error: ' + e); return Boom.badImplementation('AMI passthrough failed'); } } }; module.exports = { routes: [{ method: 'GET', path: '/api/originate', handler: originateHandler, options: { validate: { query: Joi.object({ from: Joi.string().min(1).max(100).trim().pattern(/^[0-9]+$/).required(), to: Joi.string().min(1).max(100).trim().pattern(/^[0-9]+$/).required() }) } } }], config: Joi.object({ ORIGINATE_ENABLE: Joi.boolean().optional().default(true), ORIGINATE_CONTEXT: Joi.string().min(1).required(), ORIGINATE_TIMEOUT: Joi.number().positive().min(1).max(3600).optional().default(60), ORIGINATE_TECHNOLOGY: Joi.string().optional().default('PJSIP') }) };