STORY 1. 웹 서버의 설치 장소
1. 사내에 웹 서버를 설치하는 경우
- 가장 간단한 방법
- 사내 LAN에 서버 설치하고, 인터넷에서 직접 액세스
- IP 주소가 부족하여 이 방법 안씀
- 또한 보안 문제 → 공격에 노출
- 그래서 방화벽을 둠
- 특정 서버에서 동작하는 특정 애플리케이션에 액세스하는 패킷만 통과, 나머지는 차단
- 그러나 만능은 아님 → 액세스를 허가한 애플리케이션에 보안 구멍이 있으면 공격받음
2. 데이터센터에 웹 서버를 설치하는 경우
- 데이터센터 시설에 서버를 가지고 들어가서 설치하거나 프로바이더가 소유하는 서버를 빌려쓰는 형태
- 고속 액세스 가능
- 안전성도 높음
STORY 2. 방화벽의 원리와 동작
1. 패킷 필터링형이 주류이다
- 지금은 거의 무조건 서버의 바로 앞에 방화벽이 있는 것이 보통
- 방화벽은 패킷을 차단하는 방식인데, 이것이 간단하지 않음
- 지금은 패킷 필터링형이 주류
2. 패킷 필터링의 조건 설정 개념
- 먼저 IP 주소를 이용하여 필터링한다
- 웹 서버 ← 인터넷은 허용하나, 사내 LAN이 아닌 공개 서버용 LAN에 접속만 허용해야함
- 수신처 IP 주소를 확인하여 공개 서버용 LAN일 경우 허용
- 웹 서버 → 인터넷 은 불허 → 다른 서버로 감염시키는 악성 소프트웨어 때문
- 송신처 IP 주소를 확인하여 공개 서버용 LAN일 경우 차단
- 그러나 ACK을 보내야 하기 때문에 위 방식으로는 불가능
3. 애플리케이션을 한정할 때 포트 번호를 사용한다
- 위 경우 완전 뚫리기 때문에 파일 서버 등 다양한 위험에 노출
- 최소한 포트 80만을 허용함으로써 웹 어플리케이션만을 허용함
- 나머지 웹서버 → 인터넷 패킷은 전부 차단
4. 컨트롤 비트로 접속 방향을 판단한다
- 위 경우를 만족해도 웹 서버에서 인터넷으로의 접속을 끊을 수가 없다.
- 이를 끊기 위해서, SYN 비트가 1이고 ACK 비트가 0인 패킷만을 끊는다.
- 이 방식으로, 첫 핸드셰이크가 성립되지 않으므로 다음 것들도 모두 성립되지 않는다.
- 또한 인터넷 → 서버로 커넥션 수립 후 서버 → 인터넷으로 응답 보낼 때는 SYN + ACK이므로 필터링을 통과할 수 있다.
- 그러나 DNS 서버 액세스는 UDP를 사용하므로 컨트롤 비트가 없다.
- 이 경우에는 모두 통과시키거나, 다 막을 수밖에 없음
5. 사내 LAN에서 공개 서버용 LAN으로 조건을 설정한다
6. 밖에서 사내 LAN으로 액세스할 수 없다
- 주소 변환이 이루어지므로 방화벽을 설정할 필요가 없음
7. 방화벽을 통과한다
- 방화벽을 통과한 패킷은 일반 라우터와 같이 중계된다.
- 패킷 필터링은 방화벽용의 특별한 구조가 아닌 라우터의 패킷 중계 기능의 부가 기능이라고 간주해도 좋음
- 그러나 이러한 기능들이 너무 많아지면 라우터가 복잡해지니까 전용 하드웨어나 소프트웨어를 사용하는 개념
8. 방화벽으로 막을 수 없는 공격
- 방화벽은 결국 송신지와 수신지를 주로 보기 때문에 내용에 문제가 있는 경우를 필터링하지 못함
- 첫번째 해결책 : 서버 내부 버그 픽스
- 두번째 : 패킷 내용 조사하여 위험한 데이터 차단하는 별도 프로그램 준비
STORY 3. 복수 서버에 리퀘스트를 분배한 서버의 부하 분산
1. 처리 능력이 부족하면 복수 서버로 부하 분산된다
- 서버 액세스가 증가하면 회선을 빠르게 하는게 효과적
- 그러나 회선이 빨라짐과 대비해 웹 서버의 처리 능력이 딸릴 수 있음
- 가장 쉬운건 서버를 좋은 머신으로 바꾸는 것 (Scale Up)
- 그러나 서버 한 대로는 여전히 부족
- 그래서 여러 서버를 통해 한 서버가 받는 부하를 줄이는 방법 사용 → 분산 처리
- 리퀘스트를 어떻게 분배하는지가 중요해짐
- 가장 쉬운 방법 : 라운드 로빈 (Round Robin)
- DNS 서버에 같은 도메인에 대해 여러 IP를 등록
- 클라이언트의 다수 요청에 따라 IP를 순차적으로 돌리면서 제공
- 문제
- 중간에 고장난 서버가 있어도 DNS는 알지 못함
- 쇼핑몰 같이 연결이 지속되어야 하는 경우에도 돌려 연결이 자꾸 끊어짐
2. 부하 분산 장치를 이용해 복수의 웹 서버로 분할된다
- 이를 해결하기 위해 부하 분산 장치 (로드 밸런서, Load Balancer) 사용
- 부하 분산 장치의 IP를 DNS 서버에 등록
- 대화가 복수 페이지에 걸쳐 있지 않음 (단순 액세스)
- 웹 서버의 부하 상태 확인 (시험 패킷 혹은 지속적 정보 교환) 후 가장 부하가 적은 곳에 리퀘스트 보냄
- 복수 페이지에 걸쳐 있는 경우
- HTTP는 하나의 리퀘스트 당 하나의 TCP 연결을 수립하고 끊음 → 연결되지 않음
- 송신처 IP를 사용하더라도 프록시와 같은 것 때문에 제대로 된 클라이언트의 송신처 IP를 받기 쉽지 않음
- 해결
- 리퀘스트 안에 전후 상황 관련 정보를 부가
- HTTP 사양을 확장하여 (쿠키) 전후 관계 정보를 HTTP 헤더에 부가
STORY 4. 캐시 서버를 이용한 서버의 부하 분산
1. 캐시 서버의 이용
- 같은 기능 여러대 서크랄버 설치 외에 역할별로 서버를 나누는 방법도 존재 → 캐시 서버
- 캐시는 프록시 이용 → 클라이언트와 서버 사이에서 존재하고, 캐시에 존재하는 데이터면 바로 클라이언트로 보냄으로써 서버 부하 및 응답 속도를 높임
2. 캐시 서버는 갱신일로 콘텐츠를 관리한다
- 캐시 서버를 웹 서버 대신 DNS 서버에 등록
- 캐시에 데이터 없는 경우
- 웹 서버에 요청
- 이 때 서버가 한대라면 바로 보내면 되지만, 여러대일 경우 URI를 보고 어디 서버로 요청 보낼지 결정하는 설정이 필요
- 서버로부터 응답을 받고, 이를 캐시에 저장한 뒤 클라이언트로 전송
- 데이터 저장된 경우
- 웹 서버로 If-Modified-Since 헤드 필드를 추가하여 전송
- 만약 수정되지 않았다면
- 서버로부터 304 Not Modified 메시지가 옴 → 수정할 필요 없음
- 캐시에서 데이터 꺼내서 클라이언트로 전송
- 만약 수정되었다면
3. 프록시의 원점은 포워드 프록시이다
- 위 방법은 프록시 구조를 웹 서버쪽에 둔 것
- 클라이언트 쪽에 캐시 서버를 두는 것도 존재 → 포워드 프록시
- 원래 방화벽을 실현하기 위해 존재한 것이었음
- 브라우저에 프록시 서버를 등록하면 요청시 무조건 프록시 서버를 거침
- 원래는 URI에 디렉토리만 파싱되서 요청이 가지만, 프록시 서버를 거치면 http://~~ 전체가 가게 됨
- URL이 전체가 있으므로 URL이 전송 대상이 됨
4. 포워드 프록시를 개량한 리버스 프록시
- 그러나 포워드 프록시는 매번 브라우저에 등록해야했고, 제대로 동작하지 않을 수 있었음
- 브라우저에 프록시를 등록하지 않아도 되는 방식 개량
- URI가 보통 리퀘스트 메시지와 같이 보낼 수 있음
- 캐시 서버가 채택한 방식 → 리버스 프록시
5. 트랜스페어런트 프록시
- IP 헤더에는 수신처 IP 주소가 있으므로, 액세스 대상 웹 서버가 어디 있는지 알 수 있음 → 트랜스페어런트 프록시
- 브라우저에 프록시 서버를 등록할 필요 없고, 캐시 서버에서도 전송 대상을 직접 설정할 필요 없음
- DNS 서버에 따로 등록하지 않기 때문에 프록시를 거치지 않고 그냥 흘러갈 수도 있음
- 브라우저에서 웹 서버로 가는 길목에 프록시 설치 → 가로챔
- 장점
- 사용자가 프록시의 존재를 알 필요가 없이 캐싱의 장점을 수용 가능
STORY 5. 콘텐츠 배포 서비스
1. 콘텐츠 배포 서비스를 이용한 부하 분산
- 서버측에 캐시를 두는 것 → 웹 서버의 부하를 줄일 수는 있지만 인터넷의 트래픽은 줄지 않음
- 클라이언트측에 캐시 → 인터넷의 트래픽은 줄지만 웹 서버 운영자가 캐시 서버를 제어할 수 없음
- 프로바이더와 계약해서 캐시 서버를 클라이언트의 프로바이더에 두는 것
- 인터넷 트래픽 억제 및 캐시 서버 제어가 가능
- 문제
- 서버는 인터넷의 어디에서 액세스하는지 알수 없음 → 프로바이더 전부에 캐시 서버를 설치해야함 → 비현실적
- 만약 중요한 프로바이더부터 한다고 해도 비용이 많이 듦
- 캐시 서버를 설치하고 이를 웹 서버 운영자에게 대출하는 방식 → 콘텐츠 배포 서비스 (Content Delivery Service, CDS)
- 사업자 CDSP는 중요한 프로바이더와 계약 후 다수 캐시 서버 설치
- 웹 서버 운영자와 계약하여 캐시 서버를 연대시킴
- 비용 측면에서 효율적
2. 가장 가까운 캐시 서버의 관점
- CDS를 사용하는 경우 인터넷 전체에 다수 캐시 서버가 분포되어 있음
- 이 중 클라이언트에서 가장 가까운 캐시 서버를 액세스하도록 중재하는 구조 필요
- 첫번째 방법 → 로드 밸런서와 비슷한 방법
- 각 캐시 서버의 경로 정보를 저장해놓음
- 클라이언트 측의 DNS 서버에 이르는 경로를 경로표를 통해 계산
- 가장 가까운 캐시 서버의 IP 주소를 클라이언트 측 DNS 서버로 리턴
-
3. 리피터용 서버로 액세스 대상을 분배한다
- HTTP 헤더에 Location 헤더를 이용 ← 웹 서버의 데이터를 다른 곳에 옮기는 경우 사용 - 리다이렉트
- 웹 서버의 DNS 서버에 리다이렉트용 서버 IP 주소 등록
- 클라이언트 요청
- 클라이언트 DNS에서 웹 서버의 IP 주소 조회
- 리다이렉트용 서버의 IP 주소 회답
- 리퀘스트 메시지 리다이렉트용 서버로 전송
- HTTP 응답 메시지 받음 (리다이렉트)
- 리퀘스트 메시지를 가장 가까운 캐시 서버로 전송
- HTTP 메시지의 양이 많아져 오버헤드 증가
- 그러나 리다이렉트는 클라이언트 HTTP 메시지의 송신처 주소를 바탕으로 거리 판단하므로 정밀도 높음
4. 캐시 내용의 갱신 방법에서 성능의 차이가 난다
- 원래 캐시에서는 두번째 접근 이후에서도 웹 서버에 갱신 여부를 확인 → 혼잡하게 되면 응답 시간 악화
- 따라서 웹 서버에서 데이터 갱신 시 즉시 캐시 서버에 반영하여 갱신 여부를 확인하지 않게 만들어야 효과적
- 다음 장에서 알려줌
https://product.kyobobook.co.kr/detail/S000000559964