홈 › 개발·웹 도구

CSP 헤더 만들기·검사

운영 사이트에 바로 적용하기보다 Content-Security-Policy-Report-Only 헤더로 며칠 지켜본 뒤 바꾸는 게 안전해요. 막히는 스크립트가 있으면 브라우저 콘솔에 나와요.

입력한 내용은 서버로 보내지 않고 이 기기에서만 처리돼요
점검 결과

지시어별 정리

CSP가 하는 일

Content-Security-Policy(콘텐츠 보안 정책, CSP)는 서버가 브라우저에게 ‘이 페이지에서는 이 출처의 스크립트·스타일·이미지만 써라’라고 알려 주는 HTTP 헤더예요. 공격자가 게시판 글이나 주소창 값으로 <script>를 몰래 끼워 넣어도(XSS), 정책에 없는 스크립트라 브라우저가 실행하지 않아요. 그래서 OWASP 등 보안 가이드에서 꼭 권하는 보안 헤더예요. 정책은 지시어 출처 출처; 지시어 출처 형식이에요.

정책 검사

쓰고 있는 정책을 붙여넣으면 지시어별로 정리하고, 흔한 약점을 위험·주의·참고로 나눠 알려 줘요. 대표적인 위험은 script-src의 'unsafe-inline'(끼워 넣은 스크립트도 실행), *·https:·data: 같은 넓은 출처, 그리고 script-src와 default-src가 모두 없는 경우예요. object-src 'none'과 base-uri가 빠진 것도 우회 통로가 될 수 있어 알려 줘요. 키워드에 작은따옴표를 빠뜨리면(self) 브라우저는 ‘self’라는 이름의 사이트로 읽어서 의도와 다르게 동작해요.

새로 만들기

템플릿을 고른 뒤 칸을 고치면 헤더가 바로 만들어지고, nginx(add_header … always;), Apache(Header always set), HTML meta 태그 형식으로 바꿔 복사할 수 있어요. 가장 안전한 방식은 ‘엄격(nonce)’ 템플릿처럼 요청마다 바뀌는 nonce 값을 스크립트 태그와 헤더에 함께 넣는 것인데, 서버 코드가 필요해요. 정적 사이트라면 ‘기본’ 템플릿에서 시작해 필요한 외부 주소만 더하세요.

점검 규칙은 W3C CSP Level 3 명세와 MDN·OWASP 안내를 바탕으로 했지만, 사이트마다 필요한 출처가 다르기 때문에 경고가 없다고 완벽히 안전한 것은 아니에요. 적용 전에는 Content-Security-Policy-Report-Only로 시험하세요. 정책은 이 브라우저 안에서만 분석해요.

참고한 자료

자주 묻는 질문

적용했더니 사이트 일부가 안 나와요.

브라우저 개발자 도구 콘솔에 ‘Refused to load …’로 막힌 주소가 나와요. 그 출처를 해당 지시어(script-src, img-src 등)에 더하세요.

인라인 스크립트를 꼭 써야 하는데요?

'unsafe-inline' 대신 스크립트 내용의 SHA-256 해시('sha256-…')나 nonce를 넣으면 그 스크립트만 허용돼요. ‘해시 생성기’로 해시를 만들 수 있어요.

X-Frame-Options 헤더와 무엇이 다른가요?

둘 다 클릭재킹을 막지만 CSP의 frame-ancestors가 더 새롭고 여러 사이트를 지정할 수 있어요. 오래된 브라우저를 위해 둘 다 보내도 돼요.

함께 쓰면 좋은 도구