Home > OS >  How to appropriately wrap callback functions from jquery load() in Promises, so I can use await Prom
How to appropriately wrap callback functions from jquery load() in Promises, so I can use await Prom

Time:09-27

I feel like there must be a simple, searchable answer to this, but try as I might, I am unable to find the solution to this simple problem. I am new to Promises and callbacks, so I am probably using the wrong search terms.

I have multiple DOM objects that have HTML loaded in via jquery's load function. The order the pieces are loaded in the page does not matter - however, I want to do some tasks only after ALL of them have completed loading.

Promise.all seemed like a great solution, something such as this:

// what I'd like to be able to do.

function init_page() {

    var init_tasks = [];
    init_tasks.push($("#divA").load("page1.html"));
    init_tasks.push($("#divB").load("page2.html"));
    init_tasks.push($("#divC").load("page3.html"));

    await Promise.all(init_tasks);

    // do stuff here    

}

However, load() returns a callback function, not a Promise object, so this does not work.

I made a wrapper function (shown below), which wraps load's returned callback function in a Promise, so I can use the above approach. Unfortunately, with the way I've written it, the Promises never resolve. I figure I am probably doing something very obviously wrong, but I can not figure out what. (Do I need to be returning something other than the Promise? Do I need to define resolve and reject cases?)

// incorrect "Promise wrapper" attempt

function loadPromiseWrapper(dom_id, filename) {
    return new Promise(function(resolve, reject) {
        $(dom_id).load(filename);

        // what am I missing here?
    }); 
}

// revised init_page function that calls my incorrect "Promise wrapper"

function init_page() {

    var init_tasks = [];
    init_tasks.push(loadPromiseWrapper("divA", "page1.html"));
    init_tasks.push(loadPromiseWrapper("divB", "page2.html"));
    init_tasks.push(loadPromiseWrapper("divC", "page3.html"));

    await Promise.all(init_tasks);

    // never gets here because none of the Promises resolve

}

What am I missing? How do I properly wrap the returned callback of jquery's load function in to a Promise, so that I can use Promise.all and wait for all the individual pieces to complete?

CodePudding user response:

.load can take more parameters and one of them is a complete callback. That is where you should put the resolve

function loadPromiseWrapper(dom_id, filename) {
    return new Promise(function(resolve, reject) {
        $(dom_id).load(filename, resolve);
    }); 
}
  • Related