How event handlers executed internally in javascript?

Viewed 540

I understand that javascript is single thread and that any asynchronous task is executed only after the current stack is empty. Callbacks, setTimeout, promises, are executed only after the current function is completed.

I want to know how the browser calls my event handler function when I perform some events.

When we say we are registering an event, where are we registering it? (message queue, job queue)? Where does it get saved in memory and how does the browser know that some event has occurred?

Are events related to operating systems call?

I have watched the philip roberts video and I understood the functionality of the event loop.

I want to know internals of javascript.

2 Answers

When we say we are registering an event, where are we registering it? Where does it get saved in memory?

A handler function is installed on the resource that you are listening to. For DOM events, it's the DOM objects that the browsers uses for displaying the document, for promises it's a JS object, for timers there's an internal timer object laying around (related to the DOM, since timers are defined in HTML and per window).

(message queue, job queue)?

No, those stay empty when an event handler is registered. Only when the event actually occurs, the handler that needs to run gets put on the queue.

How does the browser know that some event has occurred? Are events related to operating systems call?

Yes, ultimately events come from the operating systems, be it network packets arriving, timeouts occurring, or clicks being placed on the browser window. (Only very few events are triggered from within the browser machinery itself). The browser then checks which resources are affected by the system event (e.g. which DOM element was clicked), and then fires the respective event so that it may schedule any handlers as necessary.

The browser main thread is an event loop. It's an infinite loop that keeps the process alive. It waits for events and processes them. Events here mean several sort of things like:

  • A user has interacted with an UI component (button click, hover over something, etc...)
  • An API request has returned a response
  • A request to access an OS resource has been fulfilled

For example, this is Firefox code for the main event loop:

while (!mExiting)
    NS_ProcessNextEvent(thread);

Imagine we have the following piece of code:

function jsFunction() {
    console.log("prints first");
    // execute remote API call
    axios.get("url").then(reponse => {
        console.log("success");
    }).catch(error => {
        console.log("error");
    });
    console.log("prints second");
}

and we call this function:

jsFunction();

So what happens here is the following:

  • You have your single thread line of control executing this function prints "prints first".
  • Then you have that external API call, so the browsers sends this as a request to the networking layer of your OS to perform the http request and registers this callback function we've provided to be executed upon the response comes from the networking layer and instead of waiting for this to happen it continues execution.
  • Continuing execution it prints "prints second".
  • When the response comes from the networking layer, the event loop executes the callback function you have provided. This response is the event that is emitted to the event loop described above. It executes the suitable callback and prints "success" or "error" according to the response status.

See the Reference for more actual explanation about how event loop is implemented in browsers and browser engines in general.

Related