aws rds를 만들었는데 접속이 안된다.

noname2048·2021년 8월 12일
0

아두이노에서 온도 정보를 UDP로 1차 서버에게 보내고, 1차 서버가 이를 토대로 RDS에 데이터를 저장하는 간단한 프로젝트를 진행중이였다. 저번에 VPC를 만들어 본 경험이 있어서 쉽게 RDS를 구성하여 데이터를 올릴 수 있을 거라 생각했다.

그런데, 이게 왠걸, connection timed out이 뜬다. 보통은 시큐리티 설정이 잘못되면 connection refuse, 인스턴스가 안뜨면 주소를 찾을 수 없다. 이런 경고문을 봤기 때문에, 중간에 연결설정을 잘 못했으리라 짐작했다.

물론 연결설정을 잘못한건 맞았다. 극히 초반에 라우팅 테이블과 인터넷 게이트웨이를 연결하지 않았던 실수를 좋은 블로그들 통해 보며 바로잡을 수 있었다. 그렇게 해결되면 참 좋았는데...

라우팅 문제는 해결했으나, 동작하지 않아 하루정도 삽질했다. 어디가 잘못된 걸까? 도식화와 키워드 점검을 수행하였다.

1차 도식화

1차도식화
빠진게 많아 보인다. 개념이해도 잘 못한것 같다. 좀더 알아보기 쉽게 다시 그렸다.

2차 도식화


조금 더 개념이 잡힌 모습이다. 아래는 확대한 사진.

키워드 점검

어디가 잘못 된지 잘 모르겠어서 키워드 별로 살펴보려고 한다.

  • vpc (10.10.0.0/16)
    • DNS hostnames: Enabled 설정했다.
    • DNS resolution: Enabled 설정완료.
  • subnet 8개
    • 10.10.0.0/24 부터 10.10.7/24 까지 8개를 만들었다. (각 사용가능 IP, 250~251)
    • 그 중 0~3은 auto-assign IP settings: Enable 설정이 켜져있다.
    • 가용영역에대해 ap-northeast-2a ~ 2d 를 번걸아가며 지정했다.
  • 인터넷 게이트웨이
    • 위에 지정한 vpc와 연결하였다.
  • 라우팅 테이블
    • 10.10.0.0/16 은 내부로 향한다. (기본)
    • 그 외 나머지 0.0.0.0/0 는 모두 인터넷 게이트웨이를 향한다.(추가)
  • 시큐리티그룹
    • in과 out에 대해 모두 허용하는 default를 지정하였다.
  • 네트워크 ACL
    • 마찬가지로 default라 모든 연결에 대해 허용한다.

DB 설정과 관련해서 점검해보았다.

  • db subnet group
    • 위의 vpc와 연결하였다.
    • 가용서브넷으로 0~3까지, 2a-2d까지 모든 가능한 가용서브넷을 등록하였다.
  • RDS
    • postgres 2개, mysql 2개를 기본으로 만들어 보았다 (모두 프리티어: t2.micro)
    • public access 가능성: true로 모두 설정
    • 모두 connection timed out

주요증상

주요 증상은 다음과 같다.

  • telnet 혹은 dbdeaver를 통한 연결 모두가 time out 상태이다.
  • 연결을 시도하면 ipv4는 정상적으로 찾는다.
  • ec2 ->(10.10..) db, 내컴퓨터 (3...*) -> db
  • 해당 VPC를 이용하는 EC2 인스턴스는 정상적으로 접근이 가능하다.
  • RDS 만 먹통.

해결과정

1. 커뮤니티에 지원요청

정보수집을 위해 며칠 전부터 들어가 두었던 AWS 정보공유방에 염치를 무릎쓰고 질문하였다. (500명 정도의 오픈카톡)

3분께서 짚어주신 부분은 다음과 같다.
1. 보안그룹 문제가 아닐까 (1명)
2. 서브넷에서 외부와 통신이 되는지 확인하고, 라우팅 테이블과 RDS를 연결하라 (2명)

2. 문제 확인하기

  1. 라우팅 테이블과 RDS는 따로 연결하는 부분이 있나 싶어서 라우팅 테이블을 살펴보았다.
  2. 라우팅 테이블 - edit routes - add rules
  3. 관련항목은 게이트웨이, 로드밸런서, 인스턴스, 로컬, 등이였다. RDS는 없었다.
  4. 해당 도큐를 찾아보았다. (커뮤티니에서 올려주심)
  5. 그러나 RDS를 라우팅 테이블을 따로 만들어준 경우는 없었다. (슬펐다)
  6. 나중에 안 사실이지만 서브넷에서 그저 외부로 나갈 통로를 만드는 건 게이트 웨이 연결로 충분했다.
  7. 시큐리티에 문제가 있을까 싶어서 다시 돌아왔다.
  8. 문제가 없어보이는데 하면서 다시 봤다.
  9. 그리고 혹시나 싶어서 (모든 이해가 안가는건 태클하기 시작하는 시점) 규칙하나를 추가했는데... 되더라 (슬플과 비탄과 감격. 그런 시간)

3. 문제 정리하기

  • RDS에 붙어있는 시큐리티 그룹에서, 인바운드룰에 (type: All), (Protocol: All), (Port: All) 이라고 적혀있어서 모든 통신을 허용하는 것 인줄 알았다.
  • 아웃바운드를 유심히 살펴보다가 아웃바운드는 왜 destination 인데 인바운드는 source 네 하던중에 무언가 이상한 점을 발견했다.
  • 인바운드 룰에 source가 sg-097 로 시작하는 아이디로 되어있었다.
  • 저 아이디가 가르키는건 내가 보고있는 시큐리티 그룹인데.. 그럼 자기 자신을 가리키는.. 이상한 소스...
  • 포트를 규칙에 추가하니 잘 작동하더라

그래서 결론

  • 해당 소스의 의미는 같은 VPC 내에서 (다른 vpc에서는 선택지로 나오지도 않는다.) 시큐리티 그룹을 동일 하게 사용하는 인스턴스 간의 통신을 허용한 것이였다.
  • 즉, 그룹을 중복해서 사용하는 RDS나, EC2등과는 통신이 가능하다?
    • 해당명제를 실험해보기위해서 시큐리티 그룹의 인바운드를 ssh, self (postgres 제거)로 설정
    • 해당 보안그룹을 사용하는 EC2와 RDS를 준비하였다.
    • (외부 - EC2: 연결가능), (외부 - RDS: 연결불가) (EC2 - RDS) 연결가능
    • 신기한 결과를 도출해낼 수 있었다.
  • 즉, 결론. inbound: self(self-securitygroup)를 any(0.0.0.0/0)로 보고 왜 안되지 했던 것이였다.

4. 해결

EC2와 RDS의 그래서 시큐리티 그룹을 동일하게 지정할때

  • ssh는 기본적으로 오픈 상태여야하니 ssh 추가.
  • 퍼블릭 RDS가 필요하다면 postgres 포트를 인바운드에 추가
  • 프라이베잇의 경우 postgres 포트를 cidr로 제한하지 않아도 그냥 시큐리티 그룹간 통신 가능

EC2와 RDS의 시큐리티 그룹을 다르게 지정할때

  • postgres 포트를 모든 IP에 대해 추가. (퍼블릭 접근가능)
  • 퍼블릭 접근을 막으려면...? postgresl 포트를 local 만 접근 가능하게 지정 (cidr 표기)

5. 별개로 느낀점

  • 해당 내용은 44bit에 정리되어 있는 내용이었다. (2번 읽었다)
  • 역시 개변을 하는 수준까지, 혹은 해당 블로그 도움을 받지 않고 설명을 제대로 할 수 있어야 이해한 것이겠다.
  • 프로그래머는 해봐야 아는거다. 라는 개인적인 지론이 좀 더 확고해지는 시간이였다 (토이프로젝트열심히하자)
  • 이러한 문제는 거시적인 도움을 줄 수 없고, 하나하나 다 까봐야하기에 도움을 주는 입장에서도, 도움을 받는 입장에서도 서로 내용을 주고받기 힘들다. ㅠㅠ
  • 이런 문제가 반복되지 않았으면 좋겠다. (원래 계획은 반나절만 잡고있는 거였는데 하루반이 걸렸다.)
profile
설명을 쉽게 잘하는 개발자를 꿈꾸는 웹 개발 주니어

0개의 댓글