여러 사이트 주소 입력 검증: HTTPS와 허용 호스트 확인
여러 사이트를 입력받을 때는 줄 단위로 나누고 URL 구조·허용 호스트·중복을 검증한 뒤 작업 대상으로 확정합니다.
어떤 상황에서 적용하나요?
사용자가 입력한 URL을 그대로 서버에서 요청하면 내부 주소 접근 같은 문제가 생길 수 있습니다. 아래는 자신이 관리하는 두 예시 호스트만 허용하는 로컬 입력 검사이며 실제 접속은 하지 않습니다.
검증 범위: 아래 코드는 외부 서비스에 요청하지 않는 로컬 예제입니다. 실제 서비스 연결은 별도로 검증해야 합니다.
최소 예제로 동작 확인하기
from urllib.parse import urlsplit, urlunsplit
allowed = {"www.example.com", "docs.example.com"}
def targets(text):
result = []
for line in text.splitlines():
if not line.strip():
continue
p = urlsplit(line.strip())
if p.scheme != "https" or p.hostname not in allowed or p.username or p.password:
raise ValueError("허용된 HTTPS 주소만 입력하세요")
if p.port not in (None, 443):
raise ValueError("허용되지 않은 포트")
normalized = urlunsplit((p.scheme, p.netloc.lower(), p.path or "/", p.query, ""))
if normalized not in result:
result.append(normalized)
return result
rows = targets("https://www.example.com/\nhttps://www.example.com/#top")
assert rows == ["https://www.example.com/"]
print(rows)
결과는 어떻게 확인하나요?
동일 페이지의 fragment 차이를 제거한 한 주소가 남습니다. 쿼리 문자열은 의미가 있을 수 있어 그대로 유지합니다. 모든 사이트에 임의의 정규화 규칙을 적용하면 서로 다른 주소를 잘못 합칠 수 있습니다.
실제 업무에 적용할 때 확인할 점
이 검사는 완전한 SSRF 방어가 아닙니다. 서버에서 실제 요청한다면 DNS 해석 결과·리디렉션 대상·사설 IP·응답 크기와 연결 시간을 추가로 검증해야 합니다. 허용 호스트 목록은 요청 입력과 분리해 관리하세요.
공식 자료와 다음 단계
관련 공식 문서에서 사용하는 버전의 기능과 제한을 확인하세요.
학습 경로: 웹 스크래핑 가이드 · 요청 정책과 헤더
작성: 로그 · 2026-10-17 수정: 확인되지 않은 경험담과 성능 보장 표현을 제거하고 예제·적용 조건·공식 근거를 보완했습니다.
댓글
댓글 쓰기