I having a problem (well two if I'm honest) getting a promise or a callback to work inside a switch-case. Here is the basic code.
switch (page) {
case 'contact':
alert('contact in switch');
var promise = $.get(page +'.json');
promise.then(function(data){
console.log("Items back! ", data);
});
break;
.......
console.log("Response data: ", data); // This is undefined
I understand that due to the nature of async functions, the switch is falling through to the break
before the data comes back, making data
log as undefined
. So I thought putting the break
inside the callback would work but it doesn't. When I do that the app stops working entirely.
So I guess my first question is how do I make the switch-case
"wait" until the data comes back before going to break
.
The second problem I have is that I ultimately want to be able to reuse my switch
by wrapping it in a function where the page
argument is the title of the page the user is navigating to and the callback will pass back the data returned from the getPageData
function. When I try this it results in an undefined
error for the callback of the pageContentLoader
function.
For the record, the getPageData
in the code below is a separate function which performs a generic XMLHttpRequest. It's working fine because the data gets logged correctly in the callback.
pageContentLoader(page, function(data) {
console.log("Back with data ", data);
});
function pageContentLoader(page, callback){
var data;
switch (page) {
case 'contact':
console.log('contact in switch');
getPageData(page,function(data){
console.log("Contacts back! ", data);
});
break;
case 'blog':
console.log('blog in switch');
getPageData(page,function(data){
console.log("Posts back! ", data);
});
break;
default:
alert('hey that page doesn't exist!');
}
callback(data); // results in callback undefined!!
}
I am sure it is possible to make this work but I've tried everything I can find without any luck so far. If anyone has any pointers or wants to tell me what I am doing wrong within my code I'd be grateful!
Just ran into to this problem earlier, solved it as follows:
async getResolvedPromises(myObject) {
const promises = await Object.keys(myObject).map(async (k) => {
switch (k) {
case '1':
const firstPromise = await asyncCallNumber1()
return firstPromise
case '2':
const secondPromise = await asyncCallNumber2()
return secondPromise
case '3':
const thirdPromise = await asyncCallNumber3()
return thirdPromise
default:
return
}
})
const data = await Promise.all(promises)
return data
}
Here's a recent example in Typescript that I've adapted:
private pageContentLoader = async (): Promise<any> => {
try {
switch(page) {
case 'contact':
return await getPageData(page).then((data) => {
console.log("Contacts back! ", data);
return data;
})
case 'blog':
return await getPageData(page).then((data) => {
console.log("Posts back! ", data);
return data;
})
default:
return 'Page does not exist';
}
} catch (err) {
throw err;
}
}
private getPageContent = async () => {
try {
const contactPageData = await pageContentLoader('contact');
const blogPageData = await pageContentLoader('blog');
} catch (err) {
throw err;
}
};
Here's a solution using the Promise constructor:
pageContentLoader('blog').then(function(data) { console.log("Call to pageContentLoader results: ", data); }); function pageContentLoader(page) { switch (page) { case 'contact': return new Promise(function(resolve) { console.log('contact in switch'); getPageData(page).then(function(data) { console.log("pageContentLoader results: ",data); resolve(data) }); }); break; case 'blog': return new Promise(function(resolve) { console.log('blog in switch'); getPageData(page).then(function(data) { console.log("pageContentLoader results: ",data); resolve(data) }); }); break; default: return new Promise(function(resolve) { console.log('default in switch'); console.log("pageContentLoader results: doesn't exist"); resolve("page doesn't exist"); }); } } function getPageData(page) { return new Promise(function(resolve) { window.setTimeout(function() { console.log('getPageData executed') resolve(page); },2000); }); }
enter code here
For the first problem: You are trying to load a value of something that might not have been defined. As said, you need to think about learning some tips and tricks of asynchronous coding but here's a solution :
switch (page) {
case 'contact':
alert('contact in switch');
$.get(page +'.json').then(function(data){
/* all the code AFTER fulfilling
the promise should BE here
*/
handle_data(data);
});
break;
//console.log("Response data: ", data); this should not be here
...
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.