Lo último que quiere una empresa es ser conocida como un servicio poco confiable y de bajo rendimiento, especialmente si existen soluciones similares a unos pocos clics de distancia. Por lo tanto, conocer el rendimiento de una aplicación WebRTC o cualquier otra solución de software es imprescindible para evitar problemas en el futuro. Una solución puede ser desarrollada por personas con experiencia y probada antes de su lanzamiento, pero aun así no significa que nunca aparecerán degradaciones en el rendimiento. Detectar problemas temprano y tomar las medidas correspondientes puede ayudar mucho a que los usuarios tengan una mejor experiencia.
Imagine que su aplicación de videollamadas tiene problemas cuando se produce la pérdida de paquetes . La pérdida de paquetes puede causar audio entrecortado, video congelado o fotogramas de video faltantes, lo que dificulta que los usuarios entiendan lo que se dice o vean lo que sucede en la llamada. La alta pérdida de paquetes también puede dificultar que la aplicación establezca y mantenga una conexión, lo que provoca llamadas o chats de video interrumpidos. Si usted y su equipo no experimentaron una pérdida de paquetes mientras trabajaban en el desarrollo de la aplicación, hay una manera de descubrir que hay un problema: un cliente decepcionado puede informarle sobre su experiencia desagradable. Por supuesto, sería mucho mejor descubrir el problema y solucionarlo antes de que los usuarios lo experimenten.
Esta es la razón por la cual el monitoreo es una práctica tan beneficiosa: observar regularmente el rendimiento y el comportamiento del producto a lo largo del tiempo le permite reaccionar rápidamente ante cualquier problema que surja y mantener un servicio confiable y de alto rendimiento. Esto no solo mejora la experiencia del usuario, lo que lleva a una mayor satisfacción y lealtad del cliente, sino que también le da a su empresa una ventaja competitiva en el mercado.
Beneficios del monitoreo regular de aplicaciones:
Loadero es una herramienta de prueba de carga y rendimiento que es capaz de simular el comportamiento real del usuario y la interacción con los sitios web mediante el uso de tecnologías de automatización web, como "Javascript + Nightwatch", "Java + TestUI" o "Python + Py-TestUI". Junto con eso, le proporciona todas las estadísticas necesarias de WebRTC y de la máquina, como FPS, tasa de bits, jitter, tiempo de ida y vuelta y otras, que se recopilaron durante la ejecución de la prueba y es capaz de afirmarlas.
Dado que la monitorización requiere una observación constante, por ejemplo, pruebas de funcionamiento constantes en nuestro caso, también necesitaríamos activar periódicamente las pruebas de funcionamiento. Para ese propósito, una canalización de CI/CD es una excelente opción, ya que es flexible y no es complicada de configurar para nuestra tarea. Además de ejecutar las pruebas periódicamente, la canalización también se puede usar para automatizar las pruebas después de cada implementación para asegurarse de que el rendimiento sea correcto.
Para comenzar a monitorear su solución WebRTC con Loadero, se requiere una configuración que consta de 3 partes:
Comencemos configurando la prueba Loadero para nuestro ejemplo de configuración de monitoreo. Si ya tiene una prueba en Loadero, que se puede iniciar para verificar algunas de las métricas de rendimiento, puede omitir esta parte y pasar a la parte sobre el lanzamiento de pruebas a través de la canalización. Si es la primera vez que trabaja en una prueba en Loadero, puede encontrar una guía completa paso a paso sobre cómo crear una prueba en Loadero en esta publicación de blog . Si ya tienes una prueba de rendimiento de WebRTC en otro servicio, mira cómo puedes migrar tu prueba a Loadero aquí . En nuestro caso, tendremos una prueba de “Javascript + Nightwatch”. El escenario será una llamada 1 a 1 de un minuto de duración en Jitsi .
En la prueba, dos participantes se unirán a una llamada y permanecerán en ella durante un minuto, tomando algunas capturas de pantalla a mitad de camino para una verificación adicional de la conexión.
Los participantes se conectarán desde EE. UU., Oregón, usarán la última versión de Google Chrome (109v al momento de escribir este blog) y usarán video + audio predeterminados para simular la señal de salida.
También utilizaremos las afirmaciones posteriores a la ejecución de Loadero. Le permiten especificar los criterios de "aprobación" para WebRTC y/o métricas de máquina en su prueba, como "si el promedio de FPS es ≥ 10, entonces aprueba". Una vez completada la ejecución, los resultados de afirmación se calculan automáticamente para cada participante para verificar si los valores dados han cumplido con los criterios de aprobación. Si la afirmación falló para un participante, el estado de este participante en el informe de resultados también será "Fallo".
Con las afirmaciones, evaluaremos la tasa de bits y los paquetes entrantes y salientes tanto para audio y video como para FPS.
La configuración de nuestra prueba sería algo así:
En este ejemplo tenemos un script de prueba de Loadero escrito en Javascript + Nightwatch, pero se puede hacer lo mismo con Java + TestUI o Python + Py-TestUI.
client => { client // Open the page .url(`https://meet.jit.si/LoaderoTests`) // Wait until the username field is visible // And enter the username .waitForElementVisible('[placeholder]', 30 * 1000) .sendKeys('[placeholder]', 'User') // Wait until the "Join" button is visible // And join the call by pressing the button .waitForElementVisible('[aria-label="Join meeting"]', 10 * 1000) .click('[aria-label="Join meeting"]') // Another thing you can do is to take screenshots during the test // Which could help you to identify the cause of a failure // And give visual feeback about the test run .takeScreenshot('pre_call_screenshot.png') // Stay in the call for half a minute .pause(30 * 1000) // Take a mid-call screenshot .takeScreenshot('mid_call_screenshot.png') // Stay in the call for another half a minute .pause(30 * 1000) // Take a post-call screenshot .takeScreenshot('post_call_screenshot.png'); }
Cada aplicación WebRTC es diferente y tendrá un rendimiento ligeramente diferente. Aquí nuestro objetivo es definir los umbrales en los que queremos ser notificados de inmediato si no se cumplen las expectativas de rendimiento, incluso si eso sucede durante la noche. Para hacer esto, usaremos un conjunto de aserciones posteriores a la ejecución de Loadero para las métricas de WebRTC, lo que hará que toda la ejecución de la prueba falle si los valores de las métricas de rendimiento de WebRTC no son tan buenos como nos gustaría verlos. Por lo tanto, los valores objetivo no deben establecerse en márgenes estrechos, pero debemos permitir que las pruebas sean ocasionalmente ligeramente peores de lo que nos gustaría idealmente, pero aún dentro de un rendimiento razonable. Los valores que hemos establecido aquí son ejemplos y es posible que desee ajustarlos en función de las especificaciones de la aplicación (por ejemplo, si prioriza una velocidad de fotogramas alta sobre el ancho de banda de la red, es posible que desee aumentar la velocidad de fotogramas mínima que desea ver y disminuir los límites de la tasa de bits). Como punto de partida, puede utilizar la lista de afirmaciones a continuación:
Aquí está la lista de aserciones y sus valores que establecemos para esta prueba de ejemplo:
webrtc/video/fps/out/25th >= 10
webrtc/video/fps/in/25th >= 10
webrtc/video/fps/out/stddev < 2
webrtc/video/fps/in/stddev < 2
webrtc/audio/packets/out/avg > 40/sec
webrtc/video/packets/out/avg > 100/sec
webrtc/audio/packets/in/avg > 40/sec
webrtc/video/packets/in/avg > 100/sec
webrtc/audio/bitrate/out/95th <= 25 kbit/sec
webrtc/video/bitrate/out/95th <= 1000 kbit/sec
webrtc/audio/bitrate/in/95th <= 25 kbit/sec
webrtc/video/bitrate/in/95th <= 1000 kbit/sec
Finalmente, tenemos que configurar los participantes de la prueba. Vamos a tener 1 grupo de participantes que tendrá 2 participantes con la misma configuración que se unirán a la llamada. La configuración de los participantes es la siguiente:
Sugerencia: si desea tener muchos participantes con exactamente la misma configuración, en el menú de configuración aumente el valor
Count
. Para ahorrarle tiempo, sugerimos crear participantes individualmente solo en caso de que necesiten tener configuraciones diferentes.
Para la configuración de prueba, eso sería todo. Pero como tenemos la intención de que nuestra prueba se ejecute regularmente, antes de proceder a configurar nuestra configuración de monitoreo, ejecute la prueba y verifique que el script no sea defectuoso al verificar los registros de Selenium y las capturas de pantalla que los participantes tomaron durante la ejecución de la prueba. Si es la primera vez que inicia una prueba en Loadero, o simplemente no está seguro de si se configuró correctamente, use esta publicación de blog para verificar si su prueba está lista para iniciarse .
Como se mencionó anteriormente, los participantes aún pueden fallar si las aserciones de métricas de WebRTC fallan y la tasa de éxito podría no ser del 100%. Esto sucedió para nuestra prueba también.
Esto no significa necesariamente que la prueba sea defectuosa, solo que la aplicación no cumple con los criterios de afirmación que ha establecido. Pero si su prueba falló debido a otra razón, no a las aserciones establecidas, esta publicación de blog explica algunas formas de depurar su prueba.
Las afirmaciones que establecemos son solo una línea de base general que no se adapta a la aplicación que probamos. Puede usar la lista y comenzar con esos valores, pero la aplicación que prueba puede diferir y los resultados de la métrica también pueden ser muy diferentes.
Consejo: una buena manera de establecer sus propias afirmaciones sería hacer 5 ejecuciones de prueba, observar las métricas de los participantes y evaluar objetivos razonables.
Establecer esas afirmaciones y analizar los resultados para descubrir por qué fallaron las afirmaciones es una tarea compleja en sí misma, por lo que no entraremos en demasiados detalles al respecto en esta publicación de blog. Además, el hecho de que nuestra prueba de ejemplo haya fallado debido a un error de aserción simula exactamente el caso que necesitamos, cuando una prueba falló y se envía una notificación sobre la falla, por lo que lo dejaremos como está. Si los registros de Selenium muestran que no ha encontrado ningún error y las capturas de pantalla confirman que se tomaron todas las acciones necesarias, entonces la prueba aún está lista para continuar.
Nuestro equipo ya ha preparado algunas publicaciones de blog sobre cómo integrar pruebas en su proceso de desarrollo: usando JS y el cliente Python de Loadero . Por lo tanto aquí vamos a confiar en ellos. Para nuestra configuración, usaremos lo que se sugiere en la publicación del blog que usa Python, GitHub y su implementación de CI/CD: flujos de trabajo junto con el cliente Loadero Python.
Nota: es posible que se salte alguna información. Para obtener instrucciones detalladas, consulte la publicación original del blog Loadero Python .
Para nuestro flujo de trabajo necesitaremos:
Cree un nuevo repositorio en GitHub o use uno existente.
En su repositorio en el directorio .github/workflows
cree un archivo notify-on-fail.yml
. Este es el archivo que va a contener instrucciones sobre cómo configurar el entorno y ejecutar la prueba de Loadero.
Comencemos definiendo el flujo de trabajo especificando los activadores en la notify-on-fail.yml
.
on: schedule: - cron: '0 9-18 * * *' workflow_dispatch:
schedule
le permite activar un flujo de trabajo a una hora programada. Por lo tanto, es el lugar donde se define la frecuencia de las ejecuciones de prueba. En nuestro ejemplo, hemos establecido el cronograma para ejecutar la prueba cada hora desde las 9 a. m. hasta las 6 p. m., ya que es el momento en que es más probable que el equipo pueda reaccionar ante una falla. En caso de que necesite realizar pruebas durante todo el ciclo día-noche, es posible que prefiera ejecutarlas cada 4 horas aproximadamente. Por lo tanto, supervisa la aplicación incluso cuando nadie está despierto. Preste atención, ese schedule
utiliza una sintaxis específica sobre la que puede obtener más información aquí .
Sugerencia : al configurar la frecuencia de las pruebas, tenga en cuenta que el período entre las ejecuciones de las pruebas debe ser más largo que la duración de la prueba, ya que sus pruebas pueden interferir entre sí.
El segundo activador, workflow_dispatch
, permite activar la canalización manualmente a través de la aplicación web GitHub si es necesario.
En nuestra sección jobs
del script, especificamos el entorno y todas las dependencias que usaremos. Para nuestro propósito, la configuración de la publicación del blog Loadero Python encaja perfectamente, así que no dudes en copiar y pegar.
jobs: notify-on-fail: runs-on: ubuntu-latest steps: - uses: actions/checkout@v3 - uses: actions/setup-python@v4 with: python-version: "3.10" - run: pip install loadero-python - run: python run.py env: LOADERO_ACCESS_TOKEN: ${{ secrets.ACCESS_TOKEN }} LOADERO_PROJECT_ID: ${{ secrets.PROJECT_ID }} LOADERO_TEST_ID: ${{ secrets.TEST_ID }}
Importante: preste atención, que en línea
- run: python run.py
, después de python tenemos la ruta a su archivorun.py
en relación con la raíz del repositorio. En mi caso, la estructura del archivo se verá así:
Otra cosa a la que hay que prestar atención son las credenciales. En primer lugar, puede encontrar la ID de prueba y proyecto en Loadero, pero también necesitará un token de acceso a la API del proyecto; actualmente, los tokens de acceso al proyecto se adquieren solicitándolos a nuestro equipo de soporte. En segundo lugar, las credenciales se utilizan como secretos de GitHub Actions. Esto mantiene privado su token de acceso a Loadero. Los secretos se pueden configurar en la configuración del repositorio -> Seguridad -> Secretos y variables -> Acciones -> Nuevo secreto del repositorio.
Para obtener instrucciones detalladas paso a paso sobre los secretos, consulte la publicación del blog mencionada anteriormente.
Entonces, la configuración del flujo de trabajo por ahora debería verse así:
name: Notify about failing tests in Loadero on: schedule: - cron: '0 9-18 * * *' workflow_dispatch: jobs: notify-on-fail: runs-on: ubuntu-latest steps: - uses: actions/checkout@v3 - uses: actions/setup-python@v4 with: python-version: "3.10" - run: pip install loadero-python - run: python run.py env: LOADERO_ACCESS_TOKEN: ${{ secrets.ACCESS_TOKEN }} LOADERO_PROJECT_ID: ${{ secrets.PROJECT_ID }} LOADERO_TEST_ID: ${{ secrets.TEST_ID }}
Ahora agreguemos a nuestra configuración el script de Python para interactuar con Loadero. Una vez más, el script del blog Loadero Python es un excelente punto de partida, por lo que lo usaremos y lo modificaremos más adelante según nuestras necesidades.
import os from loadero_python.api_client import APIClient from loadero_python.resources.test import Test project_id = os.environ.get("LOADERO_PROJECT_ID", None) access_token = os.environ.get("LOADERO_ACCESS_TOKEN", None) test_id = os.environ.get("LOADERO_TEST_ID", None) if project_id is None or access_token is None or test_id is None: raise Exception( "Please set the " "LOADERO_PROJECT_ID and LOADERO_ACCESS_TOKEN AND LOADERO_TEST_ID " "environment variables." ) APIClient( project_id=project_id, access_token=access_token, ) run = Test(test_id=test_id).launch().poll() print(run) for result in run.results()[0]: print(result) if run.params.success_rate != 1: raise Exception("Test failed")
Ahora es el momento de modificar nuestro script de Python para implementar nuestras notificaciones. En este ejemplo, la alerta se enviará a un canal de Discord. Aunque la forma de implementar las notificaciones es completamente opcional, ya que depende de tus preferencias personales.
Actualicemos nuestro archivo Python importando la biblioteca de solicitudes, las clases ResultStatus
y AssertStatus
.
import requests import os from loadero_python.api_client import APIClient from loadero_python.resources.test import Test from loadero_python.resources.classificator import ResultStatus, AssertStatus
Además de actualizar nuestro archivo YAML para instalar la biblioteca de solicitudes.
- run: pip install loadero-python - run: pip install requests - run: python run.py
En caso de que la canalización esté mal configurada y el valor de alguna de las credenciales sea Ninguno, debemos notificarlo a nuestro canal de Discord enviando una solicitud POST con el mensaje de error.
missing_credentials_message = ( "Please set the " "LOADERO_PROJECT_ID and LOADERO_ACCESS_TOKEN AND LOADERO_TEST_ID " "environment variables." ) def send_notification(message): requests.post( "https://discordapp.com/api/webhooks/{id}", data={"content": message}, ) if project_id is None or access_token is None or test_id is None: send_notification(missing_credentials_message) raise Exception(missing_credentials_message)
Si la prueba falla, nos gustaría saber el motivo. Aquí agregamos la verificación del participante. Si un participante falla, enviamos el mensaje de error con la siguiente estructura:
Además, deberíamos deshacernos de la excepción que tenía el script inicial, ya que aquí es excesiva.
run_failure_message = "" for result in run.results()[0]: result.params.run_id = run.params.run_id result.read() if ( result.params.selenium_result.value != ResultStatus.RS_PASS or result.params.status.value != ResultStatus.RS_PASS ): run_failure_message += ( f"{result.params.participant_details.participant_name}:\n" f"-Selenium result: {result.params.selenium_result.value}\n" f"-Participant status: {result.params.status.value}\n" ) if result.params.asserts: run_failure_message += "-Failing asserts:\n" for assertion in result.params.asserts: if assertion.status != AssertStatus.AS_PASS: run_failure_message += f"--{assertion.path.value}\n" run_failure_message += "\n" run_failure_message += f"Run status: {run.params.status.value}" if run.params.success_rate != 1: send_notification(run_failure_message)
Y también enviemos un mensaje para la prueba exitosa:
if run.params.success_rate != 1: send_notification(run_failure_message) else: send_notification(f"The {run.params.test_name} test has been finished successfully")
Como verificación final, debemos envolver toda la llamada API en try-except
en caso de que la conexión con la API de Loadero sea defectuosa. El script final de python se ve así:
import os import requests from loadero_python.api_client import APIClient from loadero_python.resources.test import Test from loadero_python.resources.classificator import ResultStatus, AssertStatus project_id = os.environ.get("LOADERO_PROJECT_ID", None) access_token = os.environ.get("LOADERO_ACCESS_TOKEN", None) test_id = os.environ.get("LOADERO_TEST_ID", None) missing_credentials_message = ( "Please set the " "LOADERO_PROJECT_ID and LOADERO_ACCESS_TOKEN AND LOADERO_TEST_ID " "environment variables." ) def send_notification(message): requests.post( "https://discordapp.com/api/webhooks/{id}", data={"content": message}, ) if project_id is None or access_token is None or test_id is None: send_notification(missing_credentials_message) raise Exception(missing_credentials_message) try: APIClient( project_id=project_id, access_token=access_token, ) run = Test(test_id=test_id).launch().poll() print(run) run_failure_message = "" for result in run.results()[0]: result.params.run_id = run.params.run_id result.read() if ( result.params.selenium_result.value != ResultStatus.RS_PASS or result.params.status.value != ResultStatus.RS_PASS ): run_failure_message += ( f"{result.params.participant_details.participant_name}:\n" f"-Selenium result: {result.params.selenium_result.value}\n" f"-Participant status: {result.params.status.value}\n" ) if result.params.asserts: run_failure_message += "-Failing asserts:\n" for assertion in result.params.asserts: if assertion.status != AssertStatus.AS_PASS: run_failure_message += f"--{assertion.path.value}\n" run_failure_message += "\n" run_failure_message += f"Run status: {run.params.status.value}" if run.params.success_rate != 1: send_notification(run_failure_message) else: send_notification( f"The {run.params.test_name} test has been finished successfully" ) except Exception as err: send_notification(f"Error while running Loadero test: {err}")
Ahora nuestra prueba se ejecuta automáticamente cada hora desde las 9 a. m. hasta las 6 p. m. y evalúa si la aplicación funciona como se espera.
Una vez finalizada la ejecución de la prueba, en caso de fallar la prueba, se le notificará sobre la falla.
En nuestro caso, la prueba de Jitsi falló debido a que los FPS y los paquetes no cumplieron con nuestros criterios, lo que se puede ver en la pestaña Afirmaciones del resultado de la prueba. Los resultados de la afirmación también son accesibles para cada participante individualmente, por lo que puede verificar si el problema ocurrió para todos los participantes o solo para una parte de ellos.
Los valores proporcionados anteriormente para las afirmaciones pueden servir como referencia inicial y parece que, en nuestro caso, no se alinean con el rendimiento objetivo de Jitsi. Así que no dude en explorar cómo funciona su aplicación y qué afirma que se ajusta mejor a su aplicación, para asegurarse de que el proceso de monitoreo sea óptimo.
Nota: con solo mirar las afirmaciones de nuestra prueba, podemos notar que hay secciones enteras que arrojan ceros a lo largo de la ejecución de la prueba, lo que finalmente afecta los resultados de la prueba.
Sugerencia: si su prueba falló, puede navegar a la pestaña de estadísticas de WebRTC, donde puede encontrar varios gráficos con datos y obtener más información sobre la métrica que ha causado la falla.
En esta publicación de blog, proporcionamos un ejemplo de cómo puede monitorear su aplicación WebRTC con la ayuda de Loadero y los flujos de trabajo de GitHub. Con el uso de la supervisión, estará mejor equipado para hacer frente a cualquier problema que pueda surgir en su aplicación. También puede ser conveniente crear otros escenarios con diferentes condiciones para obtener una visión más holística del rendimiento de la aplicación. Establecer dicha supervisión puede ser una tarea bastante compleja. ¿Le gustaría que el equipo de Loadero creara una configuración de monitoreo similar para usted? No dude en contactarnos en [email protected] y analicemos cómo podemos ayudarlo a monitorear de manera regular y automática su solución WebRTC.
También publicado aquí .