I'm writing a Chrome Extension that can get HTTP response for a site. I try to use debugger for getting response body:
var gCurrentTab;
chrome.debugger.onEvent.addListener(function (source, method, params) {
if (gCurrentTab.id != source.tabId) {
return;
}
if (method == "Network.loadingFinished") {
var tabId = source.tabId;
var requestId = params.requestId;
chrome.debugger.sendCommand(
source,
"Network.getResponseBody",
{"requestId": requestId},
function (body) {
console.log(body);
chrome.debugger.detach(source);
});
}
}
);
chrome.webRequest.onBeforeRequest.addListener(function (details) {
var url = details.url;
if (url.indexOf('/mypage') >= 0) {
chrome.tabs.query({
currentWindow: true,
active: true
}, function (tabs) {
gCurrentTab = tabs[0];
chrome.debugger.attach({
tabId: gCurrentTab.id
}, "1.0", function () {
chrome.debugger.sendCommand({
tabId: gCurrentTab.id
}, "Network.enable");
});
});
}
},
{urls: []}, ["requestBody", "blocking"]);
But I always get
Unchecked runtime.lastError while running debugger.sendCommand: {"code":-32000,"message":"No resource with given identifier found"} at chrome-extension://ikphgobkghdkjkfplgokmapjlbdfeegl/background.js:11:29
error, and the body is undefined.
Does anyone have idea about why this happen? Thanks!
I'm writing a Chrome Extension that can get HTTP response for a site. I try to use debugger for getting response body:
var gCurrentTab;
chrome.debugger.onEvent.addListener(function (source, method, params) {
if (gCurrentTab.id != source.tabId) {
return;
}
if (method == "Network.loadingFinished") {
var tabId = source.tabId;
var requestId = params.requestId;
chrome.debugger.sendCommand(
source,
"Network.getResponseBody",
{"requestId": requestId},
function (body) {
console.log(body);
chrome.debugger.detach(source);
});
}
}
);
chrome.webRequest.onBeforeRequest.addListener(function (details) {
var url = details.url;
if (url.indexOf('/mypage') >= 0) {
chrome.tabs.query({
currentWindow: true,
active: true
}, function (tabs) {
gCurrentTab = tabs[0];
chrome.debugger.attach({
tabId: gCurrentTab.id
}, "1.0", function () {
chrome.debugger.sendCommand({
tabId: gCurrentTab.id
}, "Network.enable");
});
});
}
},
{urls: []}, ["requestBody", "blocking"]);
But I always get
Unchecked runtime.lastError while running debugger.sendCommand: {"code":-32000,"message":"No resource with given identifier found"} at chrome-extension://ikphgobkghdkjkfplgokmapjlbdfeegl/background.js:11:29
error, and the body is undefined.
Does anyone have idea about why this happen? Thanks!
Share Improve this question edited Jan 15, 2022 at 16:12 Bruno Francisco 4,2206 gold badges35 silver badges73 bronze badges asked Dec 24, 2017 at 16:01 Romulus Urakagi Ts'aiRomulus Urakagi Ts'ai 3,87012 gold badges45 silver badges76 bronze badges3 Answers
Reset to default 6It was because the website sends many responses, and this code will see another request other than I want, then detach the debugger so I can't get the result.
To solve this, just use a single debugger and do not detach it, or only detach when it's safe to.
var gAttached = false;
var gRequests = [];
var gObjects = [];
chrome.debugger.onEvent.addListener(function (source, method, params) {
if (method == "Network.requestWillBeSent") {
// If we see a url need to be handled, push it into index queue
var rUrl = params.request.url;
if (getTarget(rUrl) >= 0) {
gRequests.push(rUrl);
}
}
if (method == "Network.responseReceived") {
// We get its request id here, write it down to object queue
var eUrl = params.response.url;
var target = getTarget(eUrl);
if (target >= 0) {
gObjects.push({
requestId: params.requestId,
target: target,
url: eUrl
});
}
}
if (method == "Network.loadingFinished" && gObjects.length > 0) {
// Pop out the request object from both object queue and request queue
var requestId = params.requestId;
var object = null;
for (var o in gObjects) {
if (requestId == gObjects[o].requestId) {
object = gObjects.splice(o, 1)[0];
break;
}
}
// Usually loadingFinished will be immediately after responseReceived
if (object == null) {
console.log('Failed!!');
return;
}
gRequests.splice(gRequests.indexOf(object.url), 1);
chrome.debugger.sendCommand(
source,
"Network.getResponseBody",
{"requestId": requestId},
function (response) {
if (response) {
dispatch(source.tabId, object.target, JSON.parse(response.body));
} else {
console.log("Empty response for " + object.url);
}
// If we don't have any request waiting for response, re-attach debugger
// since without this step it will lead to memory leak.
if (gRequests.length == 0) {
chrome.debugger.detach({
tabId: source.tabId
}, function () {
chrome.debugger.attach({
tabId: source.tabId
}, "1.0", function () {
chrome.debugger.sendCommand({
tabId: source.tabId
}, "Network.enable");
});
});
}
});
}
}
);
var initialListener = function (details) {
if (gAttached) return; // Only need once at the very first request, so block all following requests
var tabId = details.tabId;
if (tabId > 0) {
gAttached = true;
chrome.debugger.attach({
tabId: tabId
}, "1.0", function () {
chrome.debugger.sendCommand({
tabId: tabId
}, "Network.enable");
});
// Remove self since the debugger is attached already
chrome.webRequest.onBeforeRequest.removeListener(initialListener);
}
};
// Attach debugger on startup
chrome.webRequest.onBeforeRequest.addListener(initialListener, {urls: ["<all_urls>"]}, ["blocking"]);
// Filter if the url is what we want
function getTarget(url) {
for (var i in TARGETS) {
var target = TARGETS[i];
if (url.match(target.url)) {
return i;
}
}
return -1;
}
const TARGETS = [
{url: '/path1', desc: 'target1'},
{url: '/path2', desc: 'target2'}
]
From my experience, it's possible that the request has not finished yet. You could try import time;time.sleep(5)
before getResponseBody.
I am facing similar issue. I figured that sendCommand was not executing immediately. I was facing the issue for the requests which are sent before sending "Network.enable" was complete. Try adding completion for
chrome.debugger.sendCommand({
tabId: gCurrentTab.id
}, "Network.enable")