Tim R.
Tim R.

Reputation: 141

Javascript anonymous function question

I have this js class which has an anonymous function to retrieve some query results. Since the function which handles the results is anonymous I can't save the results in a this.var variable and use them somewhere else since this in the anonymous function references to the window object. I can't return it as a function return either so how do I do with those results to have them available somewhere else?

someObject = {
    //  this.db is created, no need to paste that code
    dbGetAnimals: function () {
        this.db.readTransaction(function(tx) {
            tx.executeSql("SELECT * FROM animals", function(tx, results){
                return results;
            } )
        });
    },
    printAllAnimals: function () {
        var animals = this.dbGetAnimals();
        alert (animals);//  undefined
    }
}

someObject.printAllAnimals();

Upvotes: 2

Views: 583

Answers (3)

Michiel Kalkman
Michiel Kalkman

Reputation: 3054

You're trying to do traditional synchronous/non-blocking programming where you want to do asynchronous programming.

var someObject = function()({
    this.dbGetAnimals = function (callback) {
        db.readTransaction(function(tx) {
             tx.executeSql("SELECT * FROM animals", function(tx, results){
                 callback(results);
            } )
        });
    },

    this.printAllAnimals = function (callback) {
        this.dbGetAnimals(callback);
    }
})();

someObject.printAllAnimals(function(animals) {
    alert(animals);
}

There are much cleaner ways to do this, but for async programming you have to learn to do everything on callbacks instead of direct returns.

Upvotes: 3

josh3736
josh3736

Reputation: 144872

This is happening because the anonymous function in executeSql is a callback function which is not executed until the query compmetes, which by definition will be after dbGetAnimals returns. That's why your call to dbGetAnimals is returning undefined.

You'll have to pass a callback function to receive the query resutls from within the executSql callback:

someObject = {  
    //  this.db is created, no need to paste that code  
    dbGetAnimals: function (callback) {  
        this.db.readTransaction(function(tx) {  
            tx.executeSql("SELECT * FROM animals", function(tx, results){  
                callback(results);
            } );
        });  
    },  
    printAllAnimals: function () {  
        this.dbGetAnimals(function(animals) {
            alert(animals)
        });  
    }  
}  


someObject.printAllAnimals();  

Upvotes: 0

Joe White
Joe White

Reputation: 97656

You can create a local variable to hold your this reference. Your anonymous function will become a closure, so it will be able to see that local var.

dbGetAnimals: function () {
    var myself = this;
    this.db.readTransaction(function(tx) {
        tx.executeSql("SELECT * FROM animals", function(tx, results){
            myself.var = results;
        } )
    });
},

Upvotes: 4

Related Questions