- Speedbump es un proxy TCP escrito en Go que simula condiciones de demora al agregar latencia de red variable al tráfico TCP que se enruta a través del proxy
- A la latencia base se le pueden sumar componentes de latencia con forma de onda sinusoidal, diente de sierra, cuadrada y triangular, y se pueden combinar varios componentes al mismo tiempo
- El ejemplo muestra una configuración que hace proxy del tráfico dirigido a
localhost:80en el puerto2000, aplicando una demora base de100ms, amplitud sinusoidal de100msy un período de1m - La instalación puede hacerse descargando binarios precompilados por release, compilando desde el código fuente con
go build, o ejecutando la imagen de contenedorkffl/speedbump - Además del CLI, también puede usarse como biblioteca mediante el paquete
libde Go, con parámetros para ajustar el tamaño del búfer, el tamaño de la cola de demora, el nivel de logs, el host de escucha y el puerto
Proxy para simular latencia TCP
- Speedbump es un proxy TCP escrito en Go y puede simular latencia de red variable
- El destino del proxy se especifica con el argumento
<destination>del CLI, indicado con el formatohost:post - El funcionamiento básico consiste en hacer proxy del tráfico TCP hacia el destino mientras se agrega la latencia configurada
Instalación y formas de ejecución
- La forma más sencilla de instalación es descargar los binarios precompilados que se adjuntan automáticamente en
Assetsde cada release - Para compilar desde el código fuente, se clona el repositorio y luego se ejecuta
go build - Para ejecutarlo como contenedor, se puede usar la imagen kffl/speedbump
Ejemplo básico de uso
- Puede escuchar en el puerto
2000y hacer proxy del tráfico TCP hacialocalhost:80, aplicando una latencia base de100ms, amplitud sinusoidal de100msy período de1m- Esta configuración genera una latencia adicional máxima de
200msy una latencia adicional mínima de0 - El ejemplo de ejecución es
speedbump --latency=100ms --sine-amplitude=100ms --sine-period=1m --port=2000 localhost:80
- Esta configuración genera una latencia adicional máxima de
- La misma configuración también puede ejecutarse con la imagen de contenedor
- El ejemplo es
docker run --net=host kffl/speedbump:latest --latency=100ms --sine-amplitude=100ms --sine-period=1m --port=2000 localhost:80
- El ejemplo es
- También se puede configurar un componente de latencia en diente de sierra
- El ejemplo usa una latencia base de
300ms, amplitud de diente de sierra de200ms, período de2m, puerto2000y destinolocalhost:80 - El comando es
speedbump --latency=300ms --saw-amplitude=200ms --saw-period=2m --port=2000 localhost:80
- El ejemplo usa una latencia base de
Combinación de componentes de latencia
- Speedbump puede aplicar varios componentes de latencia al mismo tiempo
- El README incluye un ejemplo de gráfico de latencia que combina diente de sierra y onda sinusoidal
Argumentos del CLI y uso como biblioteca
speedbump --helpmuestra el uso con el formatospeedbump [<flags>] <destination>- Las principales opciones de red son las siguientes
--host: IP o nombre de host donde escuchará; si no se especifica, se enlaza a todas las interfaces de red--port: puerto de escucha; el valor predeterminado es8000--buffer: tamaño del búfer usado para lecturas TCP; el valor predeterminado es64KB--queue-size: tamaño de la cola de demora que almacena los búferes leídos; el valor predeterminado es1024
- También ofrece valores predeterminados y opciones de forma de onda para la latencia
--latency: latencia base que se agrega al tráfico en proxy; el valor predeterminado es5ms--sine-amplitude,--sine-period: amplitud y período de la latencia sinusoidal--saw-amplitude,--saw-period: amplitud y período de la latencia en diente de sierra--square-amplitude,--square-period: amplitud y período de la latencia cuadrada--triangle-amplitude,--triangle-period: amplitud y período de la latencia triangular
- También incluye opciones operativas
--log-level: nivel de logs; los valores posibles sonDEBUG,TRACE,INFO,WARN,ERROR--version: muestra la versión de la aplicación
- Speedbump también puede usarse como biblioteca de Go mediante el paquete
lib - La licencia es Apache 2.0 License
1 comentarios
Opiniones en Hacker News
Estuve buscando algo parecido para probar varias implementaciones de ActivityPub con distintos tamaños y condiciones de red, pero resultó que ya tenía todo lo necesario instalado en mi máquina con
tcEn mi distribución venía incluido en el paquete iproute2, y también hay una explicación aquí: https://wiki.archlinux.org/title/advanced_traffic_control
Para agregar latencia a una interfaz específica, se puede ejecutar algo como
tc qdisc add dev eth0 root netem delay 100msEs fácil de usar, funciona bien incluso en contenedores Docker, permite aplicar condiciones como latencia, pérdida y duplicación de paquetes, y probablemente ya lo tengas instalado
tc/netem/tbfson realmente buenos. Armé una GUI en Python sencilla encima de eso y la corrí en una Pi dentro de una carcasa con pantalla táctil; era una cajita negra con opciones como “paquetes descartados: [0%] [1%] [10%] [50%] / corrupción de paquetes: ...”, y a los clientes les impresionaba bastanteMe sorprende que no se vean mucho frontends parecidos como productos comerciales de hardware; si no se me escaparon en las búsquedas, parece que no existen en el mercado
tces que aplicarlo a paquetes entrantes es algo raro y complicadoHace tiempo hice mi propio emulador para imitar una terminal satelital comercial específica. Esa terminal acumulaba paquetes en una cola y, al llegar a cierto umbral o superar un límite de tiempo, los soltaba en bloque; además intentaba reducir la latencia reordenando “amablemente” los paquetes pequeños hacia el frente de la cola, pero al stack TCP eso le desagradaba muchísimo
tcno puede hacer esoPodría ser bastante útil para simular los efectos del clima en enlaces satelitales/RF que cambian con el tiempo
Esto era exactamente lo que Netflix había creado, y se llamaba latency monkey
Descubrimos que determinar si un servicio dependiente está “lento” es mucho más difícil que determinar si está “no disponible”, así que era una forma importante de probar cómo manejan los servicios la lentitud y los problemas de red
La implementación era muy simple: descartaba paquetes en una proporción configurable, lo que forzaba retransmisiones, de modo que del otro lado los paquetes llegaban con retraso y desordenados
Al final encontramos muchos problemas en el código de manejo de errores relacionado con el acceso a la red
Creo que todo ingeniero de software que haga aplicaciones interactivas de internet debería usar herramientas así en su trabajo diario. No solo para TCP, también hace falta QUIC, e idealmente todo UDP para cubrir incluso DNS
Estoy convencido de que el 90% de la hipertrofia de las aplicaciones web desaparecería si quienes las crean no usaran únicamente entornos de cómputo tipo Cadillac chapado en oro
https://firefox-source-docs.mozilla.org/devtools-user/networ...
Claro que esto solo aplica a pruebas de frontend basadas en navegador
En entornos donde la conexión de red se corta de forma intermitente, como en situaciones de ayuda ante desastres, muchas apps funcionan pésimo
Si más desarrolladores de apps probaran simulando conectividad intermitente, eso podría ayudar a otros
De “Toxiproxy is a framework for simulating network conditions” (2021) https://news.ycombinator.com/item?id=29084277#29088775:
Porque solo se están enviando paquetes de 50 bytes y 1 de cada 10 se pierde. Mientras tanto, un hilo del servidor no está haciendo ningún trabajo útil
En Mac se puede hacer lo mismo solo con herramientas integradas
Hay un proyecto que lleva un tiempo inactivo, pero cuyo nombre lo dice casi todo: https://github.com/tylertreat/comcast
Hace poco intenté simular una red lenta en Mac y encontré Network Link Conditioner, que está bastante bien. No hace falta configurar algo como un proxy
Hay que instalarlo desde las herramientas adicionales de Xcode
https://nshipster.com/network-link-conditioner/
También vale la pena ver la excelente herramienta toxiproxy de Shopify: https://github.com/Shopify/toxiproxy
También es una muy buena forma de probar una biblioteca de networking que uno mismo esté implementando, porque el stack debería poder manejar correctamente la mayoría de las situaciones adversas
La idea de la ‘ingeniería del caos’ es genial
Estoy desarrollando una barra de progreso para un crawler web, y al probar en localhost todo va demasiado rápido como para saber si hay algún problema
Con speedbump basta ejecutar
podman run --net=host kffl/speedbump:latest --latency=1s --port=8001 localhost:8000y probar el crawler en http://localhost:8001Es una herramienta limpia
Hay una herramienta parecida que he usado en Windows
https://jagt.github.io/clumsy/
FreeBSD también tiene dummynet como parte de ipfw, que permite inyectar latencia, límites de ancho de banda, tamaño de cola y pérdida de paquetes. Es la misma función que existe en MacOS
tcen Linux?