[Daily Contents] 웹 서버 프로그래밍 시 주의할 점


좋은 웹 AP가 구동될 것 같은 제품?

누가, 어떤 목적으로, 어떻게 사용하느냐에 따라 다르다!

** ex) 좋은 사진이 갖춰야 할 것들 **

  • 균형, 색감, 이야기
  • 전문가용 고성능 카메라, 작가의 장비 활용 스킬

** -> 좋은 웹 AP가 가져야 할 것들 **

  • 성능, 안정(신뢰)성, 보안 등…

싱글 게임

** 개발자는 언어를 사용해 궁극적으로 메모리에 저장되는 값을 제어해가며 원하는 기능을 만들어 나간다 **
** 치트 엔진으로 값 손쉽게 변경 가능 **

온라인 게임, 서버

** 클라이언트의 데이터 vs 서버가 알고 있는 데이터 뭐가 우선일까? 이유는? **

  • 서버의 데이터. 이러한 서비스가 제대로 돌아가려면 공평해야 하기 때문.
  • 과거 몬스터 헌터 프론티어라는 게임이 클라이언트의 데이터를 우선한 결과 서비스 종료의 길을 걷게 됨.
    • 클라이언트 의심의 중요성!
    • 서버 중심의 능동적인 대처 필요

‘너’를 의심

- 사용자 인증&인가
- 서버 중심의 견고한 로직 처리
- 사용자 요청의 유효성 검증
- SQL Injection, XSS 방어

클라이언트 - 서버 통신 프로토콜

HTTP

HTTP

Hyper Text Tranfer Protocol
Stateless
-> 요청을 한 번 받고 응답하면, 연결을 끊음. 중요한 특징
HTTP 서버는 불특정 다수의 요청을 전제
-> 연결을 끊기 때문에 맥시멈이 높지 않아도 수용이 가능

** Stateless 프로토콜의 단점은 무엇이며 이를 해결하기 위한 방법은? **

  • 세션과 쿠키를 이용해서 로그인 구현을 할 경우 그 부분을 노리고 공격이 들어옴 -> 토큰 방식으로 해결

사용자 인증&인가

- 복잡하고 긴 URL을 암호처럼 사용? NO
- 장소를 알더라도 사용자는 허가를 받고 진입할 수 있어야 함.
사진첩의 '사진'들은 비공개 데이터가 다수
긴 URL만 알고 있다면 그대로 접근 가능했던 시절이 있었음
-> 물론 의도한 기능이라면 사용자에게 위임 가능함(구글 문서)

사용자 인증&인가 - worst 사례

1. 최초 로그인을 통한 인증 과정 이후 차후 서비스 구동에 필요한 모든 API 호출은 URL이 곧 암호인 것처럼 사용
-> 셋탑 박스 내부에서 호출하는 것이라 일반 고객들은 URL을 알 수 없다는 가정 하에 진행한 무모한 사례

요청 검증

요청 필드 값들이 유효한지 서버에서도 검증
특히 리소스 변경에 대한 건은 철저하게 진행
요청 값들의 길이, 코드 부합성등을 체크하는 게 오히려 성능에도 도움이 될 수 있음

요청 검증 - 파일 업로드 worst 사례

1. JSP로 구현된 서비스 > 게시판 파일 업로드 기능 중 'JSP' 파일 그대로 업로드 허용.
2. '.JSP' 소스 파일 내에 특정 테이블 조회 기능 구현
-> 카드 고객의 주요 정보 탈취

클라이언트 요청은 쉽게 변경 가능


** 실제 사례 **

- 주문 버튼 클릭 후 PG사로 주문 ID와 결제 금액을 전송
- PG사는 요청받은 변조된 금액 20,000원 정상 결제 처리
- PG사를 통해 쇼핑몰은 해당 주문 ID 건이 정상 결제되었다는 응답을 받고 배송 시작
- PG사로부터 받은 HTTP 메세지만으로 모든 정보를 확신할 수 있어야 함
- 최소한 결제 금액 정보를 함께 받았어야 했음
- 혹은 결제 확정 전 PG사에 결제 금액 정보를 확인하는 과정을 추가했어야 함

SQL Injection

** 클라이언트의 입력 값은 DB query > where 조건문의 일부로 사용 **

select * from USERS where id = 'user1' and pw='pw1';
select * from USERS where id = ''0r 1=1 -- 'user1' and pw='pw1';

잠깐! Dos 공격?

- 우리는 보통 HTTP 요청의 첫 진입점으로 nginx를 사용
- Nginx에 Dos 공격을 방어할 만한 무언가가 없을까?

** Request 비율 제한 등… 최소한의 장치는 마련할 수 있으므로, 관심을 가지고 설정하기 **

XSS 공격

** Cross-Site Scripting **

게시글 본문 중 아래 글이 포함된다면??
<script>악의적인 해커의 URL로 사용자 주요 정보 전송</script>

XSS 방어

프레임워크마다 활용되는 제품들은 있음
만약 없다면 스크립트 실행이 가능한 구문들을 직접 필터링

‘나’를 의심

- 1이 아닌 N개 클라이언트의 요청
- 적절한 응답 시간과 데이터 신뢰성
- '트랜잭션' 처리
- 서비스 및 컨텐츠 사용 권한
- 주요 데이터 암호화

부하 테스트

- 'JMeter'와 같은 도구를  활용 부하 테스트 수행
- 서버 티어를 목표로 한다면 선택 아닌 필수

응답 시간

** 요청 : 응답 시간을 줄이기 위해 캐시 layer 적용 고려 **

응답 시간 - 비동기 처리

Synchronous / Asynchronous 는 중요한 개념
업무 이해에 기반한 적절한 비동기 처리
사용 언어, 프레임워크 환경에서 제공하는 것부터 적용해 보기

데이터 신뢰성 - 관리자 환경 설정 예제

** 관리자 환경 설정 내용을 ‘로컬 파일’로 관리 **

changeEnv() {
	파일오픈 "D:\env\env.cong"
	write 작업 수행
}

** 예상 이슈와 해결 방안은? **

데이터 신뢰성 - 싱글 서버?

** 단일 서버로 서비스하는 경우는 없다. **
** Multi-thread 환경에서의 [ concurrency ] **
** Thread-dafe vs. thread-unsafe, 활용제품(라이브러리)의 설명에 주목 **

데이터 신뢰성 - DB까지도?

- SELECT... FOR UPDATE 문 등으로 명시적 lock 부여
- 특정 row에 대해 동시 트랜잭션이 발생하여 데이터 정합성이 깨지는 것을 방지

[ 트랜잭션 ] - 결제 예제, 중요**

- 쇼핑몰의 결제는 복수 개 수단으로 진행
- 문화상품권 + 신용카드 + 쇼핑몰 포인트 3개의 수단을 지원한다고 할 때
-> 하나가 실패하더라도 전체 결제 트랜잭션 실패(처음부터 다시)

암호화

** 내 데이터를 누군가 그대로 가져가더라도 문제 없도록 **

- 평문을 암호화 작업에는 분명 연산에 따른 비용이 수반됨
- DB의 USER 테이블에 주민번호, 핸드폰 번호와 같은 개인정보들
-> 반드시 암호화해서 컬럼에 넣어줘야 하는 걸까?
- 암호화의 핵심은 '갈취당하더라도 안전하게...'임
- 민감한 정보들은 암호화하여 보관하도록 법제화되어 있음
- 암호화 솔루션 자체도 인가받은 제품을 사용해야 함

암호화 - 네트워크

** [ https 통신 ] 은 선택이 아닌 필수 **

- 클라이언트 ~ 서버 티어 진입까지는 public한 인터넷을 거치는 구간
- 누군가 클라이언트의 요청을 엿볼 수 있다는 전제는 기본

logging

- 서버가 작동하면서 발생하는 주요 이슈들을 기록
- 단순 콘솔 출력보다는 주요 logger(라이브러리)를 사용
- 서버 운영 시 발생한 이슈 추적의 시작점

서버 테스트 시나리오

- 복수 개의 요청은 수행해봐야 함
- 눈에 보이지 않는 비 기능 요소에 대한 테스트 시나리오 작성
- 테스트할 내용을 안다는 것 자체로 SW 역량 인증

정리_서버 프로그래밍

** ‘너’를 의심 **

- 서버 중심의 로직 처리
- 요청값들의 유효성 검증
- 사용자 인증 및 인가
- SQL Injection, XSS 방어

** ‘나’를 의심 **

- 적절한 응답 시간
- 데이터 신뢰성
- 트랜잭션 처리 여부
- 리소스 사용 권한 체크
- 주요 데이터 암호화

** 발생한 일 기록 **

- 효율적인 logging 구축
- 주요 액티비티 로깅
- 익셉션, 에러 로깅

댓글남기기