Переброс MySQL с одного порта на другой, в пределах одной машины
Итак, для начала попробуем сделать локальный проброс, то есть, чтобы при подключении к порту 33060 нам в реальности откликался 3306 порт, по которому работает MySQL.
Для тестов нам понадобится telnet:
apt-get install -y telnet
Итак, убедимся, что MySQL работает на 3306 порту:
netstat -lnpt | grep 3306
tcp 0 0 127.0.0.1:3306 0.0.0.0:* LISTEN 4667/mysqld
Попробуем подключиться к MySQL посредством telnet:
telnet 127.0.0.1 3306
Trying 127.0.0.1...
Connected to 127.0.0.1.
Escape character is '^]'.
?
5.0.51a-24+lenny4,X!6,zD$',5se"tHHp|?bSC
Теперь подключим к фаерволлу вот такое правило, которое перебросит все запросы с 33060 порта на 3306 посредством цели REDIRECT (которая делает примерно следующее - "It redirects the packet to the machine itself by changing the destination IP to the primary address of the incoming interface"):
iptables -t nat -I OUTPUT --src 0/0 --dst 127.0.0.1 -p tcp --dport 33060 -j REDIRECT --to-ports 3306
Теперь проверим телнетом:
telnet 127.0.0.1 33060Trying 127.0.0.1...
Connected to 127.0.0.1.
Escape character is '^]'.
?
5.0.51a-24+lenny4-KDSV4@(C,WoGTPv"@\/sv
Визуально, все работает, но будет ли работать mysql клиент?
Еще как будет, смотрим:
mysql --host=127.0.0.1 -uroot -pyour_password --port 33060 -e 'show databases;;'
+--------------------+
| Database |
+--------------------+
| information_schema |
| mysql |
+--------------------+
Переброс запросов к локалхосту на 3306 порт на удаленный сервер
Итак, теперь нам для тестов нужна еще одна машина с mysql клиентов и telnet:
apt-get install -y telnet
На первой же машине (с MySQL) нужно открыть MySQL наружу, чтобы он слушал внешний интерфейс:
vi /etc/mysql/my.cnf
И в блоке mysqld сделать следующую правку:
bind-address = 0.0.0.0
И перезаупстить сервер:
/etc/init.d/mysql restart
Теперь на второй машине-клиенте забрасываем весь трафик выходящий с интерфейса localhost на внешний сервер:
iptables -t nat -A OUTPUT -p tcp --dport 3306 -j DNAT --to ext.ernal.ip.addr:3306
После часов извращений (убрав -o lo и подключаясь не к локалхосту, а к внешнему IP клиент машину) я добился того, что:
telnet ext.ernal.ip.addr
Trying ext.ernal.ip.addr...
Connected to ext.ernal.ip.addr.
Escape character is '^]'.
dHost 'xxxx' is not allowed to connect to this MySQL serverConnection closed by foreign host.
Но команда, которая может завернуть обращения к localhost наружу по-прежнему упорно не работает:
iptables -t nat -A OUTPUT -p tcp -o lo --dport 3306 -j DNAT --to ip_of_server_with_mysql:3306
У кого есть идеи? Все машины Debian Lenny 5, а также тестил на 2.6.33.
Update:
Работать это не будет принципиально, вот такой вот iptables!
По материалам:
1. http://forums.cpanel.net/f5/iptables-redirect-internal-port-remote-mysql-98333.html (рекомендуют NAT)
2. http://ubuntuforums.org/showthread.php?t=1436579 (попытки применить NAT)
3. http://www.linuxquestions.org/questions/showthread.php?p=3909624#post3909624 (еще немного по iptables)
4. http://forum.slicehost.com/comments.php?DiscussionID=4647 (готовое решение!)
5. http://wiki.debian.org/Firewalls-local-port-redirection (примеры порт редиректа! готовые!)
6. http://www.linuxquestions.org/questions/linux-networking-3/iptables-how-to-redirect-locally-generated-packets-to-a-remote-server-797173/
7. http://www.experts-exchange.com/Networking/Linux_Networking/Q_22862486.html (проблема DNAT + loopback)
8. http://lists.netfilter.org/pipermail/netfilter/2005-April/059765.html (пару слов про необходимость CONFIG_IP_NF_NAT_LOCAL)
9. Ссылка на "как это сделать через iproute2": http://www.listware.net/201007/debian-user/27927-iptables-localhost-redirect.html
http://highloaded.blogspot.com/2010/02/mysql-socketa-localhost-tcp.html
ОтветитьУдалитьВариант, но число патчей на хостинге уже стремится к страшным числам, еще один я не хочу :)
ОтветитьУдалитьа по другому никак =)
ОтветитьУдалитьСпосибо товарищ за ваш пост. А то я чуть с ума не сошел. Сижу тут больной, с температурой 38, и поставили мне ту же задачу.
ОтветитьУдалитьПробую очевидное - не получается. Ничего понять не могу... и так пробовал, и эдтак. И на другом серваке попробовал.. нифига.
Стал гуглить и наткнулся на ваш пост.
Этот комментарий был удален автором.
ОтветитьУдалитьЭтот комментарий был удален автором.
ОтветитьУдалитьПриветствую, вот может Вам поможет, мне лично помогло для решения своей задачи.
ОтветитьУдалитьhttp://www.geekzone.co.nz/forums.asp?forumid=46&topicid=87441
YourIP=127.0.0.1
YourExternalIP=192.168.10.10
YourPort=12345
TargetIP=203.97.30.147
TargetPort=80
iptables -t nat -F
iptables -t nat -A PREROUTING --dst $YourIP -p tcp --dport $YourPort -j DNAT --to-destination $TargetIP:$TargetPort
iptables -t nat -A POSTROUTING -p tcp --dst $TargetIP --dport $TargetPort -j SNAT --to-source $YourExternalIP
iptables -t nat -A OUTPUT --dst $YourIP -p tcp --dport $YourPort -j DNAT --to-destination $TargetIP:$TargetPort
P.S Не забудьте выполнить sysctl -w net.ipv4.conf.all.route_localnet=1. Проверял на Centos 7.
Крутейше!!! Спасибо что поделились!
Удалить