
웹 서비스 개발 – API 개발 기초 – API 인증과 보안
안녕하세요! 😊
오늘은 API 개발에서 절대 빼놓을 수 없는 핵심 주제, 바로 **“API 인증과 보안”**에 대해 다뤄보겠습니다.
아무리 좋은 API라도 보안이 허술하면?
🚨 민감한 사용자 정보가 유출되고, 해킹에 노출되고, 시스템이 다운될 수 있어요!
그래서 API를 설계하고 만들 때는 **인증(Authentication)**과 권한(Authorization) 그리고 **보안(Security)**을 철저히 챙겨야 합니다!
1. API 인증(Authentication)과 권한(Authorization)의 차이
우선 용어부터 깔끔하게 정리해볼게요.
용어 | 의미 | 비유 |
---|---|---|
인증 (Authentication) | “너 누구야?” 신원 확인 | 아파트 입구 출입카드 |
권한 (Authorization) | “너 여기 들어가도 돼?” 접근 제어 | 아파트 층별 버튼 권한 |
인증이 먼저, 권한이 나중입니다.
즉, 로그인하고 나서, 어디까지 가능한지가 결정되는 거죠.
2. API 인증 방식 종류
✅ 1) API Key 방식 (간단 인증)
- URL 또는 헤더에 API 키를 포함해서 인증
- 매우 간단하고 빠름
GET /users?api_key=123abc
또는
GET /users
Authorization: ApiKey 123abc
🔐 장점: 설정 간편
⚠️ 단점: 노출 위험, 사용자 기반 제어 어려움
✅ 2) Basic Auth (기본 인증)
- 사용자 이름과 비밀번호를 base64로 인코딩하여 헤더에 포함
Authorization: Basic dXNlcjpwYXNzd29yZA==
🔐 장점: 간단한 테스트용으로 유용
⚠️ 단점: 평문 전송 위험 → 반드시 HTTPS 필수!
✅ 3) OAuth 2.0 (토큰 기반 인증의 표준)
- 제3자 인증 방식
- 대표적으로 카카오, 네이버, 구글 로그인에 사용됨
- Access Token, Refresh Token 등으로 나눠져 있음
예: 사용자가 ‘카카오 계정으로 로그인’ → 카카오가 토큰을 발급 → 내 서버는 그 토큰을 사용해 사용자 인증
🔐 장점: 외부 인증 연동에 탁월
⚠️ 단점: 구현 복잡도 높음
✅ 4) JWT (JSON Web Token)
- 요즘 가장 널리 쓰이는 인증 방식 중 하나
- 사용자가 로그인하면 토큰을 발급하고,
이후에는 매 요청마다 이 토큰을 헤더에 실어 보냄
Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
- 토큰 안에 유저 정보(Claim)가 들어있어 별도 세션 저장 불필요
- Base64로 인코딩된 구조 (header.payload.signature)
🔐 장점: 무상태(stateless), 스케일링에 유리
⚠️ 단점: 토큰 탈취 시 위험, 토큰 만료 처리 필요
3. 인증 로직 흐름 (JWT 예시 기준)
- 사용자가 로그인 → 서버가 비밀번호 확인
- 서버가 JWT 토큰 발급 (
access_token
) - 사용자는 토큰을
Authorization
헤더에 실어 API 요청 - 서버는 토큰의 유효성을 검증 → 성공 시 처리
4. API 보안에서 지켜야 할 기본 수칙
✅ HTTPS 사용은 필수!
- 모든 API는 HTTPS를 기본으로 사용해야 합니다.
- HTTP로 전송하면 토큰, 비밀번호 등이 쉽게 탈취될 수 있어요.
✅ CORS 정책 설정
- 웹 브라우저 기반 API 호출 시, 출처(origin)를 명확히 설정해야 합니다.
Access-Control-Allow-Origin: https://trusteddomain.com
모든 출처를 허용하는
*
설정은 반드시 피해주세요!
✅ 입력 값 검증 (Validation)
- 사용자가 전송하는 데이터는 반드시 서버에서 형식 검증을 해야 해요.
- 예: 이메일 형식, 비밀번호 길이 등
if (!filter_var($email, FILTER_VALIDATE_EMAIL)) {
return ['error' => '올바른 이메일 형식이 아닙니다.'];
}
이는 XSS, SQL 인젝션 등의 공격을 막는 첫 번째 방어선입니다!
✅ 권한 체크
- 인증만으로는 부족해요.
인증된 사용자라 해도 관리자, 일반 사용자, 제한 사용자 등 권한 구분이 필수입니다.
if ($user['role'] !== 'admin') {
http_response_code(403);
echo json_encode(['error' => '접근 권한이 없습니다.']);
}
✅ API Rate Limit 설정
- 특정 사용자 혹은 IP가 너무 많은 요청을 보낼 경우 **요청 제한(Throttle)**을 걸어야 해요.
HTTP/1.1 429 Too Many Requests
Retry-After: 60
무차별 대입 공격, 서버 자원 소모 방지에 효과적입니다!
✅ 민감 정보 암호화 저장
- 사용자 비밀번호는
암호화
가 아닌 해시화(hash) 해야 합니다.
$passwordHash = password_hash($password, PASSWORD_DEFAULT);
- 비교 시엔 아래와 같이:
if (password_verify($inputPassword, $passwordHash)) {
// 로그인 성공
}
md5
나sha1
은 절대 사용하면 안 돼요!
5. 인증 및 보안 적용 예시 (PHP + JWT)
// 로그인 후 JWT 발급
use Firebase\JWT\JWT;
$key = 'secret123';
$payload = [
'user_id' => 1,
'exp' => time() + 3600 // 1시간 후 만료
];
$jwt = JWT::encode($payload, $key, 'HS256');
// API 요청 시 JWT 검증
$headers = getallheaders();
$token = str_replace('Bearer ', '', $headers['Authorization']);
try {
$decoded = JWT::decode($token, $key, ['HS256']);
// 인증 성공
} catch (Exception $e) {
// 인증 실패
http_response_code(401);
echo json_encode(['error' => '토큰이 유효하지 않습니다.']);
}
주의사항 체크리스트 ✅
항목 | 주의할 점 |
---|---|
HTTP | 무조건 HTTPS 사용! |
토큰 저장 | LocalStorage보다는 쿠키(httpOnly, Secure) 권장 |
비밀번호 저장 | 평문 절대 금지, password_hash 사용 |
에러 메시지 | 너무 상세하면 보안 위험 (예: “ID는 맞지만 비밀번호가 틀림” ❌) |
로그 | 로그인 시도, 권한 거부, 토큰 만료 등은 서버에 반드시 기록 |
만료 정책 | Access Token은 짧게, Refresh Token으로 재발급 시스템 구축 |
마무리하며 😊
API 인증과 보안은 절대 나중에 고려할 문제가 아닙니다!
처음 설계할 때부터 철저히 준비하고 대응해야 나중에 큰 사고를 막을 수 있어요.
간단하게 API를 만들더라도 최소한:
- JWT 인증,
- HTTPS,
- 입력 값 검증,
- 권한 체크는 꼭 챙기셔야 해요.
다음 시간에는 **API 테스트 자동화와 디버깅 도구(Postman, curl, Swagger 등)**에 대해 알려드릴게요!
오늘도 안전하고 스마트한 개발자 되세요~ 💪🚀💻
감사합니다! 🙏