Portions created by the Initial Developer are Copyright (C) 2024-2026
the Initial Developer. All Rights Reserved.
*/
//includes files
require_once dirname(__DIR__, 2) . "/resources/require.php";
require_once "resources/check_auth.php";
//check permissions
if (!(permission_exists('fifo_add') || permission_exists('fifo_edit'))) {
echo "access denied";
exit;
}
//add multi-lingual support
$language = new text;
$text = $language->get();
//set the defaults
$fifo_strategy = '';
$fifo_exit_key = '';
$fifo_exit_action = '';
//add the settings object
$settings = new settings(["domain_uuid" => $_SESSION['domain_uuid'], "user_uuid" => $_SESSION['user_uuid']]);
//setup the event socket connection
$event_socket = event_socket::create();
//set from session variables
$button_icon_back = $settings->get('theme', 'button_icon_back', '');
$button_icon_copy = $settings->get('theme', 'button_icon_copy', '');
$button_icon_delete = $settings->get('theme', 'button_icon_delete', '');
$button_icon_save = $settings->get('theme', 'button_icon_save', '');
$input_toggle_style = $settings->get('theme', 'input_toggle_style', 'switch round');
// Set variables from http GET parameters
$page = is_numeric($_GET['page'] ?? '') ? $_GET['page'] : 0;
$order_by = preg_replace('#[^a-zA-Z0-9_\-]#', '', ($_GET['order_by'] ?? 'fifo_name'));
$order = ($_GET['order'] ?? '') === 'desc' ? 'desc' : 'asc';
$search = $_GET['search'] ?? '';
$show = $_GET['show'] ?? '';
// Build the query string
$param = [];
if (!empty($page)) {
$param['page'] = $page;
}
if (!empty($_GET['order_by'])) {
$param['order_by'] = $order_by;
}
if (!empty($_GET['order'])) {
$param['order'] = $order;
}
if (!empty($search)) {
$param['search'] = $search;
}
if (!empty($show) && $show == 'all' && permission_exists('fifo_all')) {
$param['show'] = $show;
}
$query_string = http_build_query($param);
//action add or update
if (!empty($_REQUEST["id"]) && is_uuid($_REQUEST["id"])) {
$action = "update";
$fifo_uuid = $_REQUEST["id"];
$id = $_REQUEST["id"];
}
else {
$action = "add";
}
//get http post variables and set them to php variables
if (!empty($_POST)) {
$dialplan_uuid = $_POST["dialplan_uuid"];
$fifo_name = $_POST["fifo_name"];
$fifo_extension = $_POST["fifo_extension"];
$fifo_agent_status = $_POST["fifo_agent_status"];
$fifo_agent_queue = $_POST["fifo_agent_queue"];
$fifo_strategy = $_POST["fifo_strategy"];
$fifo_members = $_POST["fifo_members"];
$fifo_timeout_seconds = $_POST["fifo_timeout_seconds"];
$fifo_exit_key = $_POST["fifo_exit_key"];
$fifo_exit_action = $_POST["fifo_exit_action"];
$fifo_music = $_POST["fifo_music"];
$domain_uuid = $_POST["domain_uuid"];
$fifo_order = $_POST["fifo_order"];
$fifo_enabled = $_POST["fifo_enabled"];
$fifo_description = $_POST["fifo_description"];
}
//process the data and save it to the database
if (!empty($_POST) && empty($_POST["persistformvar"])) {
//validate the token
$token = new token;
if (!$token->validate($_SERVER['PHP_SELF'])) {
message::add($text['message-invalid_token'],'negative');
header('Location: fifo.php'.($query_string ? '?'.$query_string : ''));
exit;
}
//process the http post data by submitted action
if (!empty($_POST['action']) && $_POST['action'] != '' && strlen($_POST['action']) > 0) {
//prepare the array(s)
$x = 0;
if (is_array($_POST['fifo_members'])) {
foreach ($_POST['fifo_members'] as $row) {
if (is_uuid($row['fifo_member_uuid']) && $row['checked'] == 'true') {
$array['fifo'][$x]['checked'] = $row['checked'];
$array['fifo'][$x]['fifo_members'][]['fifo_member_uuid'] = $row['fifo_member_uuid'];
$x++;
}
}
}
//send the array to the database class
switch ($_POST['action']) {
case 'copy':
if (permission_exists('fifo_add')) {
$database->copy($array);
}
break;
case 'delete':
if (permission_exists('fifo_delete')) {
$database->delete($array);
}
break;
case 'toggle':
if (permission_exists('fifo_update')) {
$database->toggle($array);
}
break;
}
//redirect the user
if (in_array($_POST['action'], array('copy', 'delete', 'toggle'))) {
header('Location: fifo_edit.php?id='.$id.($query_string ? '&'.$query_string : ''));
exit;
}
}
//validate the data
$fifo_extension = preg_replace('#[^a-zA-Z0-9.\-\*]#', '', $fifo_extension ?? '');
$fifo_order = preg_replace('#[^0-9]#', '', $fifo_order ?? '');
$fifo_exit_key = preg_replace('#[^0-9]#', '', $fifo_exit_key ?? '');
$fifo_timeout_seconds = preg_replace('#[^0-9]#', '', $fifo_timeout_seconds ?? '');
$fifo_agent_status = preg_replace('#[^a-zA-Z0-9.\-\*]#', '', $fifo_agent_status ?? '');
$fifo_agent_queue = preg_replace('#[^a-zA-Z0-9.\-\*]#', '', $fifo_agent_queue ?? '');
if (!empty($fifo_uuid) && !is_uuid($fifo_uuid)) { throw new Exception("invalid uuid"); }
if (!empty($dialplan_uuid) && !is_uuid($dialplan_uuid)) { throw new Exception("invalid uuid"); }
if (is_array($fifo_members)) {
$i = 0;
foreach ($fifo_members as $row) {
$fifo_members[$i]['member_contact'] = preg_replace('#[^a-zA-Z0-9/@.\-\*]#', '', $row["member_contact"] ?? '');
$fifo_members[$i]['member_call_timeout'] = preg_replace('#[^0-9]#', '', $row["member_call_timeout"] ?? '20');
$fifo_members[$i]['member_wrap_up_time'] = preg_replace('#[^0-9]#', '', $row["member_wrap_up_time"] ?? '10');
$fifo_members[$i]['member_enabled'] = $row["member_enabled"];
$i++;
}
}
//check for all required data
$msg = '';
if (strlen($fifo_name) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_name']."
\n"; }
if (strlen($fifo_extension) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_extension']."
\n"; }
//if (strlen($fifo_agent_status) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_agent_status']."
\n"; }
//if (strlen($fifo_agent_queue) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_agent_queue']."
\n"; }
if (strlen($fifo_strategy) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_strategy']."
\n"; }
//if (strlen($fifo_members) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_members']."
\n"; }
//if (strlen($fifo_timeout_seconds) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_timeout_seconds']."
\n"; }
//if (strlen($fifo_exit_key) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_exit_key']."
\n"; }
//if (strlen($fifo_exit_action) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_exit_action']."
\n"; }
//if (strlen($fifo_music) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_music']."
\n"; }
if (strlen($domain_uuid) == 0) { $msg .= $text['message-required']." ".$text['label-domain_uuid']."
\n"; }
if (strlen($fifo_order) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_order']."
\n"; }
//if (strlen($fifo_enabled) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_enabled']."
\n"; }
//if (strlen($fifo_description) == 0) { $msg .= $text['message-required']." ".$text['label-fifo_description']."
\n"; }
if (strlen($msg) > 0 && (empty($_POST["persistformvar"]) || strlen($_POST["persistformvar"]) == 0)) {
require_once "resources/header.php";
require_once "resources/persist_form_var.php";
echo "
\n";
echo "
\n";
echo $msg." ";
echo " |
\n";
persistformvar($_POST);
echo "
\n";
require_once "resources/footer.php";
return;
}
//add the fifo_uuid
$fifo_uuid = !empty($_POST["fifo_uuid"]) && is_uuid($_POST["fifo_uuid"]) ? $_POST["fifo_uuid"] : uuid();
//add a uuid to dialplan_uuid if it is empty
if (empty($dialplan_uuid) && !is_uuid($dialplan_uuid)) {
$dialplan_uuid = uuid();
}
//prepare the variables
$queue_name = $fifo_extension."@".$_SESSION['domain_name'];
$app_uuid = '16589224-c876-aeb3-f59f-523a1c0801f7';
$dialplan_context = $_SESSION['domain_name'];
$domain_uuid = $_SESSION['domain_uuid'];
$dialplan_detail_order = 0;
//prepare the array
$array['fifo'][0]['fifo_uuid'] = $fifo_uuid;
$array['fifo'][0]['domain_uuid'] = $_SESSION['domain_uuid'];
$array['fifo'][0]['dialplan_uuid'] = $dialplan_uuid;
$array['fifo'][0]['fifo_name'] = $fifo_name;
$array['fifo'][0]['fifo_extension'] = $fifo_extension;
$array['fifo'][0]['fifo_agent_status'] = $fifo_agent_status;
$array['fifo'][0]['fifo_agent_queue'] = $fifo_agent_queue;
$array['fifo'][0]['fifo_strategy'] = $fifo_strategy;
$array['fifo'][0]['fifo_timeout_seconds'] = $fifo_timeout_seconds;
$array['fifo'][0]['fifo_exit_key'] = $fifo_exit_key;
$array['fifo'][0]['fifo_exit_action'] = $fifo_exit_action;
$array['fifo'][0]['fifo_music'] = $fifo_music;
$array['fifo'][0]['fifo_order'] = $fifo_order;
$array['fifo'][0]['fifo_enabled'] = $fifo_enabled;
$array['fifo'][0]['fifo_description'] = $fifo_description;
if (is_array($fifo_members)) {
$y = 0;
foreach ($fifo_members as $row) {
if (!empty($row['member_contact']) && strlen($row['member_contact']) > 0) {
$array['fifo'][0]['fifo_members'][$y]['fifo_member_uuid'] = $row["fifo_member_uuid"];
$array['fifo'][0]['fifo_members'][$y]['domain_uuid'] = $_SESSION['domain_uuid'];
$array['fifo'][0]['fifo_members'][$y]['member_contact'] = $row["member_contact"];
$array['fifo'][0]['fifo_members'][$y]['member_call_timeout'] = $row["member_call_timeout"] ?? '20';
//$array['fifo'][0]['fifo_members'][$y]['member_simultaneous'] = $row["member_simultaneous"];
$array['fifo'][0]['fifo_members'][$y]['member_wrap_up_time'] = $row["member_wrap_up_time"] ?? '10';
$array['fifo'][0]['fifo_members'][$y]['member_enabled'] = $row["member_enabled"];
$y++;
}
}
}
//send commands for agent login or agent logout
if (is_array($fifo_members)) {
foreach ($fifo_members as $row) {
//empty row skip iteration
if (empty($row["member_contact"])) {
continue;
}
//build the command to add or remove the agent from the FIFO queue
if ($row["member_enabled"] == 'true') {
$command = "fifo_member add ".$fifo_extension."@".$_SESSION['domain_name']." {fifo_member_wait=nowait}".$row["member_contact"]." 5 ".$row['member_call_timeout']." ".$row['member_wrap_up_time'];
}
else {
$command = "fifo_member del ".$fifo_extension."@".$_SESSION['domain_name']." {fifo_member_wait=nowait}".$row["member_contact"];
}
if ($event_socket->is_connected()) {
$response = $event_socket->command('api '.$command);
}
}
}
//get the action destination number
if (!empty($fifo_exit_action)) {
$fifo_exit_destination = explode(':', $fifo_exit_action)[1];
$fifo_exit_destination = explode(' ', $fifo_exit_destination)[0];
}
//add the fifo dialplan
if (!empty($fifo_extension)) {
//escape the * symbol
$fifo_agent_status_xml = str_replace("*", "\*", $fifo_agent_status);
$fifo_agent_queue_xml = str_replace("*", "\*", $fifo_agent_queue);
//prepare the fifo orbit extension
if (!empty($fifo_exit_destination) && $fifo_timeout_seconds == 0) {
$fifo_orbit_exten = $fifo_exit_destination;
}
else {
$fifo_orbit_exten = $fifo_exit_destination.":".$fifo_timeout_seconds;
}
//build the xml dialplan
$dialplan_xml = "\n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
if ($fifo_strategy == 'longest_idle_agent') {
$dialplan_xml .= " \n";
}
if ($fifo_strategy == 'simultaneous') {
$dialplan_xml .= " \n";
}
/*
*/
if (!empty($fifo_exit_key)) {
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
}
if (!empty($fifo_orbit_exten)) {
$dialplan_xml .= " \n";
}
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= " \n";
$dialplan_xml .= "\n";
//start building the dialplan array
$y=0;
$array["dialplans"][$y]["domain_uuid"] = $_SESSION['domain_uuid'];
$array["dialplans"][$y]["dialplan_uuid"] = $dialplan_uuid;
$array["dialplans"][$y]["app_uuid"] = $app_uuid;
$array["dialplans"][$y]["dialplan_name"] = $fifo_name;
$array["dialplans"][$y]["dialplan_number"] = $fifo_extension;
$array["dialplans"][$y]["dialplan_xml"] = $dialplan_xml;
$array["dialplans"][$y]["dialplan_order"] = $fifo_order;
$array["dialplans"][$y]["dialplan_context"] = $_SESSION['domain_name'];
$array["dialplans"][$y]["dialplan_enabled"] = $fifo_enabled;
$array["dialplans"][$y]["dialplan_description"] = $fifo_description;
$y++;
}
//add the dialplan permission
$p = permissions::new();
$p->add("dialplan_add", "temp");
$p->add("dialplan_edit", "temp");
//save the data
$result = $database->save($array);
//remove the temporary permission
$p->delete("dialplan_add", "temp");
$p->delete("dialplan_edit", "temp");
//redirect the user
if (isset($action)) {
//apply settings reminder
$_SESSION["reload_xml"] = true;
//clear the cache
$cache = new cache;
$cache->delete("dialplan:".$_SESSION['domain_name']);
//clear the destinations session array
if (isset($_SESSION['destinations']['array'])) {
unset($_SESSION['destinations']['array']);
}
//set the message
if ($action == "add") {
//save the message to a session variable
message::add($text['message-add']);
}
if ($action == "update") {
//save the message to a session variable
message::add($text['message-update']);
}
//header('Location: fifo.php');
header('Location: fifo_edit.php?id='.urlencode($fifo_uuid).($query_string ? '&'.$query_string : ''));
return;
}
}
//pre-populate the form
if (!empty($_GET) && is_array($_GET) && (empty($_POST["persistformvar"]) || $_POST["persistformvar"] != "true")) {
$sql = "select ";
$sql .= " dialplan_uuid, ";
$sql .= " fifo_uuid, ";
$sql .= " fifo_name, ";
$sql .= " fifo_extension, ";
$sql .= " fifo_agent_status, ";
$sql .= " fifo_agent_queue, ";
$sql .= " fifo_strategy, ";
$sql .= " fifo_timeout_seconds, ";
$sql .= " fifo_exit_key, ";
$sql .= " fifo_exit_action, ";
$sql .= " fifo_music, ";
$sql .= " domain_uuid, ";
$sql .= " fifo_order, ";
$sql .= " fifo_enabled, ";
$sql .= " fifo_description ";
$sql .= "from v_fifo ";
$sql .= "where fifo_uuid = :fifo_uuid ";
//$sql .= "and domain_uuid = :domain_uuid ";
//$parameters['domain_uuid'] = $_SESSION['domain_uuid'];
$parameters['fifo_uuid'] = $fifo_uuid;
$row = $database->select($sql, $parameters, 'row');
if (is_array($row) && @sizeof($row) != 0) {
$dialplan_uuid = $row["dialplan_uuid"];
$fifo_name = $row["fifo_name"];
$fifo_extension = $row["fifo_extension"];
$fifo_agent_status = $row["fifo_agent_status"];
$fifo_agent_queue = $row["fifo_agent_queue"];
$fifo_strategy = $row["fifo_strategy"];
$fifo_timeout_seconds = $row["fifo_timeout_seconds"];
$fifo_exit_key = $row["fifo_exit_key"];
$fifo_exit_action = $row["fifo_exit_action"];
$fifo_music = $row["fifo_music"];
$domain_uuid = $row["domain_uuid"];
$fifo_order = $row["fifo_order"];
$fifo_enabled = $row["fifo_enabled"];
$fifo_description = $row["fifo_description"];
}
unset($sql, $parameters, $row);
}
//set the defaults
$fifo_enabled = $fifo_enabled ?? true;
//get the child data
if (!empty($fifo_uuid) && is_uuid($fifo_uuid)) {
$sql = "select ";
$sql .= " fifo_member_uuid, ";
$sql .= " domain_uuid, ";
$sql .= " fifo_uuid, ";
$sql .= " member_contact, ";
$sql .= " member_call_timeout, ";
//$sql .= " member_simultaneous, ";
$sql .= " member_wrap_up_time, ";
$sql .= " member_enabled ";
$sql .= "from v_fifo_members ";
$sql .= "where fifo_uuid = :fifo_uuid ";
//$sql .= "and domain_uuid = '".$domain_uuid."' ";
//$parameters['domain_uuid'] = $_SESSION['domain_uuid'];
$parameters['fifo_uuid'] = $fifo_uuid;
$fifo_members = $database->select($sql, $parameters, 'all');
unset ($sql, $parameters);
}
else {
$fifo_members = [];
$fifo_uuid = uuid();
}
//add a uuid to dialplan_uuid if it is empty
if (empty($dialplan_uuid) || !is_uuid($dialplan_uuid)) {
$dialplan_uuid = uuid();
}
//add the $fifo_member_uuid
if (empty($fifo_member_uuid) || !is_uuid($fifo_member_uuid)) {
$fifo_member_uuid = uuid();
}
//add an empty row to the members array
if (count($fifo_members) == 0) {
$rows = $settings->get('fifo', 'option_add_rows', '5');
$id = 0;
$show_option_delete = false;
}
if (count($fifo_members) > 0) {
$rows = $settings->get('fifo', 'option_edit_rows', '1');
$id = count($fifo_members)+1;
$show_option_delete = true;
}
for ($x = 0; $x < $rows; $x++) {
$fifo_members[$id]['domain_uuid'] = $_SESSION['domain_uuid'];
$fifo_members[$id]['fifo_uuid'] = $fifo_uuid;
$fifo_members[$id]['fifo_member_uuid'] = uuid();
$fifo_members[$id]['member_contact'] = '';
$fifo_members[$id]['member_call_timeout'] = '';
//$fifo_members[$id]['member_simultaneous'] = '';
$fifo_members[$id]['member_wrap_up_time'] = '';
$fifo_members[$id]['member_enabled'] = false;
$id++;
}
//create token
$object = new token;
$token = $object->create($_SERVER['PHP_SELF']);
//initialize the destinations object
$destination = new destinations;
//set the defaults
if (empty($fifo_timeout_seconds)) {
$fifo_timeout_seconds = 0;
}
if (empty($fifo_order)) {
$fifo_order = 50;
}
//show the header
$document['title'] = $text['title-fifo'];
require_once "resources/header.php";
//show the content
echo "";
//include the footer
require_once "resources/footer.php";
?>