Я пытаюсь передать сообщения между содержимым скрипта и расширением
Вот что у меня есть в контент-скрипте
chrome.runtime.sendMessage({type: "getUrls"}, function(response) {
console.log(response)
});
И в фоновом режиме сценарий у меня есть
chrome.runtime.onMessage.addListener(
function(request, sender, sendResponse) {
if (request.type == "getUrls"){
getUrls(request, sender, sendResponse)
}
});
function getUrls(request, sender, sendResponse){
var resp = sendResponse;
$.ajax({
url: "http://localhost:3000/urls",
method: 'GET',
success: function(d){
resp({urls: d})
}
});
}
Теперь, если я отправляю ответ до вызова ajax в getUrls
функции, ответ отправляется успешно, но в методе успеха вызова ajax, когда я отправляю ответ, он не отправляет его, когда я иду в отладку, я вижу, что Порт является нулевым внутри кода для sendResponse
функции.
Ответы:
Из документации для
chrome.runtime.onMessage.addListener
:Так что вам просто нужно добавить
return true;
после вызова,getUrls
чтобы указать, что вы будете вызывать функцию ответа асинхронно.источник
<blink>
и<marquee>
тегами где-то на странице.Принятый ответ правильный, я просто хотел добавить пример кода, который упрощает это. Проблема в том, что API (на мой взгляд) не очень хорошо разработан, потому что заставляет нас, разработчиков, знать, будет ли конкретное сообщение обрабатываться асинхронно или нет. Если вы обрабатываете много разных сообщений, это становится невыполнимой задачей, потому что вы никогда не знаете, будет ли в глубине какой-то функции переданный sendResponse вызываться как асинхронный или нет. Учти это:
Как я могу узнать, будет
handleMethod1
ли вызов в глубине асинхронным или нет? Как может кто-то, кто изменяет,handleMethod1
знает, что он сломает вызывающую сторону, введя что-то асинхронное?Мое решение таково:
Это автоматически обрабатывает возвращаемое значение, независимо от того, как вы решите обработать сообщение. Обратите внимание, что это предполагает, что вы никогда не забудете вызвать функцию ответа. Также обратите внимание, что хром мог автоматизировать это для нас, я не понимаю, почему они этого не сделали.
источник
chrome.extension.onRequest
/chrome.exension.sendRequest
методы ведут себя именно так, как вы описываете. Эти методы устарели, потому что оказывается, что многие разработчики расширений НЕ закрывали порт сообщения. Текущий API (требующийreturn true
) - лучший дизайн, потому что терпеть неудачу лучше, чем молча.return true;
. Это не препятствует очистке порта, если вызов синхронизирован, в то время как асинхронные вызовы все еще обрабатываются правильно. Код в этом ответе вносит ненужную сложность без видимой выгоды.Вы можете использовать мою библиотеку https://github.com/lawlietmester/webextension, чтобы сделать эту работу как в Chrome, так и в FF с помощью Firefox без обратных вызовов.
Ваш код будет выглядеть так:
источник