T reba ll F ina l de G rau
INGENIERÍA INFORMÁTICA
Sistema web para habitissimo
JAUME JIMÉNEZ FORTEZA
Tutors
Carlos Guerrero Tomé Jordi Llull Chavarría
Escola Politècnica Superior
Universitat de les Illes Balears
Como agradecimientos incluyo a la empresa habitissimo junto a la Universidad de las Islas Baleares, por hacer posible el acercamiento entre el mundo laboral y los estudios universitarios en forma, en este caso, de Trabajo de Fin de Grado. A mi familia por darme apoyo y ayudarme a sacar el trabajo adelante. También quiero agradecer a mis dos tutores: Dr. Carlos Guerrero Tomé, mi tutor por parte de la Universidad y Jordi Llull Chavarría, mi tutor en habitissimo, que me han dado soporte y me han animado a trabajar para sacar adelante este trabajo. Para finalizar destaco la ayuda de mis todos mis compañeros de trabajo, entre los que destaco a Joan Font, creador del sistema web inicial, y en especial a José Mañas, con quien colaboré para realizar el desarrollo de
Í NDICE GENERAL
Índice general iii
Índice de figuras v
Índice de códigos vii
Índice de tablas ix
Acrónimos xi
Resumen xiii
1 Introducción 1
1.1 Sobre este TFG . . . 1
1.2 Habitissimo . . . 2
1.3 Descripción del problema . . . 2
2 Contextualización 5 2.1 Sistema inicial . . . 5
2.1.1 Aplicación web . . . 5
2.1.2 Base de datos . . . 7
2.2 Servicios Voice over Internet Protocol (VoIP) . . . 9
2.3 Asterisk . . . 10
3 Aspectos previos al desarrollo 21 3.1 Equipo de trabajo . . . 21
3.1.1 Estructura y roles . . . 21
3.1.2 Herramientas de trabajo . . . 21
3.1.3 Metodología . . . 22
3.2 Planteamiento inicial del problema . . . 23
3.3 Soluciones propuestas . . . 24
4 Desarrollo del proyecto 27 4.1 Estructura del desarrollo . . . 27
4.2 Estructura de la nueva base de datos . . . 27
4.3 Estructura del desarrollo de la aplicación cron_script . . . 30
4.4 Optimización de cron_script . . . 36
4.5 Adaptación de cambios de modelos a la aplicación web . . . 39
iv ÍNDICE GENERAL
4.6 Nuevas implementaciones en la aplicación web . . . 40
5 Resultados y discusiones 51
6 Conclusiones 57
Bibliografía 59
Í NDICE DE FIGURAS
2.1 Estructura del sistema inicial . . . 6
2.2 Estructura inicial de la base de datos . . . 9
2.3 Arquitectura tradicional PBX vs.Asterisk[1] . . . 11
2.4 Sistema web inicial - Inicio . . . 14
2.5 Sistema web inicial - Apartado de llamadas . . . 15
2.6 Sistema web inicial - Apartado de informes - General . . . 16
2.7 Sistema web inicial - Apartado de informes - Entrantes . . . 17
2.8 Sistema web inicial - Apartado de informes - Franja horaria . . . 18
2.9 Sistema web inicial - Apartado de usuarios . . . 19
2.10 Sistema web inicial - Apartado de teléfonos . . . 20
3.1 Ciclo individual del Scrum [2] . . . 23
3.2 Patrón de llamada errónea . . . 24
3.3 Estructura final del sistema web . . . 26
4.1 Estructura de datos copy_calls . . . 32
4.2 Estructura inicial del desarrollo de cron_script . . . 36
4.3 Estructura final de cron_script . . . 39
4.4 Tiempos de llamada . . . 41
4.5 Sistema web final - Apartado de llamadas . . . 45
4.6 Sistema web final - Apartado de informes - General . . . 46
4.7 Sistema web final - Apartado de informes - Entrantes . . . 47
4.8 Sistema web final - Apartado de informes - Franja horaria . . . 48
4.9 Sistema web final - Apartado de usuarios . . . 49
5.1 Porcentaje de éxito en el filtrado de llamadas . . . 53
5.2 Comparativa tiempos de respuesta . . . 55
Í NDICE DE CÓDIGOS
4.1 Claves primarias para las tablascdryqueue_log . . . 28
4.2 Abstracción decdrcon nueva tabla . . . 29
4.3 Abstracción dequeue_logcon nueva tabla . . . 30
4.4 Creación de índices sobre las tablas generadas . . . 30
4.5 Media de llamadas/minuto en Diciembre de 2015 . . . 37
4.6 Pico de llamadas/minuto en Diciembre de 2015 . . . 38
4.7 Modificaciones relacionadas con la jornada laboral . . . 44
Í NDICE DE TABL AS
2.1 Tablas de la base de datos . . . 7
2.2 Descripción de la tablahab_cdr. . . 8
2.3 Descripción de la tablahab_answer_log . . . 8
2.4 Campos por defecto en CDR [3] . . . 13
2.5 Continuación de la tabla 2.4 . . . 14
4.1 Estructura de ficheros decron_script . . . 31
4.2 Ejemplo de patrón erróneo de llamada Queue-Queue-Direct call (Q.Q.D) . 33 4.3 Continuación de la tabla 4.2 . . . 33
4.4 Reparación del patrón erróneo de llamada Q.Q.D . . . 34
4.5 Continuación de la tabla 4.4 . . . 34
4.6 Ejemplo de llamada imposible de catalogar . . . 35
4.7 Continuación de la tabla 4.4 . . . 35
5.1 Cantidad de llamadas filtradas por patrón . . . 52
A CRÓNIMOS
ACD Automatic Call Distribution AEL Asterisk Extension Logic CDR Call Detail Records IPT IP Telephony
ODBC Open DataBase Connectivity PBX Private Branch Exchange
PSTN Public Switched Telephone Network Q.Q.D Queue-Queue-Direct call
VoIP Voice over Internet Protocol
R ESUMEN
Habitissimo S.L, con sede en el Parc Bit, cuenta con un centro de llamadas para proveer un servicio de atención al cliente personalizado. Todas las llamadas que circulan por sus centralitas, son registradas en una base de datos mediante un software VoIP libre llamadoAsterisk. Aprovechando este sistema, habitissimo dispone de una página web interna que, atacando a dicha base de datos, sirve de interfaz, para poder visualizar todas las llamadas que transcurren por habitissimo, y generar informes online de sus trabajadores. De esta manera, los jefes de los distintos equipos del centro de llamadas disponen de la información necesaria para generar, evaluar, y aplicar decisiones según los objetivos de la empresa.
El problema, del cual se nutre este TFG, se localiza en este ecosistema web. Princi- palmente la web no cumple con unos requisitos: la fiabilidad de los datos, los tiempos de carga de las secciones web son elevados y no disponen de la totalidad de las fun- cionalidades necesarias. El requisito de la fiabilidad de los datos no se cumple en el sentido que algunas llamadas muestran datos erróneos y no hay coherencia entre los informes, cosa que impide a los jefes de equipo del centro de llamadas, llevar a cabo algunas de las decisiones correspondientes a su rol. Por otra parte, los tiempos de carga de algunas secciones, superan el medio minuto de espera, por lo que se dificulta la navegación entre secciones de la web. Finalmente los jefes de equipo se ven obligados a utilizar herramientas externas para suplir funcionalidades que podrían estar en el sistema, ahorrándoles tiempo de trabajo.
La solución de este problema empieza por evaluar los datos que recibe la web; es decir, estudiar si los datos no son fiables en el entorno de la base de datos o si resultan corrompidos debido a la implementación web. Los resultados de este análisis derivan en un almacenamiento incorrecto de algunas llamadas en la base de datos, por lo que el error principal reside en la configuración del servicio VoIP de habitissimo. Para solven- tarlo, se genera un sistema que procesa las llamadas por lotes, en el que inicialmente se identifica si las llamadas forman parte de algún patrón de error, posteriormente se reparan en caso de ser necesario y posible y finalmente se guardan en una tabla nueva de la base de datos, la cual finalmente dispone de información limpia. Al disponer de información correcta, el siguiente paso es la implementación web.
Llegado el punto en que la base de datos dispone de información correcta y fun- cional, el trabajo se centra en la implementación de mejoras sobre la web. En esta fase se desarrollan funcionalidades para los usuarios finales, en este caso los jefes de equipo, que tienen un grado de implicación en el proyecto durante la definición de los
xiv RESUMEN
requisitos.
Como resultado, se consigue un sistema mejorado, con algunas implementaciones nuevas, pero principalmente con unos datos fiables y con una reducción notable de los tiempos de espera durante el uso de la web. Además, la estructura de la implementación realizada podría utilizarse en entornos donde la configuración del servicio VoIP no guardara correctamente los datos en su base de datos.
C
APÍTULO1
I NTRODUCCIÓN
1.1 Sobre este TFG
El proyecto realizado en este Trabajo Final de Grado consiste en un proceso de desa- rrollo que aborda una de las páginas web internas de la empresa habitissimo. Esta página web muestra información relacionada con las llamadas que transcurren por el centro de llamadas de habitissimo; contiene listados de llamadas, trabajadores de habitissimo, equipos de trabajadores y distintos informes de llamadas agrupados por equipos, trabajadores o país.
La necesidad de intervenir sobre dicha página web surge de un bajo nivel de fia- bilidad y usabilidad del sistema. Esto es debido principalmente a un muestreo de información con incoherencias, a la dificultad de navegación entre sus secciones, debi- do a los altos tiempos de espera de sus operaciones y, finalmente, de la necesidad por parte de los trabajadores que utilizan el sistema, de disponer nuevas herramientas que utilizar en el sistema web.
Para resolver este problema, se lleva a cabo un desarrollo que contempla la modifi- cación de la estructura de la base de datos de llamadas para garantizar que es óptima para el sistema web, la creación de una aplicación que repara la información dañada de la base de datos y finalmente nuevas implementaciones sobre el sistema web que satisfagan los requerimientos de los usuarios de la página web.
Este proceso de desarrollo se planifica, se efectúa y se testea en su totalidad dentro de habitissimo, por un grupo de desarrollo formado por José Mañas Picó y Jaume Jiménez Forteza, el autor de este documento. Además, cuenta con el soporte a nivel general del CTO de habitissimo y segundo tutor de este proyecto, Jordi Llull Chavarría.
1. INTRODUCCIÓN
1.2 Habitissimo
Habitissimo S.L es una empresa web perteneciente al sector de los servicios que conec- ta la oferta y la demanda del sector de las obras y reformas. Por una parte, permite a los usuarios particulares publicar anuncios cuando necesitan profesionales para un proyecto de obras o reformas, y por otra parte permite que profesionales, empresas y marcas comerciales, se registren en el directorio de empresas de habitissimo para ofrecer sus servicios a los particulares [4, 5, 6].
El funcionamiento básico de su entorno, consiste en que el particular expone su proyecto mediante una breve descripción del problema, y hasta un máximo de 4 profe- sionales interesados se apuntan a este proyecto según sus especialidades y su ubicación.
De esta manera, los profesionales apuntados a cada petición, podrán contactar con el particular, ofrecerle sus servicios y facilitarle información. Finalmente, será el particular el que decida cuál de los profesionales apuntados a su petición, será el que consiga el trabajo [7].
Además, habitissimo ofrece un perfil para cada profesional, donde puede subir sus proyectos realizados, visualizar opiniones de los particulares a los que ha dado servicio y obtener sellos de confianza, entre otras cosas, lo que significa que el profesio- nal puede obtener una valoración por parte del usuario, que afectará a la calidad y al posicionamiento de su ficha, dentro del directorio de empresas de habitissimo [8].
Por otra parte, habitissimo también ofrece una sección comunitaria de contenido, dirigida a los todos los usuarios que buscan inspiración e ideas a través de fotos y proyectos realizados por profesionales.
Actualmente habitissimo está disponible en 9 países: Argentina, Brasil, Chile, Co- lombia, Francia, España, Italia, México y Portugal, a los cuáles se les da soporte, tanto a los particulares como a los profesionales, mediante un centro de llamadas que ofrece un servicio de atención al cliente.
1.3 Descripción del problema
El centro de llamadas que dispone habitissimo está estructurado en un conjunto de equipos, organizados por país y operaciones a realizar, donde cada uno de ellos ofrece un servicio telefónico personalizado al país en el que operan.
Cada trabajador del centro de llamadas dispone de un teléfono, tanto para realizar llamadas, como para recibirlas o transferirlas a otro trabajador. Esto supone un volu- men medio de 81041operaciones telefónicas al día, por lo que es necesario un sistema capaz de mantener estabilidad, fiabilidad, disponibilidad, y que sea escalable, en caso de necesitar adaptar más centralitas al sistema.
1Dato calculado a partir de llamadas transcurridas en días laborables, comprendidas entre el 1 de noviembre de 2015 y el 1 de febrero de 2016
2
1.3. Descripción del problema
Todo ese volumen de operaciones telefónicas son gestionadas por un sistema VoIP, ya integrado y adaptado a las necesidades de habitissimo, llamadoAsterisk[9].
Asteriskes el sistema que utiliza habitissimo para procesar las llamadas, obtener infor- mación de ellas y almacenarlas en una base de datos, para su posterior tratamiento.
Debido al gran volumen de trabajadores que operan en el centro de llamadas, que en total suponen un 60 % de la empresa, habitissimo decide mantener un sistema web propio que ataca a las bases de datos que generaAsterisk, para monitorizar y maximizar, la eficiencia del servicio telefónico que está ofreciendo.
Este sistema web, que ofrece los datos obtenidos porAsterisk, es utilizado dia- riamente por los jefes de equipo del centro de llamadas, ya que les permite tomar decisiones según su rol. Los datos que pueden observar en las distintas secciones son: un listado de llamadas general (calls), que incluye todas las llamadas entrantes, salientes, transferidas o locales; una sección de informes (reports), que incluye un cómputo global de las llamadas, de distintos equipos o personas, durante unas fechas señaladas según unos parámetros de filtrado; una sección de usuarios (users) que corresponde al listado de trabajadores del centro de llamadas; y finalmente una sección de los teléfonos (phones) operativos.
Las secciones más transitadas de la web corresponden a las que ofrecen datos sobre las llamadas y su relación con los trabajadores de habitissimo, es decir, la sección de llamadas general y los distintos informes disponibles.
El problema surge cuando los jefes de equipo observan que la información pro- porcionada por la web no es fiable: hay incoherencias entre los informes, la cola de llamadas muestra situaciones imposibles en el listado de llamadas, algunos datos de las llamadas no son inteligibles ni razonables, etc. A este problema, además, se le aña- de que los tiempos de carga dificultan la navegación entre las secciones de la web, principalmente localizadas en los filtrados de llamadas y la carga de los informes.
Un ejemplo de esto se puede observar en la figura 3.2, en la que aparece una situa- ción imposible de llamada.
Este ejemplo de error es muy común en las llamadas del sistema inicial, al que hay que sumarle que el tiempo de carga para disponer de esa información es excesivo e inevitable, ya que los jefes de equipo no disponen de otra fuente de información. Toda esta problemática se traduce en inseguridad y falta de precisión por parte de los jefes de equipo a la hora de comunicar los resultados del trabajo de los empleados del centro de llamadas. Debido a esto, se inicia el proceso de reparación de este sistema web.
C
APÍTULO2
C ONTEXTUALIZACIÓN
2.1 Sistema inicial
2.1.1 Aplicación web
El sistema heredado consiste en una aplicación web desarrollada enPython[10], ha- ciendo uso del frameworkDjango[11]. El proyecto, está formado por 3 aplicaciones Djangollamadasapi,asteriskycdr, cada una de las cuales interacciona entre sí para dar soporte a toda la aplicación tal como se puede ver en la figura 2.1.
Una aplicación enDjangodefine un paquete dePythoncon una estructura común de ficheros, que provee algún conjunto de características y funcionalidades [12]. Las aplicacionesDjangoincluyen combinaciones entre modelos de datos, plantillas, vistas, URLs, etc, y pueden ser importadas en cualquier proyecto, ya sea definiéndolas en la configuración del proyecto o mediante algún otro mecanismo, como configuraciones en las URL o Middlewares.
La aplicaciónapiconsiste en la abstracción del modelo de datos que trabaja toda la aplicación. Tal como indica su nombre, su funcionalidad está limitada a funcionar como API, recibiendo peticiones de clientes y dando respuesta a dichas peticiones con información de base de la datos. Basada enDjango Rest Framework[13],apidefine la estructura y serialización de los datos que recibe de la base de datos, y una serie de funcionalidades para escuchar peticiones, procesarlas sobre la base de datos y dar respuesta a estas peticiones. Para comunicarse con la base de datos,apitiene 2 alter- nativas: operaciones mediante QuerySets deDjangoy consultasSQL. Las operaciones sobre base de datos que no requieran un procesamiento ni tratamiento posterior, re- caen sobre las QuerySets deDjango, mientras que para el tratamiento de datos de los informes, que contiene lógica de negocio, el proyecto dispone de una librería interna que contiene peticionesSQLgenéricas, en las cuales se definen los parámetros de filtrado dinámicamente en tiempo de ejecución.
2. CONTEXTUALIZACIÓN
La aplicaciónasteriskrepresenta la abstracción de la configuración del proyecto alojada en una aplicación deDjango. Su función principal es gestionar el entorno de desarrollo donde se trabaja, definir las rutas de la aplicación web y declarar la configu- ración del proyecto para todas las aplicaciones definiendo middlewares, variables de entorno, etc.
Figura 2.1: Estructura del sistema inicial
Finalmente, la aplicacióncdres la que contiene la implementación front-end de la web. En ella se declaran las plantillas, tablas, formularios y filtros que posteriormente declararán, manipularán y utilizarán los controladores web. Además, incluye un cliente API llamadoapi_callsque genera peticiones para atacar a la propia API, y así inter- actuar con los datos almacenados en la base de datos. Toda la estructura del sistema inicial puede observarse en la figura 2.1.
La interfaz gráfica del sistema web inicial se puede observar al final de este capítulo, 6
2.1. Sistema inicial
a partir de las figuras 2.4, 2.5, 2.6, 2.7, 2.8, 2.9 y 2.10.
2.1.2 Base de datos
El sistema web inicial dispone de una base de datos para mostrar información sobre las llamadas que transcurren por el centro de llamadas de habitissimo. La mayoría de esta información se recoge y se gestiona por el softwareAsterisk, explicado en el punto 2.3 de este documento. De hecho, la propia base de datos se llamaasterisky cuenta con un conjunto de tablas como las que se observa en la tabla 2.1.
Tabla 2.1: Tablas de la base de datos Tables_in_asterisk
cdr country
country_provider hab_answer_log hab_cdr
hab_cdr_new hab_log_new providers queue_log team_phone teams user_staff user_team users worktime
Las tablas principales de esta base de datos corresponden a las tablas con informa- ción recogida porAsterisk:cdryqueue_log. Estas tablas contienen la mayoría de la información mostrada en el sistema web inicial. La tablacdrcontiene información sobre la llamada: fechas de creación, contestación y fin, tipo de llamada, estado de la llamada, duración, país, etc. Mientras que la tablaqueue_logcontiene información relativa a los eventos generados en la estructura de colas y agentes por las que ha pasado cada llamada: fecha de evento, nombre de cola, agente, tipo de evento, etc.
Estas tablas son autogeneradas y autorellenadas con la información recopilada por el softwareAsterisk, a partir de la configuración realizada en el sistema, explicado con más profundidad en el punto 2.3.
De todas formasAsteriskalmacena información que en el caso de habitissimo no se ajusta al 100 % a sus necesidades. Es por ello que además de las tablascdryqueue_log existen otras dos tablas llamadashab_cdryhab_answer_log. Estas tablas resultan de un ajuste de la información recopilada porAsterisk, para adaptarla a las necesidades de habitissimo. La lógica funcional de estas tablas sigue siendo la misma que concdry
2. CONTEXTUALIZACIÓN
Tabla 2.2: Descripción de la tablahab_cdr
Field Type Null Key Default Extra
id varchar(32) NO
calldate timestamp YES NULL
start_stamp timestamp YES MUL NULL
end_stamp timestamp YES MUL NULL
country varchar(20) YES MUL NULL
caller_id varchar(80) NO MUL
source varchar(80) NO MUL
destination varchar(80) NO MUL direction varchar(80) NO MUL
duration int(11) NO MUL 0
disposition varchar(45) NO MUL
queue_agent text YES MUL NULL
Tabla 2.3: Descripción de la tablahab_answer_log
Field Type Null Key Default Extra
id int(11) NO PRI NULL auto_increment
time timestamp NO 0000-00-00 00:00:00
callid varchar(32) YES MUL NULL
agent varchar(32) YES NULL
queue varchar(1) YES NULL
event varchar(32) YES NULL
queue_log;hab_cdrcontiene información relativa a la llamada, yhab_answer_log contiene información relativa a los eventos de la cola de llamadas, pero de manera simplificada y personalizada para facilitar el procesamiento de la información en el sistema web. Uno de los aspectos principales de estas nuevas tablas es que disponen de un identificador único para cada registro. Ambas tablas pueden observarse en las tablas 2.2 y 2.3.
Estas tablas son rellenadas inicialmente mediante un sistema de triggers de base de datos [14]. Lo que realizan estos triggers es un volcado de información recibida encdr yqueue_logen las columnas definidas enhab_cdryhab_answer_loga medida que se van generando filas en las tablas rellenadas porAsterisk. Estos triggers, además de realizar un volcado de datos en las tablas personalizadas contienen lógica para añadir las columnasqueue_agentyqueueenhab_cdryhab_answer_logrespectivamente, que sirven para detectar en el sistema web, de manera sencilla, qué agente del centro de llamadas gestiona cada llamada.
Dentro del conjunto de las tablas de la base de datosasteriskexiste un grupo de 8
2.2. Servicios VoIP
tablas de soporte dirigidas a satisfacer los requerimientos del sistema web inicial. Por una parte destacamos las tablasteams,users,user_teamyteam_phone, las cuales están orientadas a la organización de llamadas por equipo o por agente en el apartado de informes de la aplicación web (reports), además de para mostrar un listado de agentes y teléfonos disponibles en los apartados webusersyphones. Por otra parte existen las tablascountries,country_provideryproviders, las cuales representan para cada país operativo los proveedoresVoIPdisponibles.
Además, en la tabla 2.1, se incluyen las tablashab_cdr_new,hab_log_newyworktime, las cuales provienen del proceso de desarrollo de este proyecto, que se explica en el punto 4 de este documento.
El esquema de la base de datos del sistema inicial puede verse representado en la figura 2.2.
Figura 2.2: Estructura inicial de la base de datos
2.2 Servicios VoIP
VoIPes el acrónimo de Voz Sobre IP (en inglés Voice Over Internet Protocol) [15], y bási- camente significa la transmisión de voz sobre Internet haciendo uso de sus respectivos protocolos.VoIPes conocido también como IP Telephony (IPT) al usar protocolos de Internet para hacer posible las comunicaciones, pero este término solo es correcto usarlo en el ámbito de una misma LAN. Cuando IPT traspasa de una LAN a una WAN o cualquier otra red, incluyendo distintas LANs, se transforma enVoIP.
Antes de existirVoIP, las comunicaciones telefónicas eran analógicas y estaban soportadas por Public Switched Telephone Network (PSTN) [16]. Se trata de la red telefónica clásica, en la que las estaciones telefónicas se comunican con una central de
2. CONTEXTUALIZACIÓN
conmutación a través de un solo canal compartido para generar una comunicación.
Concretando, este sistema consta de 4 elementos para su funcionamiento: estaciones telefónicas, la transmisión, el conmutador y la señalización. Un aspecto característico de PSTN es el conmutador. El medio de transmisión entre estaciones es el cableado, por lo que para conectar las líneas telefónicas PSTN se basa en la conmutación de circuitos para asignar canales de comunicación extremo a extremo. Por otra parte, en PSTN, las estaciones telefónicas necesitan transformar la voz a un formato adecuado para el medio de transmisión. Por ello, utilizan la modulación analógica para trans- formar el sonido en ondas electromagnéticas, que son volcadas sobre la línea telefónica.
ConVoIPse consigue que los servicios de la telefónica tradicional operen sobre redes informáticas usando la conmutación de paquetes. Mediante la conmutación de paquetes los sistemasVoIPdividen las señales sonoras en paquetes de información, que son enviados a través de Internet para establer una comunicación. Esto genera la posibilidad de transmitir más información para gestionar y mejorar las comunicaciones en comparación con la telefonía tradicional.
En las redes telefónicas conmutadas por circuito el enrutamiento de las llamadas es menos dinámico que en una red conmutada por paquete. Esto significa que si una línea está inoperativa las llamadas no pueden progresar. En cambio, en una red conmu- tada por paquete pueden establecerse múltiples rutas de comunicación por las cuales pueden navegar los paquetes. Si una ruta es desactivada, el paquete puede cambiar a otra ruta para mantener la llamada.
2.3 Asterisk
Asteriskes una plataforma de telefonía de código libre, que está diseñado principal- mente para funcionar sobre sistemas basados en Linux [1]. Este sistema combina más de 100 años de conocimiento en la telefonía en un robusto conjunto de aplicaciones de telecomunicaciones estrechamente integradas. La principal característica que define a Asteriskes su flexibilidad aplicativa, ya que es posible instalarlo de manera personali- zada para diferentes entornos, como es en el caso de habitissimo. El propio software incluye baterías básicas como el buzón de voz, conferencias, colas de llamadas, música de espera, pausa de llamadas, etc.
En la tecnología tradicional Private Branch Exchange (PBX) hay una diferencia de lógica entre estaciones telefónicas y las líneas telefónicas que conectan las estaciones con el mundo exterior. Esto significa, por ejemplo, que no es posible instalar una pa- sarela externa sobre una estación telefónica y dirigir las llamadas externas sobre la pasarela sin que los usuarios marquen primero el número de extensión. Además, el concepto de instalar un recurso externo sobre el tradicional PBX es más complicado de implementar, por el hecho de que el acceso por parte de los recursos externos a las ca- racterísticas internas del sistema, está abastecido solamente por algunos proveedores, los cuales limitan acceso a características y añaden la necesidad de instalar softwares de los proveedores.
10
2.3. Asterisk
Figura 2.3: Arquitectura tradicional PBX vs.Asterisk[1]
Por otro lado,Asteriskno contempla una definición interna de estación telefónica o línea telefónica. EnAsterisk, todo el tráfico que navega por el sistema pasa por un canal de cualquier tipo.Asteriskofrece diversos tipos de canales, sin embargo, el plan de ejecución deAsterisk, comúnmente llamadodialplan, gestiona todos los canales de una manera similar, lo que significa que un usuario interno sería tratado de la misma forma que una línea telefónica externa. La figura 2.3 ilustra la diferencia entre las 2 arquitecturas [1].
Otra característica del software deAsteriskes la modularidad de aplicación.Asterisk está construido sobre módulos, cada uno de los cuales se pueden cargar en el sistema para otorgar una funcionalidad específica. Los distintos módulos se organizan en las siguientes familias de módulos: Aplicaciones, Módulos puente, Módulos de grabado de llamadas, Loggers de canales, Conductores de canal, Codificadores, Intérpretes de formato, Funciones del plan de ejecución, Módulos PBX, Módulos de recursos externos, Módulos de la comunidad y Módulos de testeo. Todos ellos forman el conjunto de módulos aplicativos que ofreceAsteriskpara disponer de un sistemaVoIP.
Otro aspecto principal enAsteriskes el ya nombrado plan de ejecución (en adelante dialplan). El dialplan es el corazón deAsterisk. Todo canal que llega al sistema es enviado al dialplan, donde se haya el script del control de flujo, al que se somete cada llamada entrante o saliente para ser gestionada [1, 17]. Este script de configuración es personalizable y requiere una sintaxis propia deAsteriskque puede ser consultada en la documentación [18], pero a su vez admite 2 variantes para ser escrito: Asterisk Exten- sion Logic (AEL) yLua. Este hecho provoca otra diferencia con la telefonía tradicional, al no compartir la versatilidad de programación deldialplan.
El aspecto que más relacionaAsteriskcon este proyecto es su mecanismo para
2. CONTEXTUALIZACIÓN
guardar información en una base de datos. Internamente,Asteriskdispone de varios módulos y características de integración de la información que procesa en bases de datos relacionales, entre las cuales destacaMySQL,PostgreSQLyMicrosoft SQL. Para llevar a cabo estas funcionesAsteriskse basa en Open DataBase Connectivity (ODBC).
El conector ODBC se trata de una capa de abstracción que facilita aAsteriskla tarea de comunicación con las bases de datos evitando así el mantenimiento de conectores para cada base de datos. Es una herramienta que ahorra tiempo de desarrollo a cambio de un leve coste de eficiencia, al estar añadiendo una capa intermedia entreAsterisky la base de datos. De todas formas, esta pérdida de eficiencia puede ser mitigada con una configuración del ODBC adecuada y sale a cuenta al necesitar funciones potentes de base de datos en un sistemaAsterisk. El ODBC unido a varias funciones del dialplan deAsteriskpermite realizar un volcado de los datos que transcurren por el dialplan en bases de datos. En el caso de habitissimo, se almacenan las llamadas y la estructura de colas por las que ha pasado cada llamada en cualquier país operativo de habitissimo. Al primer proceso de guardado de llamadas,Asterisklo define Call Detail Records (CDR) y el guardado de información de colas se define como Queue Log.
El CDR es un módulo que contiene información sobre las llamadas que pasan por el sistemaAsterisky que permite almacenarlas en una base de datos. El guardado de llamadas mediante CDR es un método comúnmente utilizado en los sistemasAste- riskdebido a su facilidad de gestión y las posibilidades que ofrece para almacenar la información en base de datos. Este módulo permite elegir qué columnas provistas porAsteriskson almacenadas en la base de datos y a su vez permite añadir columnas adicionales mediante la programación del dialplan. Las columnas por defecto que ofreceAsteriskpueden observarse en las tablas 2.4 y 2.5 [3].
Mediante el módulo CDR,Asteriskguarda la información que procesa de las llama- das en base de datos. Esta información puede ser truncada en distintas tablas o incluso en distintas bases de datos, lo cual no es el caso de habitissimo, que en este aspecto mantiene la estructura por defecto deAsterisky guarda la información en la tablacdr, comentada en el punto 2.1.2 de este documento.
Por otra parte, el módulo Queue Log se basa en Automatic Call Distribution (ACD).
ACD provee una forma de poner en cola llamadas entrantes de un grupo de usuarios:
agrega múltiples llamadas en espera, asigna a cada llamada una valoración y determina en qué orden debe ser repartida una llamada hasta el agente final (normalmente se sigue un patrón primero en entrar, primero en salir). Así, cuando un agente vuelve a estar disponible, la llamada en espera con más valor es enviada al agente y las demás llamadas aumentan de valoración. El módulo Queue Log es el que se encarga de almacenar toda la información procesada por el ACD. Este contiene información sobre la colas y alguna información sobre las llamadas. Toda esta información se almacena finalmente en la tablaqueue_log, ya comentada en el punto 2.1.2 de este documento.
12
2.3. Asterisk
Tabla 2.4: Campos por defecto en CDR [3]
Option Value/Example Notes
accountcode 12345 Un ID de cuenta. Este campo está de- finido por el usuario y está vacio por defecto.
src 12565551212 Número de identificación del emisor.
Se almacena automáticamente y es so- lo de lectura.
dst 102 La extensión destinataria para la lla- mada. Se almacena automáticamente y es solo de lectura.
dcontext PublicExtensions El contexto de destino para la llama- da. Se almacena automáticamente y es solo de lectura.
clid Juan
<12565551212>
Número de identificación completo del emisor, incluyendo nombre. Se al- macena automáticamente y es solo de lectura.
channel SIP/0004F2040808- a1bc23ef
El canal del emisor. Se almacena auto- máticamente y es solo de lectura.
dstchannel SIP/0004F2046969- 9786b0b0
El canal del receptor. Se almacena au- tomáticamente y es solo de lectura.
lastapp Dial Última aplicación ejecutada en el dial- plan. Se almacena automáticamente y es solo de lectura.
lastdata SIP/0004F2046969, 30, tT
Argumentos pasados a lastapp. Se al- macena automáticamente y es solo de lectura.
start 2010-10-26
12:00:00
Inicio de la llamada. Se almacena au- tomáticamente y es solo de lectura.
answer 2010-10-26 12:00:15
Inicio de la comunicación entre emi- sor y destinatario. Se almacena auto- máticamente y es solo de lectura.
end 2010-10-26
12:03:15
Final de la llamada. Se almacena au- tomáticamente y es solo de lectura.
duration 195 Número de segundos entre los cam- pos start y end de la llamada. Se alma- cena automáticamente y es solo de lectura.
billsec 180 Número de segundos entre los cam- pos answer y end times de la llama- da. Se almacena automáticamente y es solo de lectura.
2. CONTEXTUALIZACIÓN
Tabla 2.5: Continuación de la tabla 2.4 Option Value/Example Notes
disposition ANSWERED Un indicador de estado de la llamada. Este pue- de ser NO ANSWER, FAILED, BUSY, ANSWERED, o UNKNOWN.
amaflags DOCUMENTATION El indicador de Contabilización Automática de Mensajes (del inglés Automatic Message Ac- counting) de la llamada. Este puede ser uno de los siguientes: OMIT, BILLING, DOCUMENTA- TION, o Unknown.
userfield* PerMinuteCharge:0.02 Un campo de usuario de uso general. Este cam- po está vacío de forma predeterminada y se puede establecer en una cadena definida por el usuario.
uniqueid 1288112400.1 El unique ID para el canal src. Se almacena au- tomáticamente y es solo de lectura.
* El campo userfield actualmente no es tan relevante como solia ser. Las variables CDR personalizadas ofrecen una forma más flexible de almacenar datos personalizados.
Figura 2.4: Sistema web inicial - Inicio
14
2.3. Asterisk
Figura 2.5: Sistema web inicial - Apartado de llamadas
2. CONTEXTUALIZACIÓN
Figura 2.6: Sistema web inicial - Apartado de informes - General
16
2.3. Asterisk
Figura 2.7: Sistema web inicial - Apartado de informes - Entrantes
2. CONTEXTUALIZACIÓN
Figura 2.8: Sistema web inicial - Apartado de informes - Franja horaria
18
2.3. Asterisk
Figura 2.9: Sistema web inicial - Apartado de usuarios
2. CONTEXTUALIZACIÓN
Figura 2.10: Sistema web inicial - Apartado de teléfonos
20
C
APÍTULO3
A SPECTOS PREVIOS AL DESARROLLO
3.1 Equipo de trabajo
3.1.1 Estructura y roles
El equipo involucrado en la consecución de este proyecto comprende personas con distintos roles dentro de habitissimo. Para empezar, el máximo exponente de este sistema web lo comprenden la Chief de Producto Interno Marta Mayol y el CTO Jordi Llull Chavarría por parte de tecnología. Su grado de implicación en el proyecto incluye decisiones sobre los requerimientos o soporte para lo consecución de los mismos.
Con un grado menor de responsabilidad sobre el proyecto incluimos también a los jefes de equipo de cada país, que utilizan el sistema web a diario. Esta parte implicada también aporta información sobre los requisitos del sistema, en un grado menor que el anterior escalafón, y sobre cómo se utiliza el sistema en su día a día.
Por último incluimos el equipo de desarrollo del proyecto en sí, ya mencionado en el apartado 1.1. Este equipo está comprendido por los técnicos José Mañas Picó y Jaume Jiménez Forteza y liderado por el CTO Jordi Llull Chavarría.
Los técnicos son responsables de aportar soluciones a nivel tecnológico y llevarlas a cabo para solucionar el problema global del proyecto. Estos se encargan de planificar, desarrollar y testear los requerimientos del proyecto. Por otra parte, el CTO aporta en este proyecto información sobre los requerimientos a nivel técnico y decide en última instancia la implementación planificada por los técnicos.
3.1.2 Herramientas de trabajo
Para este proyecto se utilizan varias herramientas de trabajo para satisfacer necesidades básicas, además de algunas aplicaciones que cubren las necesidades técnicas.
El aspecto de la comunicación entre trabajadores se cubre mediante comunicación
3. ASPECTOS PREVIOS AL DESARROLLO
oral,Google Hangoutsy la aplicaciónSlack. La utilización de una aplicación informática u otra depende del rol correspondiente a la persona con la que nos comunicamos. Así pues, normalmente utilizaremosGoogle Hangoutspara comunicarnos con trabajadores con perfiles no técnicos (la Chief Marta Mayol y jefes de equipo del centro de llamadas), yslackpara comunicaciones entre el equipo técnico.
La parte de gestión y dirección del proyecto y su equipo está centralizada en la apli- caciónRedmine.Redminees una aplicación web para la gestión de proyectos. Entre los servicios que ofrece esta aplicación destacan la gestión múltiple de proyectos, acceso flexible basado en roles, seguimiento flexible de tickets, diagramas de seguimiento, ca- lendario, etc. Mediante esta aplicación se desglosan los problemas técnicos del sistema web en tickets de desarrollo estimables, que son agrupados dentro del proyecto que nos abarca. Además es utilizado para realizar una planificación previa al desarrollo del proyecto para definir los requerimientos, posibles soluciones, pruebas y validaciones a realizar en cada ticket de desarrollo.
En la parte técnica, se utiliza el control de versionesgitpara la coordinación del desarrollo entre la parte técnica implicada en el proyecto. La política con la que se usa giten este proyecto es partir de una rama base en el momento inicial del desarrollo, y a partir de esa rama crear una rama por ticket de desarrollo establecido enRedmine. Una vez se acaba el proceso de desarrollo y testeo de cada ticket, se integra la rama corres- pondiente en la rama base principal del proyecto para mantener la implementación actualizada a la última versión.
El entorno de desarrollo es de libre selección para cada técnico, pero se da el caso de coincidencia en la utilización del editorAtomcomplementado conVim.
3.1.3 Metodología
Siguiendo con la estructura organizativa del trabajo en habitissimo, se decide que este proyecto se gestione a partir de metodologías ágiles, en concreto mediante la meto- dologíaScrum.Scrumes una doctrina de desarrollo ágil para proyectos que se basa principalmente en realizar tareas estimables de un proyecto en ciclos repetitivos de entre 2 y 4 semanas, también llamadossprints[2, 19].
La imagen 3.1 ilustra el proceso de desarrollo de un par de tareas mediante las fases que comprendeScrum. Para que este proceso sea posible, es necesaria la figura del cliente, que adquiere el rol de representante de todas las personas interesadas en los resultados. Esta entidad compone los objetivos y requerimientos iniciales y es respon- sable de dirigir los resultados del proyecto maximizando la eficiencia. En nuestro caso, a partir de las personas implicadas en el proyecto comentadas en el punto 3.1.1, esta figura corresponde a la Chief Marta Mayol.
A partir de los objetivos definidos por el cliente, estos se desglosan en tareas es- timables en la primera fase del sprint: la planificación. Esta fase corresponde a la preparación de un plan de trabajo sobre las tareas a desarrollar durante el ciclo, que será utilizado como soporte en las siguientes fases. Una vez acabada la planificación si- 22
3.2. Planteamiento inicial del problema
Figura 3.1: Ciclo individual del Scrum [2]
gue la fase de desarrollo. Durante esta fase el equipo se reúne una vez al día, en nuestro caso cada mañana antes de empezar la jornada, con el objetivo de comentar aspectos sobre el desarrollo que se van produciendo. A lo largo del camino de desarrollo, el cliente mantiene al equipo focalizado con los objetivos y se encarga de eliminar posi- bles impedimentos producidos durante el desarrollo. Una vez terminado el desarrollo es necesario disponer de un producto entregable para entrar en las últimas fase: la revisión y retrospectiva del sprint. En esta recta final del ciclo se reúne de nuevo al equipo para analizar el producto desarrollado y comentar aspectos relacionados con el transcurso del sprint, para que un futuro se mejore la eficiencia de los ciclos.
3.2 Planteamiento inicial del problema
Uno de los principales problemas que nos encontramos a la hora de iniciar el proyecto, es el entorno inicial. Un sistema grande que lleva tiempo sin mantener y que falla por razones inicialmente desconocidas. El primer paso para empezar a desarrollar una solución es sentarse y estudiar el ecosistema donde se va a trabajar. Para empezar, se decide hacer una lectura de la tecnología del proyecto, analizar el código en su estado original y entender como interactúan los elementos del Framework deDjango. Por ello, dedicamos unos días para familiarizarse con el entorno dePython,Djangoy todos sus complementos usados en la aplicación:API Rest,Django Tables,Django Forms,Django Templates, etc.
A continuación, sigue el estudio de la aplicación en sí: cómo está programada la web, el sistema de aplicaciones que ataca, el propioAsterisky sus configuraciones y finalmente la estructura de la base de datos. El método utilizado para analizar el sistema se definirá como un estudio transversal. No se tratarán las distintas partes
3. ASPECTOS PREVIOS AL DESARROLLO
independientemente sino que se estudiarán las interrelaciones conjuntamente, con el fin de descubrir donde se pierde o se corrompe la información. Como resultados del estudio de la aplicación, navegando por la web, se descubre que hay una serie de patrones repetitivos de error en las llamadas de la aplicación que, tras analizarlos en el entorno de la base de datos, se demuestra que los datos no se están guardando según lo esperado, razón por la que la información acaba mostrándose erróneamente en la web. Un ejemplo de este hecho puede observarse en la figura 3.2, donde se muestran 2 llamadas las cuales tienen la misma fecha de creación y han sido contestadas, teórica- mente, por los mismos agentes.
Figura 3.2: Patrón de llamada errónea
Una vez identificado el problema y estudiada la estructura de la base de datos, decidimos que el primer objetivo es, necesariamente, centrar nuestros esfuerzos en reparar la estructura de la base de datos, antes de llevar a cabo implementaciones o mejoras sobre la web.
3.3 Soluciones propuestas
Según el objetivo inicial, marcado en el punto anterior de este documento, y la es- tructura original de la base de datos, explicada en el punto 2.1.2 de este documento, identificamos 2 posibles soluciones para reparar la información de la base de datos.
La primera solución consiste en abordar los ficheros de configuración deAsterisk instalados en habitissimo. Como se ha explicado en la sección 2.3, entre estos ficheros se encuentra eldialplan[17], que define el plan de control y ejecución para todas las operaciones, entre las cuales destacan la gestión del flujo y el enrutamiento de las lla- madas, y la estructura de colas por las que se redirigen las llamadas según localización, disponibilidad y horario. Todas estas operaciones están definidas y personalizadas según la lógica de empresa referida al sistema del centro de llamadas y son las responsa- bles de realizar el almacenamiento de las llamadas en la base de datos del sistema web, explicada en la sección 2.1.2. Esta solución tiene la ventaja que ataca el fallo de raíz, es decir sobre la capa más básica del proyecto que está relacionada con los problemas de la página web.
La segunda solución consiste en incorporar una capa de aplicación adicional situa- da entreAsterisky la aplicación web, que lea periódicamente las llamadas de la base de datos y las guarde en otra tabla correctamente, solo con la información necesaria y adaptada al proyecto actual. Esta solución incluye el requerimiento de mantener la eficiencia del sistema, de manera que no se sature el servidor durante el procesamiento 24
3.3. Soluciones propuestas
de las llamadas, ni la base de datos durante las operaciones de lectura de datos, ya queAsteriskrealiza operaciones en cada llamada procesada. Asimismo, esta segunda solución ofrece la ventaja de poder ser implementada con la misma tecnología que el proyecto, pudiendo integrar la implementación de la solución sobre el proyecto web ya existente. Además, el hecho de remodelar la estructura de la base de datos creando tablas nuevas, ofrece la posibilidad de refactorizar las consultas existentes a la base de datos, para así maximizar la eficiencia e implícitamente reducir los tiempos de carga del sistema.
La implementación a realizar elegida es la segunda solución. Se decide que se va a remodelar la estructura de la base de datos creando nuevas tablas y modificando algunas ya existentes y finalmente se va a adaptar el proyecto web existente a la nueva estructura de base de datos con información fiable y bien estructurada. El problema y la razón por la que se aplica la segunda solución, es porque la configuración del proyecto deAsteriskestá muy personalizada para habitissimo, contiene lógica de negocio, los cambios son difíciles de testear y principalmente por el factor temporal. Habitissimo es una empresa, y como tal el tiempo es un activo valioso, por lo que para maximizar la eficiencia de este proceso sugiere que la segunda solución es una solución válida, y con menor dificultad. De este modo, se elimina el sistema de triggers inicial para volcar la información deAsterisksobre tablas personalizadas de habitissimo, por la aplicación que se implementará como solución. Este cambio actualiza la estructura a nivel de base de datos del sistema web inicial, mostrada en la figura 2.1, por la estructura que puede observarse en la figura 3.3.
Así pues, el objetivo final de este proyecto es remodelar la estructura de la base de datos, hacer un script que procese la información recibida deAsterisky la almacene correctamente en la nueva estructura de base de datos definida, adaptar la nueva estructura de datos al proyecto web existente y realizar nuevas implementaciones que satisfagan las necesidades de los jefes de equipo que utilizan este sistema web.
3. ASPECTOS PREVIOS AL DESARROLLO
Figura 3.3: Estructura final del sistema web
26
C
APÍTULO4
D ESARROLLO DEL PROYECTO
4.1 Estructura del desarrollo
Haciendo un repaso de los objetivos a realizar, definidos por la solución explicada en el punto 3.3 de este documento, conseguimos desglosar el objetivo final en los siguientes subobjetivos más pequeños:
1. Cambiar la estructura de la base de datos (Sección 4.2).
2. Crear aplicación que procese las tablas definidas porAsterisky exporte sus datos una vez limpiados a la nueva estructura definida en el subobjetivo 1 (Sección 4.3).
3. Adaptar el nuevo modelo de datos al proyecto web existente (Sección 4.5).
4. Realizar implementaciones nuevas según tickets de desarrollo definidos por los jefes de equipo (Sección 4.6).
Estos subobjetivos definen la línea temporal del desarrollo de este proyecto. A lo largo de los siguientes apartados se explicarán los principales aspectos de cada subobjetivo siguiendo la línea temporal, es decir, en orden creciente de subobjetivo.
4.2 Estructura de la nueva base de datos
El primer paso para solucionar el problema es modificar la estructura de la base de datos, con el fin de establecer una nueva base sólida y estable que provea información fiable y facilite la implementación web posterior.
Las tablas que principalmente se verán afectadas a este proceso de remodelación soncdryqueue_log, explicadas en el punto 2.1.2.
4. DESARROLLO DEL PROYECTO
El primer aspecto a modificar en estas tablas es el hecho de no tener clave primaria definida. Si bien es cierto que las tablascdryqueue_logtienen definida una columna llamadauniqueid, cuyos valores representan el Unix Timestamp [20] del momento de creación de la llamada, este campo no se corresponde a una clave primaria, ya que, además de no estar reflejado como tal en la base de datos, observamos que hay llamadas relacionadas entre sí que contienen el mismo valor para esta columna, como por ejemplo las transferencias.
Este hecho provoca dificultades a la hora de identificar llamadas por algún campo único, por lo que a cada tabla se le añade una columna identificadora para cada registro, mediante el código que se puede observar en el código 4.1.
Código 4.1: Claves primarias para las tablascdryqueue_log
# MySQL:
ALTER TABLE cdr
ADD COLUMN id INT NOT NULL AUTO_INCREMENT PRIMARY KEY;
ALTER TABLE queue_log
ADD COLUMN id INT NOT NULL AUTO_INCREMENT PRIMARY KEY;
El siguiente paso, que servirá como base para el siguiente subobjetivo, será crear 2 nuevas tablas de base de datos. Estas tablas definirán la simplificación de los datos contenidos encdryqueue_log, y es donde se almacenará la información filtrada, reparada y personalizada de dichas tablascdryqueue_log. Las tablas surgirían del mismo concepto que las tablashab_cdryhab_answer_log, pero se decide deprecar estas tablas y utilizar otras desde cero.
La primera de ellas, bautizada con el nombre dehab_cdr_new, define una herencia con la tablacdr. Esta tabla nueva tiene la misma funcionalidad quecdrde cara a la aplicación, ya que contiene la información relativa a cada llamada proveniente decdr. La particularidad de esta tabla es que la información que reciba será almacenada una vez sea filtrada y reparada por la aplicación que se explica en el punto 4.3 de este docu- mento. Además, esta tabla nueva contiene algunos rasgos propios como las columnas queue_agent,billsec,is_office_closedypattern.
La columnaqueue_agentdefine un conjunto de agentes por los que ha pasado la llamada hasta finalizar.Billseces una columna decdrque no estaba en uso en la anterior tablahab_cdry la recuperamos para disponer del tiempo efectivo de cada llamada, es decir excluyendo el tiempo de espera. La columnapatterncorresponde al patrón de llamada resultante del filtrado al que se someterá cada llamada antes de ex- portarse ahab_cdr_new. Finalmente, la columnais_office_closedsurge como un nuevo requerimiento de la aplicación, por lo que será explicado con más detenimiento en el punto 4.6 de este documento. El resultado de esta abstracción puede observarse en el código 4.2.
28
4.2. Estructura de la nueva base de datos
Código 4.2: Abstracción decdrcon nueva tabla
# MySQL:
CREATE TABLE hab_cdr_new (
id i n t NOT NULL PRIMARY KEY AUTO_INCREMENT, c a l l i d varchar( 3 2 ) ,
c a l l d a t e timestamp default 0 , start_stamp timestamp,
end_stamp timestamp, country varchar( 2 0 ) , c a l l e r _ i d varchar( 8 0 ) , source varchar( 8 0 ) , destina ti on varchar( 8 0 ) , d i r e c t i o n varchar( 8 0 ) , duration i n t( 1 1 ) , b i l l s e c i n t( 1 1 ) ,
d i s p o s i t i o n varchar( 4 5 ) , queue_agent varchar( 2 5 5 ) , pattern i n t( 1 1 ) ,
i s _ o f f i c e _ c l o s e d t i n y i n t ( 1 ) , cdr_fk i n t( 1 1 ) UNIQUE NOT NULL,
FOREIGN KEY ( cdr_fk ) REFERENCES cdr ( id ) ) ;
La segunda tabla corresponde a los logs de cada llamada. Se define comohab_log_new, y las variaciones que sufre son cambios en las relaciones foráneas de base de datos entre los logs y las llamadas. Anteriormente la relación entre una llamada y sus logs estaba definida por el campouniqueiddecdr, que como se ha explicado no define un campo único. Por ello, se crean relaciones foráneas a partir de los identificadores añadi- dos a las tablascdr(cdr.id-hab_log_new.cdr_fk) yqueue_log(queue_log.id- hab_log_new.queue_log_fk). El resultado de esta abstracción puede observarse en el código 4.3.
4. DESARROLLO DEL PROYECTO
Código 4.3: Abstracción dequeue_logcon nueva tabla
# MySQL:
CREATE TABLE hab_log_new (
id i n t NOT NULL PRIMARY KEY AUTO_INCREMENT, cdr_fk i n t( 1 1 ) NOT NULL,
queue_log_fk i n t( 1 1 ) UNIQUE, agent varchar( 3 2 ) ,
event varchar( 3 2 ) , c a l l t i m e timestamp,
FOREIGN KEY ( cdr_fk ) REFERENCES cdr ( id ) ,
FOREIGN KEY ( queue_log_fk ) REFERENCES queue_log ( id ) ) ;
Si recordamos los requerimientos iniciales de esta solución, uno de los aspectos que hay que tener en cuenta para justificar este desarrollo es el mantenimiento de la eficiencia. Por ello, para agilizar las consultas que se realizarán en la web una vez terminado el desarrollo, el último paso para acabar de reestructurar la base de datos es añadir una serie de índices de base de datos [21], en las columnas que sufran una carga mayor. Este cambio se puede visualizar en el código 4.4
Código 4.4: Creación de índices sobre las tablas generadas
# MySQL:
CREATE INDEX import_cdr ON cdr ( import_cdr ) ; CREATE INDEX agent ON hab_log_new ( agent ) ;
CREATE INDEX c a l l d a t e ON hab_cdr_new ( c a l l d a t e ) ; CREATE INDEX source ON hab_cdr_new ( source ) ;
CREATE INDEX de st ination ON hab_cdr_new ( de stina tio n ) ; CREATE INDEX d i r e c t i o n ON hab_cdr_new ( d i r e c t i o n ) ; CREATE INDEX teams ON teams (name ) ;
4.3 Estructura del desarrollo de la aplicación cron_script
Una vez decidido el objetivo de reparar la estructura de la base datos y decidido el procedimiento que lo va a llevar a cabo, empezamos con el desarrollo de la aplicación que limpia la información y la almacena correctamente en las nuevas tablas generadas.
El procedimiento que se quiere conseguir es un procesamiento periódico que lea el conjunto de llamadas y sus logs no importadas de las tablascdryqueue_log, las filtre y catalogue según sus características, las repare en caso de contener algún error y finalmente las almacene en las nuevas tablas de la base de datos.
30
4.3. Estructura del desarrollo de la aplicación cron_script
Tabla 4.1: Estructura de ficheros decron_script cron_script
call_dict_keys.py call_log_notifier.py call_type.py
cron_hab_tables.py filters.py
__init__.py repairs.py save.py
Para ello, generamos una aplicación enPythonllamadacron_script, que operará con una estructura de ficheros funcionales como se ve en la tabla 4.1.
El fichero principal es el llamadocron_hab_tables.py. En él se define toda la estructura del procedimiento a la que se someterá cualquier llamada no importada a las nuevas tablas de base de datos y mediante que estructuras se va a llevar a cabo. Para identificar este tipo de llamadas no importadas existe un campo en la tablacdrcon el nombreimport_cdr, que identifica el estado de importación de cada llamada (0 para llamadas todavía no importadas, 1 para llamadas importadas correctamente y 2 para llamadas que no se han podido importar debido a errores durante el proceso).
Así pues, el proceso de la aplicación empieza por recoger llamadas decdrque toda- vía no han sido importadas a la nueva tabla de base de datoshab_cdr_new. Estas serán almacenadas en una estructura de datos que llamaremosnew_calls, que consiste en una lista de diccionarios (cada llamada corresponde a un diccionario dePython). Una vez se dispone de todas las llamadas a tratar, empieza el procesamiento iterativo de las llamadas.
Antes de realizar los procedimientos de filtrado, reparación y guardado de cada llamada individualmente, se genera otra estructura de datos de soporte, que almacena para cada llamada sus relaciones con otras llamadas (si existieran). Un ejemplo de esto serían las transferencias, en las que cada llamada proviene de otra. El uso que le damos a esta estructura es que mediante estas relaciones se puede obtener información para encontrar los diversos patrones de error que contienen las llamadas y además, para repararlas.
Para crear dicha estructura de datos, se utilizan estructuras proporcionadas por Python; los diccionarios y las listas, combinándose entre sí. Esta estructura se llama copy_callsy consiste en un diccionario de listas de diccionarios. Cada llamada está representada mediante un diccionario, por lo que a efectos reales esta estructura defi- niría un grupo de llamadas que comparten una relación almacenadas en una lista, la cual estaría identificada por el identificador de llamada, el campouniqueid(a partir de ahoracallid) de las llamadas. Los logs de aquellas llamadas a tratar también van a
4. DESARROLLO DEL PROYECTO
formar una estructura de datos con la misma base quecopy_calls.
Figura 4.1: Estructura de datos copy_calls
Un ejemplo gráfico de esta estructura se puede observar en la figura 4.1
Una vez terminado el proceso de preparación de los datos, se procede al filtrado de las llamadas, definido en el ficherofilters.py. El objetivo de este fichero es catalogar cada llamada que recibe con un patrón, es decir, identificar posibles errores y etiquetar la llamada con un código de patrón para identificarla en los siguientes procesos de la aplicación.
Los códigos de los patrones y los atributos de las llamadas están definidos en dos ficheros auxiliares decron_script, los cuales no ofrecen funcionalidad pero sirven de soporte:call_type.pyycall_dict_keys.py. El primero contiene una clase con los códigos de patrones y una pequeña documentación que explica que características que tienen los patrones identificados. El segundo es un archivo declarativo de constantes para mantener un código limpio. Se utiliza para definir y acceder a los campos de las estructuras de datos, evitando así un código Hard Code.
En el archivofilters.pyse define un proceso iterativo para todas las llamadas que recibe, en el cual para cada llamada se aplicará un conjunto de comprobaciones que determinará si la llamada contiene algún campo incorrecto y será catalogada con un patrón de llamada. Cabe destacar que una llamada no será sometida a todas las comprobaciones relativas a todos los patrones existentes, ya que los patrones de error se reparten según la dirección de la llamada (entrante, saliente, local o transferencia).
Cada dirección, contiene una serie de patrones distintos, por lo que se realizan com- probaciones diferentes, a excepción de las transferencias, que durante este proceso serán consideradas llamadas entrantes.
Como se ha explicado, cada llamada se cataloga según los patrones relacionados con la dirección de la llamada. A partir de la distinción por dirección, se realiza una 32
4.3. Estructura del desarrollo de la aplicación cron_script
Tabla 4.2: Ejemplo de patrón erróneo de llamada Q.Q.D
id Calldate answer end Calltype
4821521 2015-11-17 13:47:25 2015-11-17 13:47:40 2015-11-17 13:48:36 incoming 4821586 2015-11-17 13:48:36 2015-11-17 13:48:44 2015-11-17 13:52:14 incoming 4821645 2015-11-17 13:48:36 2015-11-17 13:48:44 2015-11-17 13:58:00 incoming
Tabla 4.3: Continuación de la tabla 4.2 id lastapp duration billsec uniqueid
4821521 Queue 71 56 1447764445.25273
4821586 Queue 218 210 1447764445.25273
4821645 Transferred Call 564 556 1447764445.25273
serie de comprobaciones (organizadas en subrutinas) entre los datos de las llamadas y las estructuras de soporte generadas encron_hab_tables, que proveen informa- ción necesaria para realizar las comprobaciones. En caso de que se cumplan todas las condiciones de un patrón se añade el código de patrón a la llamada para su posterior tratamiento. En caso contrario, se le define un patrón estándar para identificar que no ha sido posible encontrar coincidencias con los patrones establecidos.
Un aspecto a considerar de este proceso es que toda llamada acabe catalogada con algún patrón establecido, lo que significará que ha sido identificada por sus ca- racterísticas y se puede reparar, en caso de que fuera errónea. Por eso, un objetivo de el proceso de filtrado es reducir al máximo el porcentaje de llamadas no catalogadas.
Por otra parte, aquellas llamadas que no han sido catalogadas no están perdidas, el sistema se encargará de que en un futuro puedan ser catalogadas y reparadas, cosa que se explicará más adelante en el proceso final del proyectocron_script.
En las tablas 4.2 y 4.3 podemos observar un ejemplo de un patrón de llamada erró- nea. En este caso, representa un patrón que lo hemos llamado Q.Q.D debido al flujo que sigue la llamada: Inicialmente entra en cola (Queue), posteriormente el agente que ha contestado la llamada la vuelve a poner en la cola (Queue) y finalmente el segundo agente la transfiere directamente a otro agente en concreto (Direct). Si observamos los tiempos de contestación de la tercera llamada (id=4821645), veremos que son iguales a los de la segunda llamada, por lo se está almacenado información de la segunda llamada en la tercera, provocando implícitamente un error en los datosbilltimey durationde la última llamada. Este tipo de errores son lo que se detectan en el fichero filters.py. En este caso, la última llamada será catalogada con un patrón de error identificativo para preparar su futura reparación.
Una vez termina el proceso de filtrado se dispone de la misma estructura de lla- madas a procesar, una lista de diccionarios, con el añadido de tener guardado el iden- tificador de patrón resultante del filtrado. Esta información va a ser de ayuda para el
4. DESARROLLO DEL PROYECTO
Tabla 4.4: Reparación del patrón erróneo de llamada Q.Q.D
id Calldate answer end Calltype
4821521 2015-11-17 13:47:25 2015-11-17 13:47:40 2015-11-17 13:48:36 incoming 4821586 2015-11-17 13:48:36 2015-11-17 13:48:44 2015-11-17 13:52:14 incoming 4821645 2015-11-17 13:52:14 2015-11-17 13:52:15 2015-11-17 13:58:00 transfer
Tabla 4.5: Continuación de la tabla 4.4 id lastapp duration billsec uniqueid
4821521 Queue 71 56 1447764445.25273
4821586 Queue 218 210 1447764445.25273
4821645 Transferred Call 345 344 1447764445.25273
siguiente proceso del proyecto, la reparación de los campos erróneos de las llamadas.
Este proceso de reparación se realiza en el ficherorepairs.py, el cual sigue con una estructura de operación iterativa para cada llamada. En este fichero se realizan una serie de modificaciones sobre las estructuras de datos que almacenan en tiempo de ejecución la información de la llamada y sus logs, según el parámetro de patrón asignado durante el proceso de filtrado. Para ello, dispone de un conjunto de subrutinas que, a partir de las estructuras de datos formadas encron_hab_tables.py, modifi- can aquellos campos mal formados o con información no válida. Como resultado de este proceso se obtiene una estructuranew_callsmodificada, ya con información correcta y lista para guardarse en las nuevas tablas de base de datoshab_cdr_newy hab_log_new.
En las tablas 4.4 y 4.5, podemos ver las modificaciones que se llevarían a cabo durante el proceso de reparación de una llamada Q.Q.D. En este punto, a partir de las estructuras de datos formadas encron_hab_tables.py, la aplicación dispone de información suficiente para modificar los campos erróneos que sigue este patrón, por lo que son modificados y preparados para importarse a las nuevas tablas de la base de datos.
Llegados a este punto, el último procedimiento para disponer de información fiable en base de datos, consiste en importar las estructuras de datos generadas y modificadas convenientemente, y finalmente marcar las llamadas como ya procesadas e importadas.
El proceso de guardado se realiza en el ficherosave.py, donde se forma una query SQL de inserción con todos los datos de las llamadas y otra de la misma forma para los logs.
Finalmente, el último proceso es actualizar el estado de importación de las llamadas.
34