<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0"><channel><title><![CDATA[Alan Lins]]></title><description><![CDATA[Alan Lins]]></description><link>https://blog.alanlins.me</link><generator>RSS for Node</generator><lastBuildDate>Sun, 26 Apr 2026 04:29:18 GMT</lastBuildDate><atom:link href="https://blog.alanlins.me/rss.xml" rel="self" type="application/rss+xml"/><language><![CDATA[en]]></language><ttl>60</ttl><item><title><![CDATA[Git Rebasing: Must-Know Commands Simplified]]></title><description><![CDATA[Using rebasing can make development easier. However, it gets complex when the team decides to keep a single commit per pull request, rebase branches with master, check out branches from remote, and fix conflicts. This article will list a few of the m...]]></description><link>https://blog.alanlins.me/git-rebasing-must-know-commands-simplified</link><guid isPermaLink="true">https://blog.alanlins.me/git-rebasing-must-know-commands-simplified</guid><category><![CDATA[GitHub]]></category><category><![CDATA[Git]]></category><category><![CDATA[git rebase]]></category><category><![CDATA[git-conflict]]></category><dc:creator><![CDATA[Alan Lins]]></dc:creator><pubDate>Tue, 06 Aug 2024 17:02:31 GMT</pubDate><enclosure url="https://cdn.hashnode.com/res/hashnode/image/stock/unsplash/nShLC-WruxQ/upload/7f990801db78fbfc7c4b15d63bb561c8.jpeg" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>Using rebasing can make development easier. However, it gets complex when the team decides to keep a single commit per pull request, rebase branches with master, check out branches from remote, and fix conflicts. This article will list a few of the most used git commands that can help during rebasing.</p>
<h2 id="heading-adding-new-changes-to-your-existing-branch">Adding new changes to your existing branch</h2>
<p>Once you have committed and pushed your branch, you will raise a Pull Request. After a code review, it is common to be asked to make some changes. If you need to update the code but want to keep a single commit and reuse the same message, you can use these commands:</p>
<pre><code class="lang-bash">git add .
git commit --amend --no-edit
git push --force-with-lease
</code></pre>
<p>The <code>--amend</code> option will overwrite your existing commit with your changes. The <code>--no-edit</code> option will keep the same message as the previous commit without opening the editor. These options save time because you won't need to squash commits or change the message in editor mode. Since the last commit was overwritten, a regular <code>git push</code> won't work. You must force the push using <code>--force</code> or <code>--force-with-lease</code>.</p>
<h2 id="heading-rebasing-your-branch-with-the-master-branch">Rebasing your branch with the master branch</h2>
<p>If you just want to sync your current branch with the latest master branch, you can do it with a single command:</p>
<pre><code class="lang-bash">git pull origin master -r
</code></pre>
<p>This command will rebase your branch with the latest master branch. Now, just push it again:</p>
<pre><code class="lang-bash">git push --force-with-lease
</code></pre>
<h3 id="heading-fixing-git-conflicts">Fixing git conflicts</h3>
<p>If the command <code>git pull origin master -r</code> doesn't complete because of conflicts, fix the conflicts, mark them as resolved, and then continue the rebase:</p>
<pre><code class="lang-bash"><span class="hljs-comment"># after conflicts got fixed</span>
git add .
git rebase --<span class="hljs-built_in">continue</span>
git push --force-with-lease
</code></pre>
<h3 id="heading-prevent-losing-approvals-on-github">Prevent losing approvals on github</h3>
<p>Some platforms, like GitHub, have an approval feature for pull requests. This ensures developers can't merge changes into the codebase without a minimum number of approvals. Depending on the setup, it also prevents accepting a PR with an outdated branch. This means developers need to rebase their branches whenever a PR is merged into the master branch. If you rebase your branch with master and push it using the <code>--force</code> option, GitHub will revoke all approvals, requiring developers to seek approvals again. However, if you use the <code>--force-with-lease</code> option, it will keep the approvals, as long as your branch didn't have any conflicts with master.</p>
<h2 id="heading-checkout-modified-remote-branch">Checkout modified remote branch</h2>
<p>Let's assume there is a branch called featureA on the remote origin. To pull it, you can use the commands:</p>
<pre><code class="lang-bash">git fetch
git checkout -b featureA origin/featureA
</code></pre>
<p>If someone else rebases the <code>featureA</code> branch with master and you try to pull the latest changes with <code>git pull</code>, it will mix the new and old commits from your local branch. Since the latest commit was overwritten due to rebasing, it will add an extra commit, even if you didn't make any changes yourself. If you want to pull the latest changes and ignore your local changes, you can use these commands:</p>
<pre><code class="lang-bash">git checkout featureA
git fetch
git reset --hard origin/featureA
</code></pre>
<p>That's it. The local branch <code>featureA</code> is an exact copy of the remote branch.</p>
<h2 id="heading-conclusion">Conclusion</h2>
<p>Using Git rebasing can greatly improve your development workflow. By understanding and using commands like <code>git commit --no-edit --amend</code>, <code>git push --force-with-lease</code>, and <code>git pull origin master -r</code>, you can simplify your commits, resolve conflicts, and keep your branches up-to-date with the master branch.</p>
]]></content:encoded></item><item><title><![CDATA[Understanding the keyword ‘this’ in JavaScript]]></title><description><![CDATA[Introduction
The keyword this works differently for javascript language. It can change its value depending on how it is called. After facing many issues, I wrote this article explaining how it works with just 4 rules to simplify the understanding and...]]></description><link>https://blog.alanlins.me/understanding-the-keyword-this-in-javascript</link><guid isPermaLink="true">https://blog.alanlins.me/understanding-the-keyword-this-in-javascript</guid><category><![CDATA[this]]></category><category><![CDATA[JavaScript]]></category><category><![CDATA[Testing]]></category><category><![CDATA[Jest]]></category><category><![CDATA[karma]]></category><dc:creator><![CDATA[Alan Lins]]></dc:creator><pubDate>Sat, 18 Jun 2022 16:47:01 GMT</pubDate><enclosure url="https://cdn.hashnode.com/res/hashnode/image/unsplash/geM5lzDj4Iw/upload/v1655557793810/tnKtyDVV3a.jpeg" length="0" type="image/jpeg"/><content:encoded><![CDATA[<h2 id="heading-introduction">Introduction</h2>
<p>The keyword <code>this</code> works differently for javascript language. It can change its value depending on how it is called. After facing many issues, I wrote this article explaining how it works with just 4 rules to simplify the understanding and avoid common issues like <code>undefined method</code> and calling wrong context. It explains how it works with callback functions, different platforms like nodejs and browser, and how to prevent bugs on testing with tools like jest.</p>
<h2 id="heading-what-is-this">What is <code>this</code>?</h2>
<p>According to Mozilla, the keyword <code>this</code> works like below:</p>
<blockquote>
<p>In most cases, the value of this is determined by how a function is called (runtime binding). It can't be set by assignment during execution, and it may be different each time the function is called.</p>
</blockquote>
<p>The problem below shows the value of <code>this</code> is different in two cases</p>
<h2 id="heading-the-problem">The problem</h2>
<p>See the two examples below:</p>
<ol>
<li>using function</li>
</ol>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> a = [<span class="hljs-number">1</span>,<span class="hljs-number">2</span>,<span class="hljs-number">3</span>].map(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">n</span>)</span>{
  <span class="hljs-keyword">return</span> n*<span class="hljs-built_in">this</span>;
}, <span class="hljs-number">2</span>);
</code></pre>
<p>output</p>
<pre><code class="lang-sh">[2,4,6]
</code></pre>
<ol start="2">
<li>using arrow function</li>
</ol>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> b = [<span class="hljs-number">1</span>,<span class="hljs-number">2</span>,<span class="hljs-number">3</span>].map( <span class="hljs-function"><span class="hljs-params">n</span> =&gt;</span> {
  <span class="hljs-keyword">return</span> n*<span class="hljs-built_in">this</span>;
}, <span class="hljs-number">2</span>);
</code></pre>
<p>output</p>
<pre><code class="lang-sh">[NaN,NaN,NaN]
</code></pre>
<p>This first example returns [2,4,6], while the second one, gets [NaN, NaN, NaN]. At the end of this article you will understand why they have different results.</p>
<h2 id="heading-the-4-rules">The 4 rules</h2>
<p>There are 4 rules that helps to understand how the keyword <code>this</code> works:</p>
<ul>
<li><p><strong>Rule 1</strong>: Inside a function, <code>this</code> refers to a global context(<code>window</code> for browser, <code>global</code> for nodejs);</p>
</li>
<li><p><strong>Rule 2</strong>: Inside a method, refers to an object;</p>
</li>
<li><p><strong>Rule 3</strong>: The value of <code>this</code> can be modified by <code>call</code> and <code>apply</code> functions and also when converts a method to a function and vice-versa;</p>
</li>
<li><p><strong>Rule 4</strong>: The value of <code>this</code> will never change if is in an <code>arrow function</code> or a <code>bind</code> function, therefore invalidating the rules 1, 2 and 3;</p>
</li>
</ul>
<h3 id="heading-rule-1">Rule 1</h3>
<p>Within a function, <code>this</code> refers to a global object. In a browser, the global object is <code>windows</code>, while in NodeJs is <code>global</code>.</p>
<pre><code class="lang-javascript"><span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">print</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span> == <span class="hljs-built_in">window</span>);
}
print() <span class="hljs-comment">//true</span>
</code></pre>
<p>Even nested functions refers to a global context</p>
<pre><code class="lang-javascript">
<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">print</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span> == <span class="hljs-built_in">window</span>);
  <span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">print2</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span> == <span class="hljs-built_in">window</span>);
  }
  print2(); <span class="hljs-comment">//true</span>
}
print() <span class="hljs-comment">//true</span>
</code></pre>
<h3 id="heading-rule-2">Rule 2</h3>
<p>Within a method, <code>this</code> refers to an object. The code below <code>this</code> refers to object <code>account</code>. This applies to object literal, class constructor and function contructor:</p>
<h4 id="heading-object-literal">Object literal</h4>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> account = {
  <span class="hljs-attr">balance</span>: <span class="hljs-number">100</span>,
  <span class="hljs-attr">showBalance</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">value</span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.balance) 
  }
}

account.showBalance(); <span class="hljs-comment">//100</span>
</code></pre>
<h4 id="heading-class-constructor">Class constructor</h4>
<pre><code class="lang-javascript"><span class="hljs-class"><span class="hljs-keyword">class</span> <span class="hljs-title">Account</span></span>{
  <span class="hljs-keyword">constructor</span>(){
    <span class="hljs-built_in">this</span>.balance = <span class="hljs-number">100</span>;
  }
  showBalance(value){
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.balance) 
  }
}
<span class="hljs-keyword">const</span> account = <span class="hljs-keyword">new</span> Account();
account.showBalance(); <span class="hljs-comment">//100</span>
</code></pre>
<h4 id="heading-function-constructor">Function constructor</h4>
<pre><code class="lang-javascript"><span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">Account</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">this</span>.balance = <span class="hljs-number">100</span>;
  <span class="hljs-built_in">this</span>.showBalance = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">value</span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.balance) 
  }
}
<span class="hljs-keyword">const</span> account = <span class="hljs-keyword">new</span> Account();
account.showBalance(); <span class="hljs-comment">//100</span>
</code></pre>
<h3 id="heading-rule-3">Rule 3</h3>
<p>The value of <code>this</code> can be modified by using <code>call</code>, <code>apply</code> and converting a method to a function and vice-versa.</p>
<h4 id="heading-converting-a-method-to-a-function">Converting a method to a function</h4>
<p>The code below has two variables:</p>
<ul>
<li><p>the global variable <code>balance</code>. Line 1</p>
</li>
<li><p>the variable <code>balance</code> at object account. Line 2</p>
</li>
</ul>
<p>On line 9 is doing <code>aliasing</code> which means, converting the <code>method</code> showBalance to <code>function</code> showBalance. The line 10 is calling a function(Rule 1), then the value of <code>this</code> will be global. On line 11, is a method(Rule 2), then it refers to object account.</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">var</span> balance = <span class="hljs-number">500</span>;
<span class="hljs-keyword">const</span> account = {
  <span class="hljs-attr">balance</span>: <span class="hljs-number">100</span>,
  <span class="hljs-attr">showBalance</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">value</span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.balance);
  }
}

<span class="hljs-keyword">const</span> showBalance = account.showBalance; <span class="hljs-comment">//aliasing</span>
showBalance(); <span class="hljs-comment">//500</span>
account.showBalance(); <span class="hljs-comment">//100</span>
</code></pre>
<h4 id="heading-converting-a-function-to-a-method">Converting a function to a method</h4>
<p>The opposite way, by assigning a function to a method, has also the same effect:</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">var</span> balance = <span class="hljs-number">500</span>;
<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">showBalance</span>(<span class="hljs-params">value</span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.balance);
}

<span class="hljs-keyword">const</span> account = {
  <span class="hljs-attr">balance</span>: <span class="hljs-number">100</span>
}

account.showBalance = showBalance;
showBalance(); <span class="hljs-comment">//500</span>
account.showBalance(); <span class="hljs-comment">//100</span>
</code></pre>
<h4 id="heading-call-and-apply">call and apply</h4>
<p>Another way to change the value of this is by using <code>call</code> or <code>apply</code>. The first parameter of call/apply is the value that sets <code>this</code>.</p>
<pre><code class="lang-javascript"><span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">showBalance</span>(<span class="hljs-params">value</span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.balance);
}

<span class="hljs-keyword">const</span> account1 = {
  <span class="hljs-attr">balance</span>: <span class="hljs-number">100</span>
}

<span class="hljs-keyword">const</span> account2 = {
  <span class="hljs-attr">balance</span>: <span class="hljs-number">50</span>
}

showBalance.call(account1); <span class="hljs-comment">//100</span>
showBalance.apply(account2); <span class="hljs-comment">//50</span>
</code></pre>
<h3 id="heading-rule-4">Rule 4</h3>
<p>The value of <code>this</code> will never change if is in an <code>arrow function</code> or a <code>bind</code> function, therefore invalidating the rules 1, 2 and 3;</p>
<h4 id="heading-arrow-function">Arrow function</h4>
<p>As the method <code>account.showBalance</code> is a <code>arrow function</code>, then the value of <code>this</code> will always refer to <code>account</code> object, the <code>showBalance</code> will always return the same value regardless how it has been called.</p>
<pre><code class="lang-javascript"><span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">Account</span>(<span class="hljs-params"></span>) </span>{
  <span class="hljs-built_in">this</span>.balance = <span class="hljs-number">100</span>;
  <span class="hljs-built_in">this</span>.showBalance = <span class="hljs-function">() =&gt;</span> {
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.balance);
  };
}
<span class="hljs-keyword">const</span> account = <span class="hljs-keyword">new</span> Account();
<span class="hljs-keyword">const</span> showBalance = account.showBalance;
account.showBalance(); <span class="hljs-comment">//100</span>
showBalance(); <span class="hljs-comment">//100</span>
showBalance.call(); <span class="hljs-comment">//100</span>
showBalance.apply(); <span class="hljs-comment">//100</span>
</code></pre>
<h4 id="heading-bind">bind</h4>
<p>The same behavior for <code>bind</code>.</p>
<pre><code class="lang-javascript"><span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">Account</span>(<span class="hljs-params"></span>) </span>{
  <span class="hljs-built_in">this</span>.balance = <span class="hljs-number">100</span>;
}
<span class="hljs-keyword">const</span> account = <span class="hljs-keyword">new</span> Account();
<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">showBalance</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.balance);
}
accountShowBalance = showBalance.bind(account);
accountShowBalance(); <span class="hljs-comment">//100</span>
accountShowBalance.call(); <span class="hljs-comment">//100</span>
accountShowBalance.apply(); <span class="hljs-comment">//100</span>
showBalance(); <span class="hljs-comment">//undefined</span>
</code></pre>
<p>The <code>accountShowBalance</code> is a <code>bind</code> function, then the <code>this</code> refers to <code>account</code> object. The <code>showBalance</code> is just a normal function, then the <code>this</code> value refers to global context, that's why it displayed <code>undefined</code>.</p>
<h2 id="heading-callback-function">Callback function</h2>
<p>Depending how a callback function is called and created the <code>this</code> will have different values.</p>
<h3 id="heading-called-as-a-function-rule-1">called as a function - Rule 1</h3>
<p>See the code below:</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">var</span> price = <span class="hljs-number">200</span>;
<span class="hljs-keyword">const</span> product = {
  <span class="hljs-attr">price</span>: <span class="hljs-number">100</span>,
  <span class="hljs-attr">showPrice</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">callback</span>)</span>{
    callback(); <span class="hljs-comment">// Rule 1</span>
  }
}

product.showPrice(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.price); <span class="hljs-comment">//200</span>
});
</code></pre>
<p>The result will be 200. Why? As the callback has been created as <code>function</code> at line 9 and it was called as <code>function</code> at line 5, the <code>this</code> will refer to <code>window</code> that contains the price 200.</p>
<h3 id="heading-called-as-a-method-rule-2">called as a method - Rule 2</h3>
<pre><code class="lang-javascript"><span class="hljs-keyword">var</span> price = <span class="hljs-number">200</span>;
<span class="hljs-keyword">const</span> product = {
  <span class="hljs-attr">price</span>: <span class="hljs-number">100</span>,
  <span class="hljs-attr">showPrice</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">callback</span>)</span>{
    <span class="hljs-built_in">this</span>.callback = callback; <span class="hljs-comment">// converting to method - Rule 3</span>
    <span class="hljs-built_in">this</span>.callback(); <span class="hljs-comment">// method - Rule 2</span>
  }
}

product.showPrice(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.price);
});
</code></pre>
<p>At the line 5, the callback function is assigned into a method, it is available now by product.callback. At the line 6, as it is been called by <code>this</code> which refers <code>product</code> object, so the line 11 returns 100.</p>
<h3 id="heading-callback-called-by-applycall-rule-3">callback called by apply/call - Rule 3</h3>
<p>The context of <code>this</code> of callback can be modified by <code>apply</code> or <code>call</code>.</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> product2 = {
  <span class="hljs-attr">price</span>: <span class="hljs-number">300</span>
}
<span class="hljs-keyword">const</span> product = {
  <span class="hljs-attr">price</span>: <span class="hljs-number">100</span>,
  <span class="hljs-attr">showPrice</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">callback</span>)</span>{
    callback.apply(product2); <span class="hljs-comment">//Rule 3</span>
  }
}

product.showPrice(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.price); <span class="hljs-comment">//300</span>
});
</code></pre>
<p>At the line 7, the contenxt of <code>this</code> is changed to <code>product2</code>, then line 12 will return 300.</p>
<h3 id="heading-callback-created-by-arrow-function-or-bind-rule-4">callback created by arrow function or bind - Rule 4</h3>
<p>If the callback is created by arrow function or bind, the value of <code>this</code> never changes.</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">var</span> value = <span class="hljs-string">'value from global'</span>;
<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">App</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">this</span>.value = <span class="hljs-string">'value from app'</span>;
  <span class="hljs-built_in">this</span>.addCallback = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">callback</span>)</span>{
    <span class="hljs-built_in">this</span>.callback = callback;
  }

  <span class="hljs-built_in">this</span>.triggerCallback = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-keyword">const</span> callback = <span class="hljs-built_in">this</span>.callback;
    <span class="hljs-built_in">this</span>.callback();
    callback();
  }
}

<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">System</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">this</span>.value = <span class="hljs-string">'value from system'</span>;

  <span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">callback</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.value);
  }

  <span class="hljs-built_in">this</span>.run = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-keyword">var</span> app = <span class="hljs-keyword">new</span> App();
    app.addCallback(<span class="hljs-function">()=&gt;</span>{ <span class="hljs-comment">//Rule 4</span>
      <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.value);
    }); 
    app.triggerCallback(); 
    <span class="hljs-comment">//value from system</span>
    <span class="hljs-comment">//value from system</span>

    app.addCallback(callback.bind(<span class="hljs-built_in">this</span>)); <span class="hljs-comment">//Rule 4</span>
    app.triggerCallback();
    <span class="hljs-comment">//value from system</span>
    <span class="hljs-comment">//value from system</span>

    app.addCallback(callback); <span class="hljs-comment">//Rule 3</span>
    app.triggerCallback();
    <span class="hljs-comment">//value from app</span>
    <span class="hljs-comment">//value from global</span>
  }
}

<span class="hljs-keyword">var</span> system = <span class="hljs-keyword">new</span> System();
system.run();
</code></pre>
<h2 id="heading-arrow-functions">Arrow functions</h2>
<p>The arrow functions will access the enclosing lexical context's <code>this</code>, in another words, it will access the <code>this</code> from closest constructor function or class that surrounds it.</p>
<pre><code class="lang-javascript"><span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">Person</span>(<span class="hljs-params"></span>)</span>{ <span class="hljs-comment">//contructor</span>
  <span class="hljs-built_in">this</span>.name = <span class="hljs-string">'Foo'</span>;

  <span class="hljs-keyword">const</span> getName = <span class="hljs-function">() =&gt;</span> {
    <span class="hljs-keyword">return</span> <span class="hljs-built_in">this</span>.name;
  }
  <span class="hljs-built_in">this</span>.show = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(getName());
  }
}
<span class="hljs-keyword">const</span> p = <span class="hljs-keyword">new</span> Person();
p.show();


<span class="hljs-class"><span class="hljs-keyword">class</span> <span class="hljs-title">PersonClass</span></span>{ <span class="hljs-comment">//contructor</span>
  <span class="hljs-keyword">constructor</span>(){
    <span class="hljs-built_in">this</span>.name = <span class="hljs-string">'Foo'</span>;
  }

  show(){
    <span class="hljs-keyword">const</span> getName = <span class="hljs-function">() =&gt;</span> {
      <span class="hljs-keyword">return</span> <span class="hljs-built_in">this</span>.name;
    }
    <span class="hljs-built_in">console</span>.log(getName());
  }
}
<span class="hljs-keyword">const</span> pc = <span class="hljs-keyword">new</span> PersonClass();
pc.show();
</code></pre>
<p>output</p>
<pre><code class="lang-plaintext">foo
foo
</code></pre>
<p>The line 4 declares an arrow function. As it is in the constructor function <code>Person</code>, then <code>this</code> value will be the instance of <code>Person</code>;</p>
<p>If a nested arrow function is created, the this' value will still be the same.</p>
<pre><code class="lang-javascript"><span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">Person</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">this</span>.name = <span class="hljs-string">'Foo'</span>;

  <span class="hljs-keyword">const</span> getName = <span class="hljs-function">() =&gt;</span> {
    <span class="hljs-keyword">const</span> nestedGetName = <span class="hljs-function">() =&gt;</span> {
      <span class="hljs-keyword">return</span> <span class="hljs-built_in">this</span>.name;
    }
    <span class="hljs-keyword">return</span> nestedGetName();
  }
  <span class="hljs-built_in">this</span>.show = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(getName());
  }
}
<span class="hljs-keyword">const</span> p = <span class="hljs-keyword">new</span> Person();
p.show();
</code></pre>
<p>output</p>
<pre><code class="lang-plaintext">foo
</code></pre>
<p>The arrow function set <code>this</code> value from the closest constructor function or class.</p>
<pre><code class="lang-javascript"><span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">Person</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">this</span>.name = <span class="hljs-string">'Foo'</span>;

  <span class="hljs-keyword">const</span> getParentName = <span class="hljs-function">() =&gt;</span> {
    <span class="hljs-keyword">return</span> <span class="hljs-built_in">this</span>.name;
  }

  <span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">Child</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">this</span>.name = <span class="hljs-string">'bar'</span>;
    <span class="hljs-built_in">this</span>.surname = <span class="hljs-string">' surname'</span>;
    <span class="hljs-keyword">const</span> getSurname = <span class="hljs-function">()=&gt;</span>{
      <span class="hljs-keyword">return</span> <span class="hljs-built_in">this</span>.surname;
    }
    <span class="hljs-built_in">this</span>.getName = <span class="hljs-function">() =&gt;</span>{
      <span class="hljs-keyword">return</span> <span class="hljs-built_in">this</span>.name+getSurname();
    }
  }

  <span class="hljs-keyword">var</span> child = <span class="hljs-keyword">new</span> Child();

  <span class="hljs-built_in">this</span>.showChild = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(child.getName());
  }
  <span class="hljs-built_in">this</span>.show = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(getParentName());
  }
}
<span class="hljs-keyword">const</span> p = <span class="hljs-keyword">new</span> Person();
p.show();
p.showChild();
</code></pre>
<p>Output</p>
<pre><code class="lang-plaintext">Foo
bar surname
</code></pre>
<p>The line 4, the variable <code>getParentName</code> is inside of <code>Person</code> function. When it creates an arrow function, the lexical context is <code>Person</code>, so the <code>this</code> value belong to <code>Person</code> instance. The line 10 and 14 create an arrow function, but the lexical context now is <code>Child</code> which is a constructor function as it will be instantiated on line 19.</p>
<p>Arrow function won't access object literal's context like a method.</p>
<pre><code class="lang-javascript"><span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">Person</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">this</span>.name = <span class="hljs-string">'Parent'</span>;

  <span class="hljs-built_in">this</span>.child = {
    <span class="hljs-attr">name</span>: <span class="hljs-string">'child 1'</span>,
    <span class="hljs-attr">show</span>: <span class="hljs-function">() =&gt;</span>{
      <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.name);
    }
  }


  <span class="hljs-built_in">this</span>.child2 = {
    <span class="hljs-attr">name</span>: <span class="hljs-string">'child 2'</span>,
    <span class="hljs-attr">show</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
      <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.name);
    }
  }
}

<span class="hljs-keyword">var</span> p = <span class="hljs-keyword">new</span> Person();
p.child.show();
p.child2.show();
</code></pre>
<p>Output</p>
<pre><code class="lang-plaintext">Parent
child 2
</code></pre>
<h2 id="heading-nested-functions">Nested functions</h2>
<p>On object literal, contructor or classes, the value of <code>this</code> refers to the context of the object.</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> person = { <span class="hljs-comment">//object literal</span>
  <span class="hljs-attr">name</span>: <span class="hljs-string">'foo'</span>,
  <span class="hljs-attr">showName</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.name); <span class="hljs-comment">// this == person</span>
  },
  <span class="hljs-attr">child</span>: {
    <span class="hljs-attr">name</span>: <span class="hljs-string">'bar'</span>,
    <span class="hljs-attr">showName</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
      <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.name); <span class="hljs-comment">// this == child</span>
    }
  }
}

<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">PersonConstructor</span>(<span class="hljs-params"></span>)</span>{ <span class="hljs-comment">//constructor</span>
  <span class="hljs-built_in">this</span>.name = <span class="hljs-string">'foo'</span>;
  <span class="hljs-built_in">this</span>.showName = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.name); <span class="hljs-comment">// this == PersonContructor instance</span>
  }
}

<span class="hljs-class"><span class="hljs-keyword">class</span> <span class="hljs-title">PersonClass</span></span>{ <span class="hljs-comment">//class</span>
  <span class="hljs-keyword">constructor</span>(){
    <span class="hljs-built_in">this</span>.name = <span class="hljs-string">'foo'</span>; <span class="hljs-comment">// this == PersonClass instance</span>
  }
  showName(){
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.name); <span class="hljs-comment">// this == PersonClass instance</span>
  }
}
<span class="hljs-keyword">const</span> p = <span class="hljs-keyword">new</span> PersonConstructor();
<span class="hljs-keyword">const</span> p2 = <span class="hljs-keyword">new</span> PersonClass();

person.showName();
person.child.showName();
p.showName();
p2.showName();
</code></pre>
<p>Output</p>
<pre><code class="lang-sh">foo
bar
foo
foo
</code></pre>
<p>On line 4, the function showName is assigned inside of <code>person</code> object, then its <code>this</code> will access the object. On line 6, the <code>child</code> is another object literal, then the line 9 <code>this</code> will accesss <code>child</code> context.</p>
<p>After instantiated with keyword <code>new</code> on lines 29 and 30, the lines 17 and 26 will access the context of the object instantiate from PersonContructor and PersonClass.</p>
<h2 id="heading-value-of-this-by-platforms">Value of <code>this</code> by platforms</h2>
<p>The value of <code>this</code> is different by plataform (browser or nodejs), strict mode or if is a ES6 module.</p>
<h3 id="heading-browser">Browser</h3>
<p>In browser the value of <code>this</code> in function(Rule 1) refers to <code>window</code>. Look the code below:</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">var</span> a = <span class="hljs-string">'world'</span>;
<span class="hljs-built_in">window</span>.b = <span class="hljs-string">'hello'</span>;

<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">hello</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.a)
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.b)
}
hello();
</code></pre>
<p>The lines 1 and 2 create global variables <code>a</code> and <code>b</code>. The individual function <code>hello</code> can access the global object by <code>this</code>. The lines 5 and 6 prints the <code>hello</code> and <code>world</code>.</p>
<pre><code class="lang-sh">hello
world
</code></pre>
<h3 id="heading-browser-with-strict-mode">Browser with strict mode</h3>
<p>When the <code>’use strict’</code> is added to top of the file or function, the JavaScript stops to defaulting <code>this</code> to <code>window</code> object.</p>
<h4 id="heading-strict-mode">Strict mode</h4>
<pre><code class="lang-javascript"><span class="hljs-meta">'use strict'</span>
<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">showThis</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>) <span class="hljs-comment">// output: undefined</span>
}
hello();
</code></pre>
<h4 id="heading-normal-mode">Normal mode</h4>
<pre><code class="lang-javascript"><span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">showThis</span>(<span class="hljs-params"></span>)</span>{   
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>) <span class="hljs-comment">// output: window </span>
} 
hello();
</code></pre>
<h3 id="heading-browser-with-module">Browser with module</h3>
<p>ES6 Introduced the "module". It doesn't even have global/window context. So, the code below won't work either.<br />Create a module with the code below:</p>
<p>Create the file <code>hello.js</code> with content below:</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">var</span> a = <span class="hljs-string">'world'</span>;

<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">hello</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.a)<span class="hljs-comment">// it will fail</span>
}
hello();
</code></pre>
<p>Create a file index.html then add within the tag <code>&lt;head&gt;</code> the line below:</p>
<pre><code class="lang-html"><span class="hljs-tag">&lt;<span class="hljs-name">script</span>  <span class="hljs-attr">type</span>=<span class="hljs-string">"module"</span> <span class="hljs-attr">src</span>=<span class="hljs-string">"hello.js"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
</code></pre>
<p>Open the file in browser. The code will fail on line 4, <code>this</code> can't access <code>window</code>.</p>
<blockquote>
<p>I would recommend to use "modules", because it can be transpiled with webpack or similar, and work in both environments browser and nodejs. If you want to learn to write a testable javascript code with jquery to run in both environment, read my article.</p>
</blockquote>
<h3 id="heading-nodejs">Nodejs</h3>
<p>In nodejs works a little bit different. The <code>this</code> is a <code>global</code> value.</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">var</span> a = <span class="hljs-string">'hello'</span>;
<span class="hljs-built_in">global</span>.b = <span class="hljs-string">'world'</span>;

<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">hello</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.a) <span class="hljs-comment">// fail</span>
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.b) <span class="hljs-comment">// works</span>
}
hello();
</code></pre>
<p>The variable <code>a</code> can't be access from <code>global.a</code>. The <code>this</code> access only <code>global</code> object.</p>
<h2 id="heading-issues-with-testing">Issues with testing</h2>
<p>Sometimes a JavaScript code can work on browser but its unit test fails. This happens quite often in legacy code that contains global variables spread among several files and consumed by <code>this</code> in somewhere. If this legacy code has been tested in tools like <code>jest</code> and <code>karma</code> they might have different results.</p>
<h3 id="heading-example">Example</h3>
<p>Consider a legacy app where two JavaScript files are loaded in browser by "script" tags. The example is available on <a target="_blank" href="https://github.com/alanblins/jest-karma-sample">GitHub</a>.</p>
<ul>
<li><p><strong>globalState.js</strong>: Initialize global variables,</p>
</li>
<li><p><strong>legacy.js</strong>: Access global variables through <code>this</code>.</p>
</li>
</ul>
<p>globalState.js</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">var</span> globalValue = <span class="hljs-number">10</span>; 
<span class="hljs-built_in">window</span>.globalValue2 = <span class="hljs-number">5</span>;
</code></pre>
<p>legacy.js</p>
<pre><code class="lang-javascript"><span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">getGlobalValue</span>(<span class="hljs-params"></span>) </span>{
  <span class="hljs-keyword">return</span> <span class="hljs-built_in">this</span>.globalValue;
}
<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">getGlobalValue2</span>(<span class="hljs-params"></span>) </span>{
  <span class="hljs-keyword">return</span> <span class="hljs-built_in">this</span>.globalValue2;
}
<span class="hljs-built_in">window</span>.getGlobalValue = getGlobalValue;
<span class="hljs-built_in">window</span>.getGlobalValue2 = getGlobalValue2;
</code></pre>
<p>Below are test files to verify if the functions "getGlobalValue" and getGlobalValue2" returns right values. The first one is written in <code>jest</code> while the second in <code>karma</code>.</p>
<h3 id="heading-jest-test">jest test</h3>
<pre><code class="lang-javascript">test(<span class="hljs-string">"result is 10"</span>, <span class="hljs-function">() =&gt;</span> {
  expect(getGlobalValue()).toBe(<span class="hljs-number">10</span>); <span class="hljs-comment">//FAIL</span>
});

test(<span class="hljs-string">"result is 5"</span>, <span class="hljs-function">() =&gt;</span> {
  expect(getGlobalValue2()).toBe(<span class="hljs-number">5</span>);
});
</code></pre>
<h3 id="heading-karma-test">karma test</h3>
<pre><code class="lang-javascript">describe(<span class="hljs-string">"getGlobalValue test"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>) </span>{
  it(<span class="hljs-string">"result is 10"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>) </span>{
    expect(getGlobalValue()).toBe(<span class="hljs-number">10</span>);
  });
  it(<span class="hljs-string">"result is 5"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>) </span>{
    expect(getGlobalValue2()).toBe(<span class="hljs-number">5</span>);
  });
});
</code></pre>
<p>Both tests in <code>karma</code> will all pass, while the <code>jest</code> will fail on the first test <code>result is 10</code>. Why? The issue is in the line 1 of <code>globalState.js</code>.</p>
<pre><code class="lang-js"><span class="hljs-keyword">var</span> globalValue = <span class="hljs-number">10</span>;
</code></pre>
<p>As <code>jest</code> runs in a Nodejs environment and Karma in browser environment, the variable <code>globalValue = 10</code> will be available only on browser’s object <code>window</code> but not in NodeJS’s object <code>global</code>. This is deeply explained on "Value of this by plataforms" item.</p>
<p>If the line 1 is replace by <code>window</code> like below, the code will work on both <code>jest</code> and <code>karma</code></p>
<p>globalState.js modified</p>
<pre><code class="lang-javascript"><span class="hljs-built_in">window</span>.globalValue = <span class="hljs-number">10</span>; <span class="hljs-comment">//fixed</span>
<span class="hljs-built_in">window</span>.globalValue2 = <span class="hljs-number">5</span>;
</code></pre>
<p><code>jest</code> will automatically copy all <code>window</code> values into nodejs <code>global</code> object. Then the <code>jest</code> test will pass.</p>
<h2 id="heading-explaining-the-first-example">Explaining the first example</h2>
<p>To help to understand how the native JavaScript function <code>.map</code> works under the hood, let’s implement a custom version called <code>modifyArray</code>.</p>
<pre><code class="lang-javascript"><span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">modifyArray</span>(<span class="hljs-params">array, callback ,thisArg</span>)</span>{
    <span class="hljs-keyword">var</span> newArray = [];
    <span class="hljs-keyword">for</span>(<span class="hljs-keyword">var</span> i=<span class="hljs-number">0</span>;i&lt;array.length;i++){
        newArray[i] = callback.call(thisArg, array[i]);
    }    
    <span class="hljs-keyword">return</span> newArray;
}
</code></pre>
<p>The function <code>modifyArray</code> receives an array. It will iterate each element and replace it with the return of the callback function.</p>
<p>Note that the callback function is using the <code>.call</code> function changing the value of <code>this</code> by the value <code>thisArg</code> as it shows on the 4th line.</p>
<h3 id="heading-simple-function">Simple function</h3>
<p>Let's multiply all the elements and passing a simple function <code>multiply</code> as a callback to the function <code>modifyArray</code>:</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> array = [<span class="hljs-number">1</span>,<span class="hljs-number">2</span>,<span class="hljs-number">3</span>];
<span class="hljs-keyword">const</span> multiply = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">element</span>)</span>{
  <span class="hljs-keyword">return</span> element*<span class="hljs-built_in">this</span>;
}
<span class="hljs-keyword">const</span> newArray = modifyArray(array, multiply, <span class="hljs-number">2</span>);
<span class="hljs-built_in">console</span>.log(newArray);
</code></pre>
<p>The result will be <code>[2,4,6]</code>.</p>
<p>On the 5th line the third parameter <code>thisArg</code> has the value <code>2</code>.</p>
<p>In the <code>modifyArray</code> <code>callback.call(thisArg, array[i])</code> update the <code>this</code> value with <code>2</code>.</p>
<pre><code class="lang-javascript">newArray[i] = callback.call(thisArg, array[i]); <span class="hljs-comment">//callback is `multiply` and `thisArgs` is 2.</span>
</code></pre>
<p>According to the rule 3, because the <code>multiply</code> function was called using <code>call</code>, then the value of <code>this</code> will be <code>2</code>.</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> multiply = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">element</span>)</span>{
  <span class="hljs-keyword">return</span> element*<span class="hljs-built_in">this</span>; <span class="hljs-comment">// =&gt; element * 2</span>
}
</code></pre>
<h3 id="heading-arrow-function-1">Arrow function</h3>
<p>Let's modify the <code>’multiply</code> function to an arrow function:</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> array = [<span class="hljs-number">1</span>,<span class="hljs-number">2</span>,<span class="hljs-number">3</span>];
<span class="hljs-keyword">const</span> multiply = <span class="hljs-function">() =&gt;</span> {
    <span class="hljs-keyword">return</span> element*<span class="hljs-built_in">this</span>; <span class="hljs-comment">// element * window</span>
}
<span class="hljs-keyword">const</span> newArray = modifyArray(array, multiply, <span class="hljs-number">2</span>);
<span class="hljs-built_in">console</span>.log(newArray);
</code></pre>
<p>The result will be <code>[NaN, NaN, NaN]</code>.</p>
<p>Why?</p>
<p>Because the callback is an arrow function a two things happend here:</p>
<ul>
<li><p>The line <code>callback.call(thisArg, array[i])</code> from <code>modifyArray</code> doesn’t change the value of <code>this</code>, look the Rule 4.</p>
</li>
<li><p>The value of <code>this</code> is <code>window</code> because it set the <code>this</code> to the nearest scope, which in this case is <code>window</code></p>
</li>
</ul>
<p>When it calls <code>element*this</code> it tries to multiply a number with the <code>window</code> value <code>element * window</code> resulting to NaN value.</p>
<p>Now, by understanding the previous example, the same idea may apply to the function <code>map</code>.</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> a = [<span class="hljs-number">1</span>,<span class="hljs-number">2</span>,<span class="hljs-number">3</span>].map(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">n</span>)</span>{
  <span class="hljs-keyword">return</span> n*<span class="hljs-built_in">this</span>;
}, <span class="hljs-number">2</span>);

<span class="hljs-keyword">const</span> b = [<span class="hljs-number">1</span>,<span class="hljs-number">2</span>,<span class="hljs-number">3</span>].map( <span class="hljs-function"><span class="hljs-params">n</span> =&gt;</span> {
  <span class="hljs-keyword">return</span> n*<span class="hljs-built_in">this</span>;
}, <span class="hljs-number">2</span>);
</code></pre>
<p>The <code>map</code> function has two parameters function and thisArg.</p>
<pre><code class="lang-plaintext">map(function callback( currentValue[, index[, array]]) {
    // return element for new_array
}[, thisArg])
</code></pre>
<p>The <code>thisArg</code> will be the value of <code>this</code> inside a function callback. In <code>arrow function</code> the value of <code>this</code> won't be <code>thisArg</code>. Inside the <code>map</code> function it does something similar to our function <code>modifyArray</code>. It might use the <code>call</code> or <code>apply</code> method to change the value of <code>this</code>.</p>
<h2 id="heading-summary">Summary</h2>
<h3 id="heading-4-rules">4 Rules</h3>
<ol>
<li><p>Inside a function, <code>this</code> refers to a global context(window for browser, global for nodejs);</p>
</li>
<li><p>Inside a method, refers to an object;</p>
</li>
<li><p>The value of <code>this</code> can be modified by <code>call</code> and <code>apply</code> functions and also when converts a method to a function and vice-versa;</p>
</li>
<li><p>The value of <code>this</code> will never change if is in an <code>arrow function</code> or a <code>bind</code> function, therefore invalidating the rules 1, 2 and 3;</p>
</li>
</ol>
<h3 id="heading-callback">Callback</h3>
<ul>
<li><p>If the callback is a bind function or an <code>arrow function</code>, the value of <code>this</code> will never change regardless of how it is called. Rule 4</p>
</li>
<li><p>if the callback is just a function, the value of <code>this</code> depends on how will be called then could apply the rules 1, 2 or 3.</p>
</li>
</ul>
<h3 id="heading-browser-1">Browser</h3>
<ul>
<li><p><code>this</code> is <code>window</code></p>
</li>
<li><p>declare <code>var</code> outside any function is accessible via <code>this</code></p>
</li>
</ul>
<h3 id="heading-browser-with-strict-mode-1">Browser with strict mode</h3>
<ul>
<li><code>this</code> doesn't access <code>window</code></li>
</ul>
<h3 id="heading-browser-with-module-1">Browser with module</h3>
<ul>
<li><code>this</code> doesn't access <code>window</code></li>
</ul>
<h3 id="heading-nodejs-1">Nodejs</h3>
<ul>
<li><p><code>this</code> is <code>global</code></p>
</li>
<li><p>declare <code>var</code> outside any function is NOT accessible via <code>this</code></p>
</li>
</ul>
<h3 id="heading-all-cases-in-one-code">All cases in one code</h3>
<pre><code class="lang-javascript"><span class="hljs-keyword">var</span> name = <span class="hljs-string">'Foo global'</span>;

<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">getNameGlobalFunc</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.name);
}
<span class="hljs-keyword">const</span> getNameGlobalVar = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.name);
}

<span class="hljs-keyword">const</span> personObjectLiteral = {
  <span class="hljs-attr">name</span>: <span class="hljs-string">'Foo object literal'</span>,
  <span class="hljs-attr">getName</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.name);
  }
}

<span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">PersonConstructor</span>(<span class="hljs-params"></span>)</span>{
  <span class="hljs-built_in">this</span>.name = <span class="hljs-string">'Foo constructor'</span>;

  <span class="hljs-built_in">this</span>.setCallback = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"> callback </span>)</span>{
    <span class="hljs-built_in">this</span>.callback = callback;
  }

  <span class="hljs-built_in">this</span>.callCallback = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">this</span>.callback();
  }

  <span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">getNameGlobal</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.name);
  }

  <span class="hljs-keyword">const</span> getNameArrow = <span class="hljs-function">() =&gt;</span> {
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.name);
  };

  <span class="hljs-keyword">const</span> getNameBind = getNameGlobal.bind(<span class="hljs-built_in">this</span>);

  <span class="hljs-built_in">this</span>.getName = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">this</span>.name);
  }

  <span class="hljs-built_in">this</span>.getNameReassigned = getNameGlobal;
  <span class="hljs-keyword">const</span> reasignAsGlobal = <span class="hljs-built_in">this</span>.getName;

  <span class="hljs-built_in">this</span>.callThisGlobals = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    getNameGlobal()
    reasignAsGlobal();
  }

  <span class="hljs-built_in">this</span>.callThisPersonContext = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    getNameArrow();
    getNameBind();
    <span class="hljs-built_in">this</span>.getName();
    <span class="hljs-built_in">this</span>.getNameReassigned();
  }

}

<span class="hljs-keyword">const</span> person = <span class="hljs-keyword">new</span> PersonConstructor();

getNameGlobalFunc();
getNameGlobalVar();
person.callThisGlobals();

personObjectLiteral.getName();
person.callThisPersonContext();

<span class="hljs-built_in">console</span>.log(getNameGlobalVar.call(personObjectLiteral))
<span class="hljs-built_in">console</span>.log(getNameGlobalVar.apply(person))
</code></pre>
<h2 id="heading-cheat-sheet">Cheat sheet</h2>
<div class="hn-table">
<table>
<thead>
<tr>
<td><strong>Scenario</strong></td><td><strong>Execution Example</strong></td><td><strong>Value of this</strong></td></tr>
</thead>
<tbody>
<tr>
<td><strong>Global Scope</strong></td><td><code>console.log(this)</code></td><td><code>window</code> (Browser) or <code>global</code> (Node)</td></tr>
<tr>
<td><strong>Simple Function</strong></td><td><code>myFunc()</code></td><td><code>window</code> (Non-strict) / <code>undefined</code> (Strict, ES6 module)</td></tr>
<tr>
<td><strong>Object Method</strong></td><td><code>user.greet()</code></td><td>The object before the dot (<code>user</code>)</td></tr>
<tr>
<td><strong>Arrow Function</strong></td><td><code>() =&gt; { ... }</code></td><td>Inherited from the surrounding scope</td></tr>
<tr>
<td><strong>Constructor</strong></td><td><code>new Person()</code></td><td>The brand new object being created</td></tr>
<tr>
<td><strong>Explicit Binding</strong></td><td><a target="_blank" href="http://func.call"><code>func.call</code></a><code>(obj)</code></td><td>The object passed as the argument (<code>obj</code>)</td></tr>
</tbody>
</table>
</div>]]></content:encoded></item></channel></rss>