JavaScript는 단일 스레드에서 실행되므로 AJAX 요청을 한 후에 실제로 백그라운드에서 어떤 일이 발생합니까? 이것에 대한 더 깊은 통찰력을 얻고 싶습니다. 누군가 약간의 빛을 비출 수 있습니까?
JavaScript는 단일 스레드에서 실행되므로 AJAX 요청을 한 후에 실제로 백그라운드에서 어떤 일이 발생합니까? 이것에 대한 더 깊은 통찰력을 얻고 싶습니다. 누군가 약간의 빛을 비출 수 있습니까?
답변:
커버 아래에 javascript에는 이벤트 큐가 있습니다. 자바 스크립트 실행 스레드가 완료 될 때마다 처리 할 대기열에 다른 이벤트가 있는지 확인합니다. 있는 경우 대기열에서 가져 와서 해당 이벤트를 트리거합니다 (예 : 마우스 클릭).
ajax 호출에있는 기본 코드 네트워킹은 ajax 응답이 수행되는시기를 알고 이벤트가 javascript 이벤트 큐에 추가됩니다. 원시 코드가 ajax 호출이 수행되는시기를 아는 방법은 구현에 따라 다릅니다. 스레드로 구현되거나 이벤트 중심 자체 일 수도 있습니다 (실제로 중요하지는 않습니다). 구현의 요점은 아약스 응답이 완료되면 일부 원시 코드가 완료되었음을 알리고 이벤트를 JS 큐에 넣는다는 것입니다.
당시에 Javascript가 실행되고 있지 않으면 이벤트가 즉시 트리거되어 ajax 응답 핸들러가 실행됩니다. 그 시점에서 무언가가 실행 중이면 현재 자바 스크립트 실행 스레드가 완료 될 때 이벤트가 처리됩니다. 자바 스크립트 엔진에 의한 폴링이 필요하지 않습니다. Javascript가 실행을 마치면 JS 엔진은 이벤트 큐를 검사하여 실행해야 할 다른 것이 있는지 확인합니다. 그렇다면, 다음 이벤트를 큐에서 팝하고 실행합니다 (해당 이벤트에 등록 된 하나 이상의 콜백 함수 호출). 이벤트 큐에 아무것도 없으면, JS 외부 인터프리터는 일부 외부 에이전트가 이벤트 큐에 다른 것을 넣고 다시 깨울 때까지 여유 시간 (가비지 콜렉션 또는 유휴)을 갖습니다.
모든 외부 이벤트는 이벤트 큐를 통과하고 자바 스크립트가 실제로 다른 것을 실행하는 동안 이벤트가 트리거되지 않으므로 단일 스레드 상태로 유지됩니다.
자세한 내용은 다음과 같습니다.
.focus()
항목을 호출 하면 초점이있는 항목의 "흐림"이벤트와 같은 몇 가지 다른 이벤트가 트리거됩니다. 이 블러 이벤트는 동 기적으로 발생하며 이벤트 큐를 거치지 않으므로 이벤트 큐에있을 수있는 다른 일 직전에 발생합니다. 실제로, 나는 이것이 실제적인 관심사 인 것을 결코 찾지 못했다.
답변에 언급 된 아약스 구현에 대해 조금 자세히 설명하고 싶습니다.
(일반) 자바 스크립트 실행이 있지만 하지 위의 답변에서 잘 언급 한 바와 같이 - - 멀티 스레드 그러나 ,의 실제 처리 AJAX responses
(뿐만 아니라 요청 처리) 일 하지 자바 스크립트, 그리고 - 보통 - 입니다 멀티 스레드. ( 위에서 논의 할 XMLHttpRequest의 크롬 소스 구현 참조 )
다음 코드를 살펴 보겠습니다.
var xhr = new XMLHttpRequest();
var t = Date.now;
xhr.open( "GET", "https://swx.cdn.skype.com/shared/v/1.2.15/SkypeBootstrap.min.js?v="+t(), true );
xhr.onload = function( e ) {
console.log(t() + ': step 3');
alert(this.response.substr(0,20));
};
console.log(t() + ': step 1');
xhr.send();
console.log(t() + ': step 2');
after an AJAX request is made
(-1 단계 후) js 코드 실행이 진행되는 동안 (2 단계 이후) 브라우저는 다음과 같은 실제 작업을 시작합니다. 1. tcp 요청 형식 지정 2. 소켓 열기 3. 헤더 보내기 4. 핸드 쉐이킹 5. 보내기 본문 6. 대기 응답 7. 헤더 읽기 8. 본문 읽기 등이 모든 구현은 일반적으로 js 코드 실행과 병렬로 다른 스레드에서 실행됩니다. 예를 들어 언급 된 크롬 구현은 Threadable Loader go digg-into 😉를 사용합니다 (페이지로드의 네트워크 탭을 보면 인상을 얻을 수 있으며 동시 요청이 표시됩니다).
결론적으로, 적어도 대부분의 I / O 작업은 동시에 / 비동기 적으로 수행 될 수 있습니다 ( 예를 들어 await 를 사용하여이를 활용할 수 있음 ). 그러나 해당 작업 (발행, js 콜백 실행)과의 모든 상호 작용은 모두 동 기적입니다.