iptables NAT 테이블을 활용한 포트포워딩 에러 해결

포트 번호 없애기 (5000) 

sudo iptables -t nat -A PREROUTING -i eth0 -p tcp --dport 80 -j REDIRECT --to-port 5000

이 명령어는 eth0 인터페이스를 통해 들어오는 TCP 프로토콜의 포트 80(일반적으로 HTTP 트래픽)으로 들어오는 모든 트래픽을 포트 5000으로 redirect 하는 것이다.

 

이 때 app.py를 재시작하면 포트포워딩이 제대로 되지 않는 경우가 있는데, 이는 iptables 규칙이 기본적으로 메모리에 저장되기 때문이라고 한다. iptables 규칙을 영구적으로 유지하려면 이를 파일에 저장하고, 시스템이 부팅될 때 해당 파일에서 규칙을 불러와야 한다. 

 

 

 

이번 경우에는 ssh 명령어와 aws key 를 사용해 서버에 접근했고, 그 안에 가상환경이 구성되어 있었다.

vm을 활성화 한 상태와 ubuntu환경 모두 위 명령어로 포트를 리다이렉트 하도록 했다.

 

 

iptables 규칙 저장

이후 iptables 규칙 저장을 위해 아래처럼 입력했다.

sudo sh -c "iptables-save > /etc/iptables/rules.v4"

이 명령어는 /etc/iptables/rules.v4 파일에 현재 설정된 iptables 규칙을 저장하는 것이다.

 

입력하고 다시 서비스를 시작하였을 때는 제대로 작동하는 것을 확인할 수 있었다.

http://내AWS아이피/

 

(웹 브라우저에서 위 주소로 접속)

 


iptables 규칙 백업과 초기화

VM과 우분투 서버 둘 다 포트포워딩을 해야 접속 가능한 걸까 궁금해져서 iptables 규칙을 백업해둔 뒤 venv환경에서 초기화 해 주었다.

mkdir -p ~/backups #백업 파일 저장할 디렉토리를 만듦
sudo iptables-save > ~/backups/iptables-backup.txt #백업 파일을 생성한 디렉토리에 저장
sudo iptables-restore < ~/backups/iptables-backup.txt #복원시 사용할 명령어

 

백업과 삭제를 반복하다보니 우분투 서버 내부에 적용된 iptable 규칙은 VM상에서도 그대로 적용된다는 것을 알게 되었다. (역도 마찬가지). 그러니 결국 VM이든 우분투 서버 내에서든  iptables규칙을 영구저장해주지 않아 제대로 실행되지 않았던 것이다.

 

 

 

venv 환경에서 iptable 관련 설정들을 하나씩 초기화했는데,

sudo iptables -t nat -F # NAT 관련 규칙 초기화

이 명령어를 입력했을 때에만 포트포워딩이 제대로 적용되지 않았다. (5000을 명시해두면 접속 가능) 

 

이는 포트포워딩이 NAT 테이블이 패킷의 IP 주소 및 포트를 변경하여 리다이렉트 하는 데 사용하는 것이기 때문에, NAT관련 규칙을 초기화할 경우 80 포트로는 접속할 수 없는 것임을 유추할 수 있었다.

 

sudo iptables -t nat -L PREROUTING -v -n

 NAT 테이블 규칙은 위 명령어를 통해 확인할 수 있었으며 나의 경우 포트 번호를 없애는 명령어를 반복하여 입력했기 때문에 여러 규칙이 띄워져 있었다.

 

sudo iptables -t nat -D PREROUTING -p tcp --dport 80 -j REDIRECT --to-port 5000 #강제삭제

규칙을 모두 제거하려면 위 명령어로 강제를 해주어야 한다.

 


 

이외 아래의 명령어들은 포트포워딩과는 무관하며 NAT테이블 속성을 건드렸을 때만 포트로 접근할 수 없었다

sudo iptables -P INPUT ACCEPT
sudo iptables -P FORWARD ACCEPT
sudo iptables -P OUTPUT ACCEPT

sudo iptables -F
sudo iptables -t mangle -F
sudo iptables -t raw -F
sudo iptables -t security -F