동일 출처 정책

This translation is incomplete. Please help translate this article from English

동일 출처 정책(same-origin policy)은 어떤 출처에서 불러온 문서나 스크립트가 다른 출처에서 가져온 리소스와 상호작용하는 것을 제한하는 중요한 보안 방식입니다. 동일 출처 정책은 잠재적으로 해로울 수 있는 문서를 분리해, 공격받을 수 있는 경로를 줄입니다.

출처의 정의

두 URL의 프로토콜, 포트(명시한 경우), 호스트가 모두 같아야 동일한 출처라고 말합니다. "scheme/host/port 튜플"이나 그냥 "튜플"("튜플"은 3개 이상의 요소가 전체를 구성하는 집합을 말합니다)이라고 하기도 합니다.

아래 표는 URL http://store.company.com/dir/page.html의 출처를 비교한예시입니다.

URL 결과 이유
http://store.company.com/dir2/other.html 성공 경로만 다름
http://store.company.com/dir/inner/another.html 성공 경로만 다름
https://store.company.com/secure.html 실패 프로토콜 다름
http://store.company.com:81/dir/etc.html 실패 포트 다름 (http://는 80이 기본값)
http://news.company.com/dir/other.html 실패 호스트 다름

file: URL을 위한 동일 출처 정책도 참고하세요.

출처 상속

about:blankjavascript:URL이 있는 페이지에서 실행된 스크립트는 해당 URL로 열린 문서의 출처를 상속합니다. 왜냐하면 이러한 유형의 URL들은 명시적으로 서버의 출처가 포함되어 있지않기 때문입니다. 예를 들어, about:blank는 부모 스크립트가 내용을 작성하는 빈 팝업 창에 자주 쓰입니다. 팝업 창에 코드가 포함되어 있으면, 해당 코드는 만들어진 스크립트와 동일한 출처를 상속합니다. data:URL들은 비어있는 새 보안 컨텍스트를 얻습니다.

IE 예외사항

Internet Explorer는 동일 출처 정책에 두 가지 중요한 예외사항이 있습니다.

  • Trust Zones: 두 도메인이 highly trusted zone에 속하면(기업도메인 같은) 동일 출처 제약이 적용되지 않는다.
  • Port: IE는 포트는 비교하지 않는다. 따라서 http://company.com:81/index.htmlhttp://company.com/index.html은 동일출처로 여기며 제약이 적용되지 않는다.

위의 예외는 비표준이고 다른 브라우저에는 해당하지 않습니다.

출처 변경

일부 제약이 있긴 하지만 페이지의출처를 변경하는 것이가능하다. 스크립트로document.domain 의 값을 현재 도메인이나 현재 도메인의상위 도메인으로 변경할 수 있다. 만약 도메인을현재 도메인의 상위도메인으로 변경하면,보다 짧은 도메인이 이후의출처 확인에 사용된다. 예를 들어http://store.company.com/dir/other.html문서의 스크립트가아래의 문장을 실행하면:

document.domain = "company.com";

문장이 실행된 이후에 페이지는 출처 체크에http://company.com/dir/page.html 를 보낸다. 참고로,document.domain의 값을company.com이 아닌othercompany.com 으로 설정할 수는 없다. 왜냐하면othercompany.comstore.company.com의 상위 도메인이 아니기 때문이다.

포트 번호는 브라우저별로 유지된다. document.domain = document.domain을 포함한 setter에 대한 모든 호출은 포트 번호를 null로 덮어쓸 것이다. 따라서 처음에document.domain = "company.com" 만을 설정한다고 해서 company.com:8080company.com과 통신할 수는 없다. 양쪽 포트가 모두 null이 되도록 설정되어야 한다.

참고:부모가 안전하게 접근하도록 하기 위해document.domain을 사용한다면, 부모 도메인과 서브 도메인의document.domain을 같은 값으로 설정해야 한다. 단순히 부모 도메인이 원래 값으로 설정되는 것이라고 해도 필수적이다. 이를 수행하는데 실패하면 권한 오류가 발생할 수도 있다.

Cross-origin 네트워크 접근

동일 출처 정책은 당신이 XMLHttpRequest 혹은<img> 요소를 사용할 때와 같은 두개의 다른 출처간의 상호작용을 조절한다. 이 상호작용들은 일반적으로 세개의 카테고리에 존재한다:

  • Cross-origin writes 는 일반적으로 허용된다. 링크, 리디렉션과 폼 sumissions가 그 예들이다. 아주 간혹 사용되는 특정 HTTP 요청에는 preflight가 필요하다.
  • Cross-origin embedding 은 일반적으로 허용된다. 아래에 예제들이 있다.
  • Cross-origin reads 는 일반적으로는 허용되지 않으나, 읽기 접근은 종종 임베딩에 의해 유출된다. 예를 들어 임베드된 이미지의 폭과 너비, 임베드된 스크립트의 액션,임베드된 리소스의 가용성을 읽을 수 있다.

아래에는 임베드된 cross-origin 일지도 모르는 몇가지 리소스의 예제들이 있다:

  • <script src="..."></script>를 사용한 자바스크립트. 구문 오류에 의한 오류 메시지는 오직 같은 출처의 스크립트에서만 가능하다.
  • <link rel="stylesheet" href="...">을 사용한 CSS. CSS의relaxed syntax rules때문에, cross-origin CSS는 올바른Content-Type헤더가 필요하다. 제한은 브라우저에 따라 다르다: IE, Firefox, Chrome, Safari (CVE-2010-0051으로 스크롤 다운) 과Opera.
  • <img> 을 사용한 이미지. 지원되는 이미지 포맷은 다음을 포함한다 : PNG, JPEG, GIF, BMP, SVG, ...
  • <video><audio> 를 사용한 미디어 파일.
  • <object>, <embed><applet>을 사용한 플러그인.
  • @font-face를 사용한 폰트.몇몇 브라우저는 cross-origin 폰트를 허용하나, 그 외에는 동일 출처 폰트가 필요하다.
  • <frame><iframe>을 사용한 것. 사이트는 cross-origin 상호작용의 폼을 방지하기 위해 X-Frame-Options헤더를 사용할 수도 있다.

Cross-origin 접근을 허용하는 방법

CORS를 사용해 cross-origin 접근을 허용한다.

Cross-origin 접근을 방지하는 방법

  • cross-origin 쓰기를 막으려면,Cross-Site Request Forgery (CSRF)토큰과같이,예측 불가능한 토큰을 요청에서확인한다. 이 토큰을 알고있는 페이지에 대한cross-origin 읽기는 무조건 막아야 한다.
  • cross-origin 리소스 읽기를 막으려면 그 리소스를 임베딩이가능하지 않게 하면된다. 리소스가 임베딩되면 항상그정보가 새어나가는 것에 취약하기 때문에,임베딩을 막는 것은 종종 필요하다.
  • cross-origin 임베딩을 막으려면, 리소스가 위의 임베딩 가능한 포맷 중의 하나로 해석될 수 없는지 확인한다. 대부분의 경우에 브라우저는 Content-Type을 지키지 않는다. 예를 들어 HTML 문서의 <script> 태그를 가리켰을 때, 브라우저는 HTML을 자바스크립트로 바꾸려고 할 것이다. 리소스가 사이트의 입구가 아닐 때에는 CSRF 토큰을 사용하여 임베딩을 방지할 수도 있다.

Cross-origin 스크립트 API 접근

JavaScript APIs such as iframe.contentWindow, window.parent, window.open and window.opener allow documents to directly reference each other. When the two documents do not have the same origin, these references provide limited access to the Window and Location objects. Some browsers allow access to more properties than the spec allows. You can use window.postMessage instead to communicate between documents.

Cross-origin 데이터 저장소 접근

Access to data stored in the browser such as localStorage and IndexedDB are separated by origin. Each origin gets its own separate storage, and JavaScript in one origin cannot read from or write to the storage belonging to another origin.

The window.name property can be used to temporarily store data, that can be accessed cross-origin.

Cookies use a separate definition of origins. A page can set a cookie for its own domain or any parent domain, as long as the parent domain is not a public suffix. Firefox and Chrome use the Public Suffix List to determine if a domain is a public suffix. Internet Explorer uses its own internal method to determine if a domain is a public suffix. The browser will make a cookie available to the given domain including any sub-domains, no matter which protocol (http/https) or port is used. When you set a cookie, you can limit its availability using the Domain, Path, Secure and Http-Only flags. When you read a cookie, you cannot see from where it was set. Even if you use only secure https connections, any cookie you see may have been set using an insecure connection.

함께 보기

Original Document Information

  • Author(s): Jesse Ruderman