Como redireccionar el trafico a una nueva IP con IPtables

Muchas veces nos pasa que cuando migramos un servidor o una aplicación a un nuevo servidor cambia la dirección IP y ya sea porque nuestros servidores DNS aún apuntan a la vieja dirección o nuestros clientes no han actualizado la IP en sus PC todavía apuntan al viejo servidor.

En este tutorial vamos a ver en 3 pasos sencillos como redireccionar el tráfico de nuestra red a una nueva IP utilizando IPtables con las reglas de NAT.

Les recuerdo que para ejecutar estos comandos necesitan tener privilegios de administrador (root). En caso que utilices Ubuntu debes colocar sudo al principio de cada comando.

Voy a suponer que no tienes echa ninguna regla en la tabla nat que afecte el PREROUTING o el POSTROUTING.

Vamos a comenzar

1. Habilitar el IP Forwarding

El IP Forwarding sirve para darle capacidad de Router a nuestro servidor es decir que pueda recibir y reenviar los paquetes por una o varias interfaces, ya sea que realice una transformación de dichos paquetes o no.

Para esto solo tenemos que ejecutar el siguiente comando:

echo "1" > /proc/sys/net/ipv4/ip_forward

También podemos ejecutar:

sysctl net.ipv4.ip_forward=1

Luego de esto tenemos que reniciar nuestro servicio de red ejecutando:

/etc/init.d/networking restart

Nota: En algunas distribuciones es network y no networking

También puedes ejecutar en algunas distribuciones como Fedora, CentOS, RedHat:

service network restart

2. Crear reglas en IPtables

Voy a suponer que la dirección IP del servidor viejo es 5.5.5.5 y la queremos redireccionar a la IP nueva 7.7.7.7 con el puerto 9999.

iptables -t nat -A PREROUTING -p tcp --dport 9999 -j DNAT --to-destination 7.7.7.7:9999

Esta primera regla redirecciona todo lo que entre por el puerto TCP 9999 a la dirección 7.7.7.7 puerto 9999 esta es una regla de PREROUTING que afecta a la tabla nat (-t nat) de IPtables. Si quisieras redireccionarlo a un puerto diferente solo tienes que cambiar 7.7.7.7:#puerto al que quieras, también tienes que estár pendiente si el puerto es tcp o udp.

La segunda regla es para enmascarar la dirección IP, de modo que el servidor nuevo va a ver como si todas las peticiones vienen de la IP 5.5.5.5:

iptables -t nat -A POSTROUTING -j MASQUERADE

3. Listo

Ya puedes probar que tus reglas están funcionando, con una PC que apunte al viejo servidor prueba que te responde el nuevo servidor, puedes hacer un tracert. Tambien puedes hacer un tcpdump en el nuevo servidor y ver que todas las peticiones están llegando del viejo servidor.

Otras opciones

Puedes modificar la regla de PREROUTING para otros casos por ejemplo:

Redireccionar el tráfico que viene de una IP específica:

iptables -t nat -A PREROUTING -s 10.1.1.15 -p tcp --dport 9999 -j DNAT --to-destination 7.7.7.7:9999

Redireccionar el tráfico de un segmento de red:

iptables -t nat -A PREROUTING -s 10.1.1.0/24 -p tcp --dport 9999 -j DNAT --to-destination 7.7.7.7:9999

Redireccionar el tráfico que llegue por una interfaz específica:

iptables -t nat -A PREROUTING -i eth0 -p tcp --dport 9999 -j DNAT --to-destination 7.7.7.7:9999

Y cualquier mezcla de los anteriores para más información puedes ver las páginas man de iptables:

man iptables

O ver este tutorial de IPtables muy completo en inglés.

Este tutorial está basado en el tutorial How-To: Redirecting network traffic to a new IP using IPtables que está hecho por chantra, con algunas mejoras y cambios.

Espero que les sirva cualquier duda o comentario no duden en escribir

Saludos

Olivers

Si quieres recibir notificaciones de cuando se publican nuevos artículos y tutoriales en Vensign por favor subscribete a nuestro boletín RSS.

13 comments

  1. mi situación es, tengo una red completamente local, y tengo un servidor en dicha red (ubuntu server 12.04), la red esta abierta (no tiene clave) cualquier persona puede conectarse, pero me gustaría que la persona conectada, al abrir el navegador lo redireccione a una pagina de bienvenida, he leído que los portales cautivos sirven para dar permiso a usuario y asi acceder a internet, pero este no es el caso, puesto que no hay internet de por medio, solo quiero que los usuario que se conecten sean redirigidos a una pagina de bienvenida, con eso es posible hacer eso??

    disculpa mi ognoracia, no soy bueno en redes :(

  2. Hola, muchas gracias por la explicación…

    tengo problemas con el correo saliente y podría ser por bloqueo del puerto 25… si realizo estos pasos, y resulta que sigue sin funcionar… ¿cómo elimino la regla creada?

    Los correos me devuelven lo siguiente:
    Ocurrió un error al enviar el mensaje. El servidor de correo respondió: 5.7.1 : Recipient address rejected: Mail appeared to be SPAM or forged. Ask your Mail/DNS-Administrator to correct HELO and DNS MX settings or to get removed from DNSBLs; MTA helo: [192.168.0.133], MTA hostname: 30.pool85-53-194.dynamic.orange.es[85.53.194.30] (helo/hostname mismatch). Por favor, compruebe el destinatario del mensaje email@dominio.tld y vuelva a intentarlo.

    1. Hola Lusinho,

      Hay varias formas de eliminar la regla puedes ejecutar en terminal:

      iptables -L INPUT -n --line-numbers

      Te aparecerá la lista de las reglas con los números de línea al lado y después ejecutas:

      iptables -D INPUT número_aquí

      Cambiando por supuesto donde dice número aquí por el número de línea que quieras eliminar

      En cuanto a tu problema el servidor te está respondiendo que debes cambiar tu configuración de MX, probablemente porque está detectando la dirección como falsa, tienes que configurar correctamente los MX para que seas detectado como un gateway legítimo de correo.

      Avísanos si te funcionó

  3. Saludos, es una buena informacion, gracias, quisiera preguntar si me puede ser util en el siguiente caso:

    Tengo un servidor web con php en el mismo servidor que la base de datos MySQL y ahora, por seguridad, quisiera mover el servidor MySQL a otro servidor fisico con una IP diferente, sin embargo, todas las aplicaciones, al hacer conexion a la BD lo hacen a traves de “localhost” o “127.0.0.1”.

    Con iptables puedo redireccionar los querys que se hacen a localhost hacia el otro servidor fisico?? es decir cuando una aplicacion web se conecte a localhost de MySQL en realidad me responda el otro servidor??

    Quizas puediera parecer mas sencillo hacer que las aplicaciones se conecten a la ip del nuevo servidor, pero hay una gran cantidad de aplicaciones y la mayoria de ellas no tienen sus conexiones estandarizadas y algunas se conectan en cada script. Muchas de esas aplicaciones fueron desarrolladas por personas que ya no estan laborando aca y no hay docuementacion de las mismas. De modo que la opcion mas transparente me parece que es redireccionar las peticiones de “localhost” o “127.0.0.1” hacia la ip del nuevo servidor.

    Gracias por su atencion.

    1. Hola Niko, gracias por tu comentario en cuanto a tu duda

      Lo más sano sería cambiar la dirección en las aplicaciones porque puedes llegar a tener problemas por esto.

      Mas que redireccionar la IP es mejor que redirecciones el puerto, ya que si redireccionas 127.0.0.1 puedes ocasionar que muchas cosas dejen de funcionar.

      El puerto por defecto de MySQL es 3306 por lo que la regla sería algo como (ojo no la he probado tienes que probar que te funciona):

      iptables -t nat -A OUTPUT -p tcp –dport 3306 -j DNAT –to 192.168.1.X

      Colocando en 192.168.1.X la dirección IP de el servidor donde esté MySQL

      Recuerda habilitar MySQL para que acepte conexiones remotas y tambien verificar que las contraseñas sean iguales a las que tenias en tu otro servidor o igualmente tendrás que cambiar usuarios y contraseñas en las aplicaciones.

      Te aconsejo tener esto como una solución temporal y poco a poco ir actualizando tus aplicaciones.

      Avísanos si te funcionó y si quieres puedes registrarte en nuestro boletín de noticias en el cuadro amarillo a la derecha

      Saludos
      Olivers

  4. Como redirecciono el trafico entre dos redes con rango ip diferente con iptables para que puedan tener comunicacion entre las dos?

    DIAGRAMA ASI:

    cliente1Linux Iptables1Linux Iptables2cliente2

    que se puedan ver los dos clientes entre si