I have been smashing my head against this problem for a very long time; far too long for what it, almost certainly trivial.
I want to get a specific value, as if it were returned by a function. Promises are supposed to be placeholders for values and onAuthRequired takes a function that returns a blocking response object:
{
authCredentials: {
username: "..."
password: "..."
}
}
So I need to create a function that returns that structure and does so asynchronously. So I put in the async
keyword, meaning I can await
the resolution of the promise ... I think.
But before I can build that structure, I have to do an asynchronous operation on the nativeMessaging API ... which doesn't return a promise ... I think.
So I have to wrap it, somehow, in a promise ...
Edit: I have updated the code below to reflect the current state, an amalgam of all the great responses thus far.
async function get_data() {
return new Promise((resolve, reject) => {
var data = chrome.runtime.sendNativeMessage('Host', {text:'Ready'},
function(response) {
resolve(response);
}
};
})
};
async function get_creds() {
var data = await get_data();
if (null != data) {
creds = JSON.parse(data);
return {
authCredentials: {
username: creds.username,
password: creds.password
}
};
}
};
chrome.webRequest.onAuthRequired.addListener(
function(details, get_creds),
{urls: ["<all_urls>"]},
['blocking']
);
I experimented with the following code:
chrome.webRequest.onAuthRequired.addListener(
function handler(details){
var creds = await get_data(); // Uncaught SyntaxError: unexpected identifier
creds = JSON.parse(creds);
return {
authCredentials: {
username: creds.username,
password: creds.password
}
};
},
{urls:["<all_urls>"]},
['asyncBlocking']
);
It called get_data()
directly but had an unexpected identifier error.
If I removed the await
keyword it "worked" ... that is, it tried to do something on the event ... but it didn't pass the object back. What it did is set a message in the bottom left of the screen "waiting on extension ... " and call the get_data()
function about 3 times.
If I change ['asyncBlocking']
to ['blocking']
, it fails to call get_data() at all.
I have no idea what's happening here.
So this should pass the value returned by the Native Messaging Host back via these weird promises and then plug right in to where onAuthRequired expects its JSON structure to be returned ...
Edit:
I expect the object returned by get_creds() to be passed to onAuthRequired.
At this present point, there's an 'unexpected token' token on function(details, get_creds)
... so that's obviously wrong.
I suspect that I might need to use another promise in get_creds()
which will fill in for the authCredentials
object ...
Aside from all the unexpected identifiers whose origin I can't fathom, I've a sense that I'm doing this whole thing backwards.
Welcome to my wit's end ... and thanks for any light you can shed on my ignorance.
You are returning a promise on get_creds() but you are doing nothing with it.
try to return just the result that you want on
get_creds()
like this:To answer the question "How do I get values out of promises?" I was informed by all 3 provided examples. No one had the full solution, however.
Edit:
Full solution to my specific problem (as it happens, it used callbacks, not promises) is here.
Caveat - While I have managed to have an object passed back to
onAuthRequest
by passing values back through promises, there is some issue with the object, such that it's not having the desired effect.Firstly,
get_data()
needed to be changed.Next, I was returning a promise on
get_creds()
(nowget_data()
) ... but I wasn't doing anything with it. I needed to usepromiseFunction.then(function(response){ ... })
in order to move the resolved value of the promise out. This was helpful, too.Additionally, I needed to return an object - which is done via the callback:
Finally, there needs to be a modification of the callback to allow the promise.then() to output something ... Found here
becomes:
So that's how to get the value out of that promise and into the callback function... I have more work to do to get the desired result, however.
Your
get_data()
method needs to change.sendNativeMessage
returns a promise if I am correct. Firefox'ssendNativeMessage
does this returns a promise.You need to resolve the promise using
.then
and then resolve it using the wrapper'sresolve
callback.If the function does not return a promise, then looks like it accepts and optional callback which will have the response.
https://developer.chrome.com/apps/runtime#method-sendNativeMessage
Also, this, the addListener expects a callback but you seem to be invoking it. And the documentation does not show any other arguments. You might want to check this https://developer.chrome.com/extensions/webRequest#event-onAuthRequired
If your function needs to return an object and not a promise (which is what an
async
function always returns), then a simple function will do: