bestsource

XMLHttpRequest에서 XXX No 'Access-Control-Allow-Origin' 헤더를 로드할 수 없습니다.

bestsource 2023. 9. 21. 20:40
반응형

XMLHttpRequest에서 XXX No 'Access-Control-Allow-Origin' 헤더를 로드할 수 없습니다.

tl;dr; 동일 오리진 정책 정보

express.js 서버의 인스턴스를 시작하는 Grunt 프로세스가 있습니다.Chrome(최신 버전)의 개발자 콘솔에 다음과 같은 오류 로그가 표시되는 빈 페이지를 제공하기 시작했을 때까지만 해도 이것은 완전히 잘 작동하고 있었습니다.

XMLHttpRequest가 https://www.example.com/ 을 로드할 수 없습니다. 요청한 리소스에 'Access-Control-Allow-Origin' 헤더가 없습니다.따라서 오리진 'http://localhost:4300'은(는) 접근이 허용되지 않습니다.

무엇이 내가 그 페이지에 접속하지 못하게 합니까?

tl;dr — 주로 클라이언트JS를 사용하여 데이터를 읽으려면 데이터를 원하는 코드에 명시적인 권한을 부여하기 위해 데이터가 있는 서버가 필요합니다.

답변 끝에 요약과 제목이 있어 해당 부분을 쉽게 찾을 수 있습니다.모든 것을 읽는 것이 좋지만, 다른 상황에서 어떻게 적용되는지를 쉽게 볼 수 있는 이유를 이해하는 데 유용한 배경을 제공하기 때문입니다.

동일한 오리진 정책 정보

이것은 동일한 오리진 정책입니다.브라우저에서 구현하는 보안 기능입니다.

수 ), 는 XMLHtpRequest (), (: ) 됩니다에 <canvas>할 수 있습니다.<iframe> 약간 입니다.), .

SOP의 필요성을 보여주는 표준 시나리오는 세 가지 문자로 설명할 수 있습니다.

  • 앨리스는 웹브라우저를 가진 사람입니다.
  • 밥 합니다)를 운영합니다https://www.example.com/예를 들어)
  • 맬로리는 웹사이트를 운영합니다.http://localhost:4300예를 들어)

앨리스는 밥의 사이트에 로그인되어 있고 거기에 몇 가지 기밀 자료가 있습니다.아마도 회사 인트라넷(LAN의 브라우저에서만 액세스 가능)이거나 그녀의 온라인 뱅킹(사용자 이름과 비밀번호를 입력한 후 쿠키를 통해서만 액세스 가능)일 것입니다.

앨리스는 Alice의 브라우저가 Bob의 웹사이트에 HTTP 요청을 하게 하는 자바스크립트가 있는 Mallory의 웹사이트를 방문합니다.이것은 사용하는 것만큼 간단할 수 있습니다.XMLHttpRequestg을 읽습니다.responseText.

브라우저의 동일한 오리진 정책은 자바스크립트가 Bob의 웹사이트(Bob과 Alice는 Mallory가 액세스하는 것을 원하지 않음)에서 반환된 데이터를 읽지 못하도록 합니다.(예를 들어, 이미지를 표시할 수 있습니다.<img>이미지의 내용이 JavaScript(또는 Mallory)에 노출되지 않기 때문에 오리진 전반에 걸친 요소입니다. 이 경우 혼합물에 캔버스를 던지지 않으면 동일 오리진 위반 오류가 발생합니다.)


동일 오리진 정책이 적용되지 않아야 한다고 생각하는 이유

특정 URL의 경우 SOP가 필요하지 않을 수 있습니다.이 경우 몇 가지 일반적인 시나리오는 다음과 같습니다.

  • 앨리스, 밥, 말로리는 같은 사람입니다.
  • 밥은 완전히 공개적인 정보를 제공하고 있습니다.

… 그러나 브라우저는 위 두 가지 중 어느 하나라도 사실인지 알 방법이 없어 신뢰가 자동화되지 않고 SOP가 적용됩니다.브라우저가 Bob으로부터 받은 데이터를 다른 웹사이트에 제공하기 전에 사용 권한을 명시적으로 부여해야 합니다.


웹 페이지의 JavaScript에 동일한 오리진 정책이 적용되지만 다른 것은 거의 적용되지 않는 이유

웹 페이지 외부

*, 브라우저 개발자 도구의 네트워크 탭과 Postman과 같은 응용 프로그램은 설치된 소프트웨어입니다.단지 당신이 다른 웹사이트를 방문했다고 해서 한 웹사이트의 데이터를 다른 웹사이트에 속한 자바스크립트로 전달하는 것은 아닙니다.소프트웨어를 설치하는 것은 보통 좀 더 의식적인 선택이 필요합니다.

위험으로 간주되는 제3자(말로리)는 없습니다.

*브라우저 확장자는 교차 오리진 문제를 방지하기 위해 주의 깊게 작성되어야 합니다.를 들어 Chrome 설명서를 참조합니다.

웹페이지 내부

대부분의 경우, 웹 페이지에 무엇인가를 보여줄 때 정보 유출이 많지 않습니다.

하는 경우<img>이미지를 로드하는 요소가 페이지에 표시되지만 맬로리에 노출되는 정보는 거의 없습니다.자바스크립트는 이미지를 읽을 수 없습니다(사용자가 a를 사용하지 않는 한).crossOriginCORS)로 요청 권한을 명시적으로 활성화하도록 속성을 지정한 다음 서버에 복사합니다.

그렇기는 하지만, 일부 정보는 유출되기 때문에, (구글의) 도미니크 데니콜라의 말을 인용하면 다음과 같습니다.

웹의 기본 보안 모델은 동일한 오리진 정책입니다.보안 모델이 구축되기 전부터 이 규칙에 대한 몇 가지 기존 예외 사항이 있습니다. 스크립트 태그는 가장 터무니없고 위험한 것 중 하나입니다.(다양한 "JSONP" 공격 참조)

수년 전, 아마도 XHR이나 웹 폰트의 도입으로 (정확하게는 기억할 수 없습니다), 우리는 모래 위에 선을 그었고, 어떤 새로운 웹 플랫폼 기능도 동일한 오리진 정책을 위반하지 않을 것이라고 말했습니다.기존 기능은 웹을 차단하지 않기 위해 신중하게 다듬고 자주 이용하는 예외를 적용할 필요가 있지만, 보안 정책에 구멍을 더 이상 추가할 수는 없습니다.

이것이 오리진 전체에 글꼴을 로드하려면 CORS 권한이 필요한 이유입니다.


데이터를 JS로 읽지 않고 페이지에 표시할 수 있는 이유

하게 할 수 Mallory 의3 (: ).<img>이미지를 표시할 요소).Mallory의 JavaScript는 해당 리소스의 데이터를 읽을 수 없지만 Alice의 브라우저와 Bob의 서버만이 데이터를 읽을 수 있으므로 여전히 안전합니다.


코르스

Access-Control-Allow-Origin오류 메시지에서 언급되는 HTTP 응답 헤더는 Bob이 Alice의 브라우저를 통해 데이터에 액세스할 수 있는 권한을 Mallory의 사이트에 명시적으로 부여할 수 있는 CORS 표준의 일부입니다.

기본적인 구현은 다음과 같습니다.

Access-Control-Allow-Origin: *

… 모든 웹 사이트가 데이터를 읽을 수 있도록 허용하는 응답 헤더.

Access-Control-Allow-Origin: http://example.com

특정 수 있도록 은 … Bob 를 할 수 .Origin 모든 사이트가 아닌 여러 사이트에서 액세스할 수 있도록 요청합니다.

Bob이 응답 헤더를 설정하는 방법은 Bob의 HTTP 서버 및/또는 서버측 프로그래밍 언어에 따라 달라집니다.Node.js/Express.js 사용자는 잘 문서화된 CORS 미들웨어를 사용해야 합니다.다른 플랫폼 사용자는 도움이 될 수 있는 다양한 공통 구성에 대한가이드 모음을 살펴봐야 합니다.

Model of where CORS rules are applied

NB: 일부 요청은 복잡하며 브라우저가 JS가 원하는 GET/POST/PUT/무엇이든 요청하기 전에 서버가 응답해야 하는 비행 옵션 요청을 보냅니다.추가만 가능한 CORS 구현Access-Control-Allow-Origin특정 URL들은 종종 이것에 의해 걸려 넘어집니다.


분명히 CORS를 통해 허가를 받는 것은 밥이 다음 중 하나를 수행할 경우에만 할 수 있는 일입니다.

  • 데이터가 개인 정보가 아니었거나
  • 맬로리는 믿었습니다

이 머리글을 추가하려면 어떻게 해야 합니까?

서버측 환경에 따라 다릅니다.

가능하다면 CORS를 처리할 수 있도록 설계된 라이브러리를 사용하면 모든 것을 수동으로 처리할 필요 없이 간단한 옵션을 제공할 수 있습니다.

Enable-Cors.org 에는 유용한 특정 플랫폼 및 프레임워크에 대한 설명서 목록이 있습니다.

하지만 난 밥이 아닙니다!

맬로리가 이 헤더를 추가할 수 있는 표준 메커니즘은 없습니다. 왜냐하면 그것은 밥의 웹사이트에서 온 것이고, 그녀는 그것을 통제하지 않기 때문입니다.

Bob이 공용 API를 실행 중인 경우 CORS를 켜는 메커니즘이 있을 수 있습니다(특정 방식으로 요청을 포맷하거나 Bob의 사이트에 대한 Developer Portal 사이트에 로그인한 후 구성 옵션).하지만 이것은 Bob에 의해 실행되는 메커니즘이어야 할 것입니다.맬로리는 밥의 사이트에 있는 문서를 읽어서 이용 가능한 것이 있는지 확인하거나, 밥에게 말을 걸어 CORS를 시행해달라고 요청할 수도 있습니다.


"사전 비행에 대한 응답"을 나타내는 오류 메시지

일부 교차 오리진 요청은 미리 발송됩니다.

이는 (대략적으로 말하면) 다음과 같은 교차 오리진 요청을 하려고 할 때 발생합니다.

  • 쿠키와 같은 자격 증명 포함
  • 수 HTML 수 함)(: Content-Type )enctype또는 기타 요청 헤더(들)를 선택합니다.

사전 비행이 필요한 작업을 올바르게 수행하고 있는 경우

이 경우 나머지 답변은 여전히 적용되지만, 서버가 비행 전 요청을 수신할 수 있는지 확인해야 합니다.OPTIONS(그렇지 않음)GET,POST 것이 , 합니다), 이든.Access-Control-Allow-Origin만 아니라oAccess-Control-Allow-Methods그리고.Access-Control-Allow-Headers특정 HTTP 메서드 또는 헤더를 허용합니다.

실수로 프리플라이트를 트리거하는 경우

때때로 사람들은 Ajax 요청을 구성하려고 할 때 실수를 하게 되고, 때로는 이러한 실수가 사전 비행의 필요성을 유발하기도 합니다.API가 교차 오리진 요청을 허용하도록 설계되었지만 사전 비행이 필요하지 않은 경우 액세스가 중단될 수 있습니다.

이를 유발하는 일반적인 실수는 다음과 같습니다.

  • 집어넣으려고 하는Access-Control-Allow-Origin요청에 대한 다른 CORS 응답 헤더.이러한 정보는 요청에 속하지 않으며, 도움이 되는 어떤 것도 하지 않습니다(자신에게 권한을 부여할 수 있는 권한 시스템의 요점은 무엇입니까?). 응답에만 표시해야 합니다.
  • Content-Type: application/json더 GET때를 )는)Content-Type그리고.Accept).

이 두 경우 모두 추가 요청 헤더를 제거하면 프리플라이트(간단한 요청은 지원하지만 프리플라이트 요청은 지원하지 않는 API와 통신할 때 문제가 해결됨)가 필요하지 않은 경우가 많습니다.


()no-cors드)

HTTP 요청을 해야 하는 경우도 있지만, 서버에 기록을 위해 로그 메시지를 게시하는 경우와 같이 응답을 읽을 필요는 없습니다.

API를 사용하는 경우(단,XMLHttpRequestCORS를 사용하지 않도록 구성할 수 있습니다.

이를 통해 CORS에 필요한 작업을 수행할 없습니다.응답을 읽을없습니다.사전 비행이 필요한 요청은 할 수 없습니다.

간단한 요청을 하고 응답을 볼 수 없으며 개발자 콘솔에 오류 메시지를 채우지 않을 수 있습니다.

Chrome error 로 시 메시지로 합니다.fetchCORS로 응답을 볼 수 있는 권한을 얻지 마십시오.

'에서 가져올 수 있는 액세스 권한https://example.com/원산지'''https://example.net' CORS 정책에 의해 차단되었습니다: 아니오'Access-Control-Allow-Origin .불투명 응답이 필요한 경우 요청의 모드를 'no-cors'로 설정하여 CORS가 비활성화된 리소스를 가져옵니다.

따라서:

fetch("http://example.com", { mode: "no-cors" });

CORS의 대안

JSONP

Bob은 또한 JSONP와 같은 해킹을 사용하여 데이터를 제공할 수 있었는데, 이것은 CORS가 나오기 전에 사람들이 Ajax를 교차 기원시킨 방법입니다.

맬로리 페이지에 데이터를 주입하는 자바스크립트 프로그램 형태로 데이터를 제시하는 방식으로 작동합니다.

맬로리는 밥이 악성코드를 제공하지 않도록 신뢰해야 합니다.

공통된 주제를 참고합니다.데이터를 제공하는 사이트는 브라우저에 타사 사이트가 브라우저로 전송하는 데이터에 액세스해도 괜찮다는 것을 알려주어야 합니다.

는 JSONP 는 A 를 입니다.<script>JSON이 자바스크립트가 아니기 때문에 JSON을 반환하는 URL에 JSONP 기법을 사용하려고 하면 실패하고 일반적으로 CORB 오류가 발생합니다.

두 리소스를 단일 오리진으로 이동

JS가 실행하는 HTML 문서와 요청 중인 URL이 동일한 오리진(동일한 스킴, 호스트 이름 및 포트 공유)에 있는 경우, 동일 오리진 정책은 기본적으로 권한을 부여합니다.CORS는 필요 없습니다.

에이 프락시

Mallory는 서버측 코드를 사용하여 데이터를 가져올 수 있습니다(그리고 나서 평소와 같이 HTTP를 통해 서버에서 Alice의 브라우저로 전달할 수 있습니다).

다음 중 하나입니다.

  • CORS 머리글 추가
  • 응답을 JSONP로 변환합니다.
  • HTML 문서와 동일한 출처에 존재합니다.

서버측 코드는 제3자(예: CORS Anywhere)에 의해 작성 및 호스팅될 수 있습니다.이로 인한 개인 정보 보호의 의미에 주목하십시오.제3자는 서버 전체에서 누가 무엇을 프록시하는지 모니터링할 수 있습니다.

밥은 그런 일이 일어나도록 허락할 필요가 없을 겁니다.

맬로리와 밥 사이의 일이기 때문에 여기에는 보안상의 영향이 없습니다.밥이 맬로리를 앨리스라고 생각하고 앨리스와 밥 사이에 비밀로 유지되어야 할 자료를 맬로리에게 제공할 방법은 없습니다.

따라서 맬로리는 공공 데이터를 읽을 때만 이 방법을 사용할 수 있습니다.

그러나 다른 사람의 웹 사이트에서 콘텐츠를 가져다가 스스로 표시하는 것은 저작권을 침해하는 것이며 법적 조치를 취할 수 있습니다.

웹 앱이 아닌 다른 것을 쓰는 것

"Web 페이지의 자바스크립트에만 동일 오리진 정책이 적용되는 이유" 부분에서 언급한 바와 같이, 웹 페이지에 자바스크립트를 작성하지 않음으로써 SOP를 피할 수 있습니다.

그렇다고 자바스크립트와 HTML을 계속 사용할 수는 없지만 노드-웹킷이나 폰갭과 같은 다른 메커니즘을 사용하여 배포할 수도 있습니다.

브라우저 확장자

브라우저 확장자가 동일 오리진 정책을 적용하기 전에 응답에 CORS 헤더를 주입할 수 있습니다.

이러한 기능은 개발에는 유용하지만 실제 운영 사이트에는 유용하지 않습니다(모든 사이트 사용자에게 브라우저의 보안 기능을 비활성화하는 브라우저 확장 기능을 설치하도록 요청하는 것은 무리입니다).

또한 단순한 요청(비행 전 OPTONSE 요청 처리 시 실패)에 대해서만 작업하는 경향이 있습니다.

로컬 개발 서버와 함께 적절한 개발 환경을 구축하는 것이 일반적으로 더 나은 접근 방식입니다.


기타 보안 위험

SOP/CORS는 독립적으로 처리해야 하는 XSS, CSRF 또는 SQL Injection 공격을 완화하지 않습니다.


요약

  • 다른 사용자의 서버에 대한 CORS 액세스를 가능하게 하는 클라이언트 측 코드에는 사용자가 할 수 있는 일이 없습니다.
  • 서버를 제어하는 경우 요청 대상: CORS 권한을 추가합니다.
  • 통제하는 사람과 친할 경우: CORS 권한을 추가하도록 합니다.
  • 공공 서비스인 경우(대부분의 타사 API는 서버코드로만 상호 작용하도록 설계되어 있으며 CORS를 지원하지는 않지만 해당 API의 경우):
    • API 설명서를 읽고 클라이언트 측 자바스크립트로 액세스하는 방법에 대해 설명합니다.
      • 특정 URL을 사용하라고 할 수도 있습니다.
      • CORS 대신 JSONP를 지원할 수도 있습니다.
      • 클라이언트 측 코드에서 교차 오리진 액세스를 전혀 지원하지 않을 수 있습니다(특히 각 요청에서 개인화된 API 키를 전달해야 하는 경우).
    • 필요 없는 비행 전 요청을 트리거하지 않도록 하십시오.API는 단순 요청에 대한 권한을 부여할 수 있지만 사전 비행 요청은 허용하지 않습니다.
  • 위의 내용 중 하나가 적용되지 않는 경우: 브라우저가 서버와 대화할 수 있도록 한 다음, 서버가 다른 서버에서 데이터를 가져와 전달하도록 합니다(사용할 수 있는 공개적으로 액세스 가능한 리소스에 CORS 헤더를 첨부하는 타사 호스팅 서비스도 있습니다).

대상 서버에서 교차 오리진 요청을 허용해야 합니다.express를 통해 허용하려면 http options 요청을 처리하기만 하면 됩니다.

app.options('/url...', function(req, res, next){
   res.header('Access-Control-Allow-Origin', "*");
   res.header('Access-Control-Allow-Methods', 'POST');
   res.header("Access-Control-Allow-Headers", "accept, content-type");
   res.header("Access-Control-Max-Age", "1728000");
   return res.sendStatus(200);
});

이것은 인정된 답변에 언급되지 않았기 때문입니다.

  • 이 정확한 질문에는 해당되지 않지만 해당 문제를 찾는 다른 사람에게 도움이 될 수 있습니다.
  • 이는 경우에 따라 CORS 오류를 방지하기 위해 클라이언트 코드에서 수행할 수 있는 작업입니다.

단순 요청을 사용할 수 있습니다.
'하려면 몇 단순 요청'을 수행하려면 몇 가지 조건을 충족해야 합니다.예를 들어 허용만 하는POST,GET그리고.HEAD메서드는 물론 일부 지정된 헤더만 허용합니다(여기서 모든 조건을 찾을 수 있습니다).

클라이언트 코드가 요청에 수정 값을 포함하여 영향을 받는 헤더(예: "승인")를 명시적으로 설정하지 않으면, 일부 클라이언트가 일부 "비표준" 값으로 헤더를 자동으로 설정하여 서버가 이를 단순 요청으로 승인하지 않을 있습니다. 그러면 CORS 오류가 발생합니다.

CORS 오류 때문에 발생하는 일입니다.CORS는 Cross Origin Resource Sharing의 약자입니다.간단히 말해서, 이 오류는 다른 도메인에서 도메인/자원에 액세스하려고 할 때 발생합니다.

여기서 더보기: Jquery와 CORS 오류

이 문제를 해결하려면 다른 도메인에 액세스할 수 있는 경우 서버에서 Access-Control-Allow-Origin을 허용해야 합니다.머리글에 추가할 수 있습니다.모든 요청/도메인 또는 특정 도메인에 대해 활성화할 수 있습니다.

CORS(Cross Origin Resource Sharing) 포스트 요청을 작동시키는 방법

이러한 링크가 도움이 될 수 있습니다.

이 CORS 문제는 (다른 이유로) 더 이상 자세히 설명하지 않았습니다.

저는 현재 다른 이유로 이 문제를 겪고 있습니다.프론트엔드에서 'Access-Control-Allow-Origin' 헤더 오류도 반환합니다.

단지 내가 잘못된 URL을 가리켜서 이 헤더가 제대로 반영되지 않았다는 것입니다(나는 계속 그렇게 했다고 추정했습니다).localhost (front end) -> 보안되지 않은 http (https로 추정) 에 호출합니다. 프론트 엔드의 API 끝점이 올바른 프로토콜을 가리키고 있는지 확인합니다.

크롬 콘솔에서도 같은 오류가 발생했습니다.

입니다를 에 들어가려고 이었습니다.http://https://그래서 게 , 를 요.https.

이 벌레 때문에 이틀이나 걸렸어요.서버 로그를 확인해보니 브라우저 Chrome/Edge와 Server 간의 Preflight Option 요청/응답이 정상이었습니다.주된 이유는 XHTMLRequest에 대한 GET/POST/PUT/DEELETE 서버 응답에도 다음과 같은 헤더가 있어야 하기 때문입니다.

access-control-allow-origin: origin  

"origin"이 요청 헤더에 있습니다(브라우저가 요청에 추가합니다).예를 들어 다음과 같습니다.

Origin: http://localhost:4221

다음과 같은 응답 헤더를 추가하여 모두에게 수락할 수 있습니다.

access-control-allow-origin: *  

또는 다음과 같은 특정 요청에 대한 응답 헤더.

access-control-allow-origin: http://localhost:4221 

브라우저의 메시지가 명확하게 이해할 수 없습니다: "...요청한 리소스"

참고: CORS는 로컬 호스트에 잘 작동합니다. 포트가 다르면 도메인이 다릅니다.에러 메시지가 뜨면 서버측 CORS config를 확인합니다.

대부분의 주택 서비스에서는 대상 서버 폴더에 다음과 같은 .htaccess만 추가하면 됩니다.

헤더 집합 Access-Control-Allow-Origin 'https://your.site.folder'

저도 같은 문제가 있었습니다.하였습니다의 하였습니다.timestamp가 접속하고 되지 않았습니다 URL로를제합니다.다.

예: yoururl.com/yourdocument?timestamp=1234567

참고: epos 타임스탬프를 사용했습니다.

헤더를 추가한 "Get" 요청을 "Options" 요청으로 변환합니다.그래서 코르스 정책 문제가 발생합니다.서버에 "옵션" 요청을 구현해야 합니다.서버측에 대한 Cors 정책 및 서버측에 Cors 정책을 허용해야 합니다.Nodejs 서버의 경우:상세 정보

app.use(cors)

Java를 Angular:details와 통합하려면

@CrossOrigin(origins = "http://localhost:4200")

CORS를 활성화하여 작동시켜야 합니다.

언급URL : https://stackoverflow.com/questions/35553500/xmlhttprequest-cannot-load-xxx-no-access-control-allow-origin-header

반응형