Search code examples
javascriptnode.jsgoogle-chromev8

The Javascript v8 engine and Web APIs


I have been reading into the internals of Javascript (in the context of the chrome browser) and I have a few questions that I can't seem to find proper answers to.

As per my understanding:

  • Core Javascript (as per ECMA specification) is included in the V8 engine.

  • Functions like settimeout are provided by the browser's Web APIs.

  • The V8 engine includes a call stack and any Javascript that is to be executed gets pushed on to this stack.

  • Non-standard functions are then called via Web APIs.

  • These on completion gets pushed to a callback queue.

  • Once the stack is empty, anything on the callback queue gets pushed onto the stack by the event loop.

My question is When the V8 engine interprets Javascript code, how does it know that a particular function is from the Web APIs? And how are Web APIs actually linked with the engine?


Solution

  • APIs like setTimeout() are added to the global object in Javascript. When the JS engine is looking to resolve a symbol, it starts in the local scope and goes up a chain of scopes. At the very end of the chain is the global scope.

    The host environment can, as part of initializing the V8 engine, add it's own APIs to the global scope in the V8 engine and that's exactly what a browser does for things it needs that aren't already built into V8.

    The notion of the global object in a browser is a bit messier than it probably should be. For many years, the global object was the window object. All globally accessible host environment functions like setTimeout() are properties of the window object.

    Similarly, declaring any variables at the top level scope in a browser would automatically make those variables be properties of the window object.

    This got messy fast. When the new class keyword came along, they decided to not continue to make this mess worse so classes declared at the top level scope in a browser are available globally, but are not added as properties of the window object.

    When the node.js environment came along, they organized user code into modules and the goal was to have as few global variables as possible. In that environment global variables are properties of an object named global. Variables you declare at the top level in node.js modules are scoped only to within the module. Nothing automatically becomes a global variable, but you can explicitly assign a new property to the global object if you want to such as:

    global.myProperty = 3;
    

    though that is strongly discourage in the node.js modular design.

    So, any API outside of the ECMAScript specification that is added at the top level in Javascript in the browser like setTimeout() is added to the global object by the browser environment when it is initializing the V8 engine.