외부 연동에서 거부 응답이 왔다. 계정 문제로 보고 자격 정보를 확인했는데 맞게 들어가 있었다.
다른 서버에서는 같은 계정으로 잘 된다.
Table of contents
Open Table of contents
서버에 따라 달랐다
두 서버에서 같은 요청을 보내 봤다.
srv-01 성공
srv-02 거부
계정도 요청 내용도 같고 curl 로 보낸 본문까지 같다. 계정이 문제라면 어디서 부르든 같은 결과가 나와야 한다.
계정이 같은데 결과가 다르면 계정 문제가 아니므로 두 서버가 무엇이 다른지를 봐야 한다.
나가는 주소를 확인했다
각 서버에서 밖으로 나가는 주소를 봤다.
$ ssh srv-01 'curl -s https://api.ipify.org'
203.0.113.10
$ ssh srv-02 'curl -s https://api.ipify.org'
203.0.113.24
api.ipify.org 가 돌려주는 공인 IP 가 서로 달랐고 상대 쪽 설정에는 허용 주소 목록이 있었다.
203.0.113.10 은 목록에 있고 203.0.113.24 는 없었는데 서버를 늘릴 때 등록을 안 한 것이다.
HTTP 응답에는 인증 실패라고만 적혀 있어서 이유가 정확히 안 나오니 계정 쪽을 먼저 뒤지게 된다.
원인 — 허용 주소 목록과 개수 제한
주소 제한이 있다는 것은 연동 문서에 적혀 있었다.
접근 제어
등록된 IP 에서만 API 호출이 허용됩니다.
IP 등록은 관리자 화면에서 최대 3개까지 가능합니다.
읽었어야 할 것을 안 읽은 것이고 등록 가능한 IP 가 세 개뿐이라 서버가 늘면 언젠가 넘는다.
연동을 붙이는 시점에 접근 제어 항목을 확인했어야 했다. 그때 봤으면 서버를 늘릴 때 등록하는 절차가 함께 만들어졌을 것이다.
나가는 주소를 하나로 모았다
세 개 제한이 있으니 서버가 늘 때마다 등록하는 방식에는 끝이 있다. 밖으로 나가는 요청을 한 곳으로 모았다.
srv-01 ┐
srv-02 ├→ 경유 서버 (203.0.113.10) → 외부 API
srv-03 ┘
경유 서버의 IP 하나만 등록하면 되고 서버가 몇 대로 늘어도 상대가 보는 주소는 그대로다.
다만 경유 서버가 죽으면 연동이 전부 멈춘다. 하나로 모으는 대신 그 자리가 약해지므로 두 대를 두고 주소 두 개를 등록했다.
검증 — 어느 연동이 제한을 쓰는가
다른 연동들도 같은 성격인지 확인했다.
연동 A 주소 제한 있음 (3개) 경유 필요
연동 B 주소 제한 없음 직접 가능
연동 C 주소 제한 있음 (무제한) 직접 가능하나 등록 필요
연동 D 확인 필요 문의함
제한이 있어도 개수가 무제한이면 경유까지 갈 것은 아니고 IP 등록만 해 두면 된다.
이렇게 나눠 두니 새 서버를 띄울 때 무엇을 해야 하는지가 연동별로 정해졌다.
주의 — 문서에 없다와 제한이 없다
넷 중 연동 D가 문제였다. 문서에 접근 제어 항목이 아예 없었다.
물어봤더니 IP 제한이 있다고 했고 문서에 안 적혀 있었을 뿐이었다.
문서에 없다는 것이 제한이 없다는 뜻은 아니다. 없는 항목을 없음으로 읽으면 이번과 같은 거부 응답을 또 만나게 된다.
등록된 주소를 목록으로 관리했다
어느 연동에 어느 주소가 등록돼 있는지를 적어 뒀다.
연동 A
203.0.113.10 (경유-01)
203.0.113.11 (경유-02)
등록일 2017-03-05, 담당 ○○
변경 방법: 관리자 화면 > 설정 > IP 관리
IP 뿐 아니라 어디서 바꾸는지도 함께 적었는데 바꿀 때 그 화면을 다시 찾는 데 시간이 걸리기 때문이다.
담당자와 등록일을 적은 것은 나중에 누구에게 물어볼지가 정해지게 하려는 것이었다.
재발 방지 — 나가는 주소 정기 확인
각 서버에서 나가는 주소를 주기적으로 보게 했다.
for h in $HOSTS; do
IP=$(ssh "$h" 'curl -s --max-time 5 https://api.ipify.org')
echo "$h -> $IP"
done
HOSTS 를 돌며 ssh 로 물어보면 경유를 타는 서버는 전부 같은 값을 낸다. 다른 값이 섞여 있으면 그 서버의 경유 설정이 풀린 것이다.
실제로 한 번 걸렸다. 서버를 재기동한 뒤 경유 설정이 다시 안 붙어 있었는데 거부 응답이 나기 전에 알았다.
전체 흐름 — 원인을 가르는 순서
거부 응답을 받았을 때 볼 순서를 정했다.
1. 같은 요청이 다른 서버에서 되나 → 되면 주소·환경 문제
2. 같은 서버에서 다른 계정은 되나 → 되면 계정 문제
3. 같은 요청이 아까는 됐나 → 되면 시간·한도 문제
4. 응답 헤더에 단서가 있나
첫째를 먼저 하니 계정을 뒤지는 시간이 없어졌고 이번 건도 curl 한 번으로 갈렸다.
네 항목이 전부 하나만 바꾸고 나머지를 고정하는 시험인데 두 가지를 한꺼번에 바꾸면 원인이 안 갈린다.
정리
- 같은 계정인데 서버에 따라 결과가 다르면 계정 문제가 아니다
api.ipify.org로 밖으로 나가는 공인IP를 확인한다- 거부 이유가 응답에 정확히 안 나오면 엉뚱한 곳을 뒤지게 된다
- 연동 문서의 접근 제어 항목을 붙이는 시점에 확인한다
- 등록 개수 제한이 있으면 경유 지점으로 모아 주소를 줄인다
- 경유 지점이 하나면 그 자리가 약해지므로 두 대를 둔다
- 연동별로 제한 유무와 개수를 정리해 두면 서버 증설 절차가 정해진다
- 문서에 없다는 것이 제한이 없다는 뜻은 아니다
- 나가는
IP를 정기적으로 확인하면 설정이 풀린 것이 드러난다 - 하나만 바꾸고 나머지를 고정해야 원인이 갈린다