Business
Jobs
  • About Us
  • Solutions
    • Job Postings
      Post your job and receive qualified candidates in 48h.
    • Candidate Assessments
      500+ technical and psychological tests, plus anti-fraud.
    • Headhunting
      Tailor-made executive search from start to finish.
    • Payroll + EOR
      Payroll dispersal and EOR across 15+ LATAM countries.
  • Pricing
  • Jobs

0

1.2K
Views
Variable inside setTimeout says it is undefined, but when outside it is defined

I have a class. I need to do some http work inside of a timeout. The problem I am faceing is the http variable inside the timeout keeps saying it is undefined.

export class MyClass {

    http:Http:

    constructor(private http:Http) {
        this.http = http;
    }

    sendFriendRequest(){

    this.http.post( ...//http variable is defined here
           setTimeout(function(){
               this.http.post(...  //http is not defined here
        }
   }
}
over 4 years ago · Santiago Trujillo
3 answers
Answer question

0

The reason for this is that the callback function inside setTimeout is in a different lexical environment. This is why in ES6+ functions can be defined using =>. This is so that the code within a function shares the same scope as the function.

To fix this, you can either use ES6+ syntax, where instead of function(a,b,args){...} you would use (a,b,args) => {...}:

setTimeout(() => {
  this.http.post(...);
});

or with ES5 syntax:

var root = this;

setTimeout(function(){
    root.http.post(...);
});

Hope this helps!

over 4 years ago · Santiago Trujillo Report

0

In JavaScript the this keyword is used to access the context in which a function is invoked. Functions in JavaScript are always invoked with a context whether you invoke them using the .methodName() syntax or without it, unless the 'use strict' flag is set in the current scope.

When a function is invoked without a context like this:

myFunction()

the context is assumed by the runtime to be the global window object (unless the 'use strict' flag is set, in which case the context will be undefined.)

Note: When using ES6 with a transpiler like Babel, strict mode is set by default in the output.

When a reference to a function is saved on an object, you can invoke that function with the object as the context of 'this' using the dot syntax.

var myObj = {
    myFunc: function(){}
};

// myFunc invoked like this, the value of 'this' inside myFunc will be myObj.
myObj.myFunc();

Manipulate 'this':

Call and Apply

You can always change the context of a function by invoking it with the .call or .apply methods. In this case you have an anonymous function which is not invoked by you, but rather is invoked by the setTimeout function. Because of that, you won't be able to take advantage of .call or .apply.

Bind

Instead, you can create a new function that has a custom context by using the .bind method. By invoking .bind() on your anonymous function, an new function will be returned which has your custom context bound to 'this'. That way you can pass your custom bound function as data to setTimeout.

setTimeout(function(){
   // your code.
}.bind(this), 1000);

now inside the anonymous function the 'this' keyword would be bound to the correct value.

Lexical 'this':

In ES6 however, when using an arrow function the rules about 'this' change. If you use this syntax you will see the context of 'this' will stay the same as whatever it is in the current scope.

setTimeout(() => {
    // Hey I can access 'this' in here!
}, 1000);

Saving a reference:

If you look at the compiled output from Babel you will see Babel keeps track of the context by saving references to 'this' with _this1, _this2 and so forth.

To use this method yourself simply declare a new variable ( it's common to use 'that' or 'self' ) and access the value using it inside your anonymous function like so:

var self = this;
setTimeout(function(){
    self.http.post...
}); 

Hope this helps.

For more explanation developer.mozilla.org has a good article describing the behavior of 'this' inside a functions scope.

over 4 years ago · Santiago Trujillo Report

0

You should use arrow function here, to preserve existense of this.

setTimeout(()=>{
   this.http.post(...  //http is not defined here
})

In doing so, this inside of the function is bound to the outer context. It is the same as:

setTimeout(function(){
    this.http.post();
}.bind(this));
over 4 years ago · Santiago Trujillo Report
Answer question
Find remote jobs

Discover the new way to find a job!

Top jobs
Top job categories
Business
Post vacancy Pricing Sales
Legal
Terms and conditions Privacy policy
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Show me some job opportunities
There's an error!