this keyword in JS can be trickier to understand at first glance. The obvious reason could be the way the this keyword behaves in JavaScript is different when compared to its peer languages like C++, Java, etc
But to be honest, understanding the this keyword in JavaScript is actually easier than it looks.
There are some fixed sets of rules provided by ECMA. So if we understand those rules, the this keyword is done and dusted.
By the end of this post, I assure every reader will gain complete knowledge of the this keyword in JavaScript and will be able to use the this keyword more confidently in their projects.
Now starting, before actually diving into the this keyword and understanding its behavior, we have to know a few prerequisites, and these prerequisites would majorly clear a lot of dust around the this keyword in JS.
Prerequisites:
The this keyword has a valid meaning only inside an execution context.
Now what does that mean?
JS has primarily 2 execution contexts defined in the language. (Actually, there are 4, but for the moment, we will skip the other 2 execution contexts (Eval, Module)). They are
Global Execution Context
Functional Execution Context
So there's the goal. Understanding this in the above two mentioned execution contexts will help us understand 95% of the this behavior in JS
1. this in Global Execution Context:
Standard Rule: this in GEC (Global Execution Context) will always represent the global object
Now what's this global object? The global object is provided by the Host
If you remember, JS, or more specifically, ECMAScript, is just a specification/contract of the language, and the JS engines (V8, SpiderMonkey, etc.) are the actual software that implements this specification.
These engines convert the JS code to machine-level code (binary).
And these JS engines are usually embedded inside the host.
The host can be a browser (Chrome, Safari, etc.), Node.js, Bun, etc
So, based on the host, the global object might differ, and so might the value of the this keyword.
So the value of the this keyword when checked on the browser console vs. on Node REPL would differ.
But the main point is that the this keyword in GEC would always hold the value of the global object
As we can see, this inside a browser gives a window object (as the window object is the global object inside a browser), but the this inside Node REPL gives a different object with different properties.
Note:
One of the very common misconceptions among many developers is that they assume the global object in Node.js is
Because when we try to check the value of this in a file and run that file via Node.js, we see
But there's a catch: a global object cannot be empty, and this is clearly evident when we tried to see the value of this in Node REPL.
Then why are we seeing an empty object ?
The answer lies in how Node.js works internally. Any code that you write inside a file run by Node.js, Node.js will never run that file in the true global scope.
Now, why's that? Before ES6, JS developers had only the var keyword to declare variables, and variables declared with the var keyword are stored in the global scope.
So, if 2 files in a project declare the same variable using the var keyword, it would pollute the global scope. Meaning the variable declared with var would override its previous entry.
Ex: Let's say a project has 2 files named f1.js and f2.js.
If f1.js has declared a variable named with hasPermission with the value true and f2.js has also declared a variable with the same name hasPermission with the value false, and assuming f1 runs first and f2 later, the final value of the hasPermission variable would be false, as running the f2.js file has overridden the value of the hasPermission variable.
Now the results of the file f1.js would be catastrophic, as the whole logic of f1.js would be affected by this overriding, as all the variables declared by the var keyword are stored in global scope.
This was a big problem.
Hence, Node.js provided a solution of its own.
Node.js always wraps your file inside a function, and that function would be internally invoked so that every variable defined with the var keyword will live only inside that file, as the function will create a separate execution context, hence saving the global scope from being polluted.
That also means that any code that is in a file when run by Node.js will be wrapped in a function, and the code truly doesn't run in the global scope of Node.js
But still, the question is unanswered. Why does this give an empty object? This will be answered in the upcoming sections of the blog...
2. this in Functional Execution Context:
As we all know, functions in JS create a new execution context; hence, the this keyword will behave differently inside a function.
But how different?
Standard Rule: The value of this inside a function will depend on how the function is invoked.
Now that
Tags:
#0
Want to run a more efficient business?
Mewayz gives you CRM, HR, Accounting, Projects & eCommerce — all in one workspace. 14-day free trial, no credit card needed.
Try Mewayz Free →