Beispiel #1
0
function manejarMonitoreo_checkStatus($module_name, $smarty, $sDirLocalPlantillas)
{
    $respuesta = array();
    ignore_user_abort(true);
    set_time_limit(0);
    // Estado del lado del cliente
    $estadoHash = getParameter('clientstatehash');
    if (!is_null($estadoHash)) {
        $estadoCliente = isset($_SESSION[$module_name]['estadoCliente']) ? $_SESSION[$module_name]['estadoCliente'] : array();
    } else {
        $estadoCliente = getParameter('clientstate');
        if (!is_array($estadoCliente)) {
            return;
        }
    }
    // Modo a funcionar: Long-Polling, o Server-sent Events
    $sModoEventos = getParameter('serverevents');
    $bSSE = !is_null($sModoEventos) && $sModoEventos;
    if ($bSSE) {
        Header('Content-Type: text/event-stream');
        printflush("retry: 1\n");
    } else {
        Header('Content-Type: application/json');
    }
    // Verificar hash correcto
    if (!is_null($estadoHash) && $estadoHash != $_SESSION[$module_name]['estadoClienteHash']) {
        $respuesta['estadoClienteHash'] = 'mismatch';
        $respuesta['hashRecibido'] = $estadoHash;
        jsonflush($bSSE, $respuesta);
        return;
    }
    $oPaloConsola = new PaloSantoConsola();
    // Estado del lado del servidor
    $estadoCampania = $oPaloConsola->leerEstadoCampania($estadoCliente['campaigntype'], $estadoCliente['campaignid']);
    if (!is_array($estadoCampania)) {
        $respuesta['error'] = $oPaloConsola->errMsg;
        jsonflush($bSSE, $respuesta);
        $oPaloConsola->desconectarTodo();
        return;
    }
    // Acumular inmediatamente las filas que son distintas en estado
    $respuesta = crearRespuestaVacia();
    // Cuenta de estados
    foreach (array_keys($estadoCliente['statuscount']) as $k) {
        // Actualización de valores de contadores
        if ($estadoCliente['statuscount'][$k] != $estadoCampania['statuscount'][$k]) {
            $respuesta['statuscount']['update'][$k] = $estadoCampania['statuscount'][$k];
            $estadoCliente['statuscount'][$k] = $estadoCampania['statuscount'][$k];
        }
    }
    // Estado de llamadas no conectadas
    foreach (array_keys($estadoCliente['activecalls']) as $k) {
        // Llamadas que cambiaron de estado o ya no están sin agente
        if (!isset($estadoCampania['activecalls'][$k])) {
            // Llamada ya no está esperando agente
            $respuesta['activecalls']['remove'][] = array('callid' => $estadoCliente['activecalls'][$k]['callid']);
            unset($estadoCliente['activecalls'][$k]);
        } elseif ($estadoCliente['activecalls'][$k]['callstatus'] != $estadoCampania['activecalls'][$k]['callstatus']) {
            // Llamada ha cambiado de estado
            $respuesta['activecalls']['update'][] = formatoLlamadaNoConectada($estadoCampania['activecalls'][$k]);
            $estadoCliente['activecalls'][$k] = $estadoCampania['activecalls'][$k];
        }
    }
    foreach (array_keys($estadoCampania['activecalls']) as $k) {
        // Llamadas nuevas
        if (!isset($estadoCliente['activecalls'][$k])) {
            $respuesta['activecalls']['add'][] = formatoLlamadaNoConectada($estadoCampania['activecalls'][$k]);
            $estadoCliente['activecalls'][$k] = $estadoCampania['activecalls'][$k];
        }
    }
    // Estado de agentes de campaña
    foreach (array_keys($estadoCliente['agents']) as $k) {
        // Agentes que cambiaron de estado o desaparecieron (???)
        if (!isset($estadoCampania['agents'][$k])) {
            // Agente ya no aparece (???)
            $respuesta['agents']['remove'][] = array('agent' => $estadoCliente['agents'][$k]['agentchannel']);
            unset($estadoCliente['agents'][$k]);
        } elseif ($estadoCliente['agents'][$k] != $estadoCampania['agents'][$k]) {
            // Agente ha cambiado de estado
            $respuesta['agents']['update'][] = formatoAgente($estadoCampania['agents'][$k]);
            $estadoCliente['agents'][$k] = $estadoCampania['agents'][$k];
        }
    }
    foreach (array_keys($estadoCampania['agents']) as $k) {
        // Agentes nuevos (???)
        if (!isset($estadoCliente['agents'][$k])) {
            $respuesta['agents']['add'][] = formatoAgente($estadoCampania['agents'][$k]);
            $estadoCliente['agents'][$k] = $estadoCampania['agents'][$k];
        }
    }
    unset($estadoCampania);
    $oPaloConsola->escucharProgresoLlamada(TRUE);
    $iTimeoutPoll = PaloSantoConsola::recomendarIntervaloEsperaAjax();
    do {
        $oPaloConsola->desconectarEspera();
        // Se inicia espera larga con el navegador...
        $iTimestampInicio = time();
        while (connection_status() == CONNECTION_NORMAL && esRespuestaVacia($respuesta) && time() - $iTimestampInicio < $iTimeoutPoll) {
            session_commit();
            $listaEventos = $oPaloConsola->esperarEventoSesionActiva();
            if (is_null($listaEventos)) {
                $respuesta['error'] = $oPaloConsola->errMsg;
                jsonflush($bSSE, $respuesta);
                $oPaloConsola->desconectarTodo();
                return;
            }
            @session_start();
            /* Si el navegador elige otra campaña mientras se espera la primera
             * campaña, entonces esta espera es inválida, y el navegador ya ha
             * iniciado otra sesión comet. */
            if (isset($_SESSION[$module_name]) && !($estadoCliente['campaigntype'] === $_SESSION[$module_name]['estadoCliente']['campaigntype'] && $estadoCliente['campaignid'] === $_SESSION[$module_name]['estadoCliente']['campaignid'])) {
                $respuesta['estadoClienteHash'] = 'invalidated';
                jsonflush($bSSE, $respuesta);
                $oPaloConsola->desconectarTodo();
                return;
            }
            $iTimestampActual = time();
            foreach ($listaEventos as $evento) {
                $sCanalAgente = isset($evento['agent_number']) ? $evento['agent_number'] : NULL;
                switch ($evento['event']) {
                    case 'agentloggedin':
                        if (isset($estadoCliente['agents'][$sCanalAgente])) {
                            /* Se ha logoneado agente que atiende a esta campaña.
                             * ATENCIÓN: sólo se setean suficientes campos para la
                             * visualización. Otros campos quedan con sus valores
                             * antiguos, si tenían */
                            $estadoCliente['agents'][$sCanalAgente]['status'] = 'online';
                            $estadoCliente['agents'][$sCanalAgente]['callnumber'] = NULL;
                            $estadoCliente['agents'][$sCanalAgente]['pausestart'] = NULL;
                            $estadoCliente['agents'][$sCanalAgente]['linkstart'] = NULL;
                            $estadoCliente['agents'][$sCanalAgente]['trunk'] = NULL;
                            $respuesta['agents']['update'][] = formatoAgente($estadoCliente['agents'][$sCanalAgente]);
                        }
                        break;
                    case 'agentloggedout':
                        if (isset($estadoCliente['agents'][$sCanalAgente])) {
                            /* Se ha deslogoneado agente que atiende a esta campaña.
                             * ATENCIÓN: sólo se setean suficientes campos para la
                             * visualización. Otros campos quedan con sus valores
                             * antiguos, si tenían */
                            $estadoCliente['agents'][$sCanalAgente]['status'] = 'offline';
                            $estadoCliente['agents'][$sCanalAgente]['callnumber'] = NULL;
                            $estadoCliente['agents'][$sCanalAgente]['pausestart'] = NULL;
                            $estadoCliente['agents'][$sCanalAgente]['linkstart'] = NULL;
                            $estadoCliente['agents'][$sCanalAgente]['trunk'] = NULL;
                            $respuesta['agents']['update'][] = formatoAgente($estadoCliente['agents'][$sCanalAgente]);
                        }
                        break;
                    case 'callprogress':
                        $bProcesar = $estadoCliente['campaigntype'] == 'incomingqueue' ? $estadoCliente['campaignid'] == $evento['queue'] && is_null($evento['campaign_id']) : $estadoCliente['campaignid'] == $evento['campaign_id'] && $estadoCliente['campaigntype'] == $evento['call_type'];
                        if ($bProcesar) {
                            // Llamada corresponde a cola monitoreada
                            $callid = $evento['call_id'];
                            // Para llamadas entrantes, cada llamada en cola aumenta el total
                            if ($evento['call_type'] == 'incoming' && $evento['new_status'] == 'OnQueue') {
                                agregarContadorLlamada('total', $estadoCliente, $respuesta);
                            }
                            if (in_array($evento['new_status'], array('Failure', 'Abandoned', 'NoAnswer'))) {
                                if (isset($estadoCliente['activecalls'][$callid])) {
                                    restarContadorLlamada($estadoCliente['activecalls'][$callid]['callstatus'], $estadoCliente, $respuesta);
                                    agregarContadorLlamada($evento['new_status'], $estadoCliente, $respuesta);
                                    // Quitar de las llamadas que esperan un agente
                                    $respuesta['activecalls']['remove'][] = array('callid' => $callid);
                                    unset($estadoCliente['activecalls'][$callid]);
                                }
                            } elseif (in_array($evento['new_status'], array('OnHold', 'OffHold'))) {
                                // Se supone que una llamada en hold ya fue asignada a un agente
                            } else {
                                if (isset($estadoCliente['activecalls'][$callid])) {
                                    restarContadorLlamada($estadoCliente['activecalls'][$callid]['callstatus'], $estadoCliente, $respuesta);
                                    $estadoCliente['activecalls'][$callid]['callstatus'] = $evento['new_status'];
                                    $estadoCliente['activecalls'][$callid]['trunk'] = $evento['trunk'];
                                    if ($evento['new_status'] == 'OnQueue') {
                                        $estadoCliente['activecalls'][$callid]['queuestart'] = $evento['datetime_entry'];
                                    }
                                    $respuesta['activecalls']['update'][] = formatoLlamadaNoConectada($estadoCliente['activecalls'][$callid]);
                                } else {
                                    // Valores sólo para satisfacer formato
                                    $estadoCliente['activecalls'][$callid] = array('callid' => $callid, 'callnumber' => $evento['phone'], 'callstatus' => $evento['new_status'], 'dialstart' => $evento['datetime_entry'], 'dialend' => NULL, 'queuestart' => $evento['datetime_entry'], 'trunk' => $evento['trunk']);
                                    $respuesta['activecalls']['add'][] = formatoLlamadaNoConectada($estadoCliente['activecalls'][$callid]);
                                }
                                agregarContadorLlamada($evento['new_status'], $estadoCliente, $respuesta);
                            }
                            $respuesta['log'][] = formatoLogCampania(array('id' => $evento['id'], 'new_status' => $evento['new_status'], 'datetime_entry' => $evento['datetime_entry'], 'campaign_type' => $evento['call_type'], 'campaign_id' => $evento['campaign_id'], 'call_id' => $evento['call_id'], 'retry' => $evento['retry'], 'uniqueid' => $evento['uniqueid'], 'trunk' => $evento['trunk'], 'phone' => $evento['phone'], 'queue' => $evento['queue'], 'agentchannel' => $sCanalAgente, 'duration' => NULL));
                        }
                        break;
                    case 'pausestart':
                        if (isset($estadoCliente['agents'][$sCanalAgente])) {
                            // Agente ha entrado en pausa
                            $estadoCliente['agents'][$sCanalAgente]['status'] = 'paused';
                            $estadoCliente['agents'][$sCanalAgente]['pausestart'] = $evento['pause_start'];
                            $respuesta['agents']['update'][] = formatoAgente($estadoCliente['agents'][$sCanalAgente]);
                        }
                        break;
                    case 'pauseend':
                        if (isset($estadoCliente['agents'][$sCanalAgente])) {
                            // Agente ha salido de pausa
                            $estadoCliente['agents'][$sCanalAgente]['status'] = is_null($estadoCliente['agents'][$sCanalAgente]['linkstart']) ? 'online' : 'oncall';
                            $estadoCliente['agents'][$sCanalAgente]['pausestart'] = NULL;
                            $respuesta['agents']['update'][] = formatoAgente($estadoCliente['agents'][$sCanalAgente]);
                        }
                        break;
                    case 'agentlinked':
                        // Si la llamada estaba en lista activa, quitarla
                        $callid = $evento['call_id'];
                        if (isset($estadoCliente['activecalls'][$callid])) {
                            restarContadorLlamada($estadoCliente['activecalls'][$callid]['callstatus'], $estadoCliente, $respuesta);
                            $respuesta['activecalls']['remove'][] = array('callid' => $estadoCliente['activecalls'][$callid]['callid']);
                            unset($estadoCliente['activecalls'][$callid]);
                        }
                        // Si el agente es uno de los de la campaña, modificar
                        if (isset($estadoCliente['agents'][$sCanalAgente])) {
                            $estadoCliente['agents'][$sCanalAgente]['status'] = is_null($estadoCliente['agents'][$sCanalAgente]['pausestart']) ? 'oncall' : 'paused';
                            $estadoCliente['agents'][$sCanalAgente]['callnumber'] = $evento['phone'];
                            $estadoCliente['agents'][$sCanalAgente]['linkstart'] = $evento['datetime_linkstart'];
                            $estadoCliente['agents'][$sCanalAgente]['trunk'] = $evento['trunk'];
                            $respuesta['agents']['update'][] = formatoAgente($estadoCliente['agents'][$sCanalAgente]);
                            $respuesta['log'][] = formatoLogCampania(array('id' => $evento['campaignlog_id'], 'new_status' => 'Success', 'datetime_entry' => $evento['datetime_linkstart'], 'campaign_type' => $evento['call_type'], 'campaign_id' => $evento['campaign_id'], 'call_id' => $evento['call_id'], 'retry' => $evento['retries'], 'uniqueid' => $evento['uniqueid'], 'trunk' => $evento['trunk'], 'phone' => $evento['phone'], 'queue' => $evento['queue'], 'agentchannel' => $sCanalAgente, 'duration' => NULL));
                            agregarContadorLlamada('Success', $estadoCliente, $respuesta);
                        }
                        break;
                    case 'agentunlinked':
                        // Si el agente es uno de los de la campaña, modificar
                        if (isset($estadoCliente['agents'][$sCanalAgente])) {
                            /* Es posible que se reciba un evento agentunlinked luego
                             * del evento agentloggedout si el agente se desconecta con
                             * una llamada activa. */
                            if ($estadoCliente['agents'][$sCanalAgente]['status'] != 'offline') {
                                $estadoCliente['agents'][$sCanalAgente]['status'] = is_null($estadoCliente['agents'][$sCanalAgente]['pausestart']) ? 'online' : 'paused';
                            }
                            $estadoCliente['agents'][$sCanalAgente]['callnumber'] = NULL;
                            $estadoCliente['agents'][$sCanalAgente]['linkstart'] = NULL;
                            $estadoCliente['agents'][$sCanalAgente]['trunk'] = NULL;
                            $respuesta['agents']['update'][] = formatoAgente($estadoCliente['agents'][$sCanalAgente]);
                            $respuesta['log'][] = formatoLogCampania(array('id' => $evento['campaignlog_id'], 'new_status' => $evento['shortcall'] ? 'ShortCall' : 'Hangup', 'datetime_entry' => $evento['datetime_linkend'], 'campaign_type' => $evento['call_type'], 'campaign_id' => $evento['campaign_id'], 'call_id' => $evento['call_id'], 'retry' => NULL, 'uniqueid' => NULL, 'trunk' => NULL, 'phone' => $evento['phone'], 'queue' => NULL, 'agentchannel' => $sCanalAgente, 'duration' => $evento['duration']));
                            if ($evento['call_type'] == 'incoming') {
                                restarContadorLlamada('Success', $estadoCliente, $respuesta);
                                agregarContadorLlamada('Finished', $estadoCliente, $respuesta);
                                agregarContadorLlamada('Total', $estadoCliente, $respuesta);
                                $respuesta['duration'] = $evento['duration'];
                            } else {
                                if ($evento['shortcall']) {
                                    restarContadorLlamada('Success', $estadoCliente, $respuesta);
                                    agregarContadorLlamada('ShortCall', $estadoCliente, $respuesta);
                                } else {
                                    // Se actualiza Finished para actualizar estadísticas
                                    agregarContadorLlamada('Finished', $estadoCliente, $respuesta);
                                    $respuesta['duration'] = $evento['duration'];
                                }
                            }
                            if (isset($respuesta['duration'])) {
                                $estadoCliente['stats']['total_sec'] += $respuesta['duration'];
                                if ($estadoCliente['stats']['max_duration'] < $respuesta['duration']) {
                                    $estadoCliente['stats']['max_duration'] = $respuesta['duration'];
                                }
                            }
                        }
                        break;
                }
            }
        }
        $estadoHash = generarEstadoHash($module_name, $estadoCliente);
        $respuesta['estadoClienteHash'] = $estadoHash;
        jsonflush($bSSE, $respuesta);
        $respuesta = crearRespuestaVacia();
    } while ($bSSE && connection_status() == CONNECTION_NORMAL);
    $oPaloConsola->desconectarTodo();
}
Beispiel #2
0
function manejarLogin_checkLogin()
{
    $respuesta = array('action' => 'wait', 'message' => '(no message)');
    $bContinuar = TRUE;
    // Verificación rápida para saber si el canal es correcto
    $sAgente = $_SESSION['callcenter']['agente'];
    $sExtension = $_SESSION['callcenter']['extension'];
    $oPaloConsola = new PaloSantoConsola('Agent/' . $sAgente);
    if ($bContinuar) {
        $estado = $oPaloConsola->estadoAgenteLogoneado($sExtension);
        switch ($estado['estadofinal']) {
            case 'error':
            case 'mismatch':
                // Otra extensión ya ocupa el login del agente indicado, o error
                $_SESSION['callcenter'] = generarEstadoInicial();
                $respuesta['action'] = 'error';
                $respuesta['message'] = _tr('Cannot start agent login') . ' - ' . $oPaloConsola->errMsg . "ext={$sExtension} agente={$sAgente}";
                $bContinuar = FALSE;
                break;
            case 'logged-out':
                // No se encuentra evidencia de que se empezara el login
                $_SESSION['callcenter'] = generarEstadoInicial();
                $respuesta['action'] = 'error';
                $respuesta['message'] = _tr('Agent login process not started');
                $bContinuar = FALSE;
                break;
            case 'logging':
                $_SESSION['callcenter']['estado_consola'] = 'logging';
                $respuesta['action'] = 'wait';
                $respuesta['message'] = _tr('Logging agent in. Please wait...');
                break;
            case 'logged-in':
                // El agente ha podido logonearse. Se procede a mostrar el formulario
                $_SESSION['callcenter']['estado_consola'] = 'logged-in';
                $respuesta['action'] = 'login';
                $bContinuar = FALSE;
                break;
        }
    }
    if ($bContinuar && $respuesta['action'] == 'wait') {
        $oPaloConsola->desconectarEspera();
        // Se inicia espera larga con el navegador...
        $iTimeoutPoll = PaloSantoConsola::recomendarIntervaloEsperaAjax();
        session_commit();
        set_time_limit(0);
        $iTimestampInicio = time();
        while ($bContinuar && time() - $iTimestampInicio < $iTimeoutPoll) {
            // Verificar si el agente ya está en línea
            $sEstado = $oPaloConsola->esperarResultadoLogin();
            if ($sEstado == 'logged-in') {
                // Reiniciar la sesión para poder modificar las variables
                session_start();
                // El agente ha podido logonearse. Se procede a mostrar el formulario
                $_SESSION['callcenter']['estado_consola'] = 'logged-in';
                $respuesta['action'] = 'login';
                $bContinuar = FALSE;
            } elseif ($sEstado == 'logged-out') {
                // Reiniciar la sesión para poder modificar las variables
                session_start();
                // El procedimiento de login ha fallado, sin causa conocida
                $_SESSION['callcenter'] = generarEstadoInicial();
                $respuesta['action'] = 'error';
                $respuesta['message'] = _tr('Agent log-in terminated.');
                $bContinuar = FALSE;
            } elseif ($sEstado == 'error') {
                // Reiniciar la sesión para poder modificar las variables
                session_start();
                // Ocurre un error al consultar el estado del agente
                $_SESSION['callcenter'] = generarEstadoInicial();
                $respuesta['action'] = 'error';
                $respuesta['message'] = _tr('Agent log-in failed!') . ' - ' . $oPaloConsola->errMsg;
                $bContinuar = FALSE;
            }
        }
    }
    $json = new Services_JSON();
    $sContenido = $json->encode($respuesta);
    Header('Content-Type: application/json');
    $oPaloConsola->desconectarTodo();
    return $sContenido;
}