我正在使用Edge扩展,我需要从外部网站请求JSON。以下示例在stackoverflow.com上运行正常,但在我需要的地方使用steamcommunity.com/id/失败。
以下是我的文件:
jQuery(来自本地文件)
的manifest.json:
var time;
window.addEventListener('click', function() {
time = setTimeout(function() {
SaveUrl('Save/SetIsOnlineUser', { isOnline: false });
}, 20000);
})
window.addEventListener("click", myFunction);
function myFunction() {
clearTimeout(time)
SaveUrl('Save/SetIsOnlineUser', { isOnline: true });
}
myscript.js:
{
"author": "me",
"name": "Get JSON",
"description": "get json",
"version": "0.1",
"manifest_version": 2,
"content_scripts": [
{
"matches": [
"*://steamcommunity.com/id/*",
"*://stackoverflow.com/*"
],
"js": ["jquery.min.js", "myscript.js"]
}
]
}
正如我所说,这个例子在Stackoverflow上工作正常,但在Steam上失败了。
这是我在Steam网站上收到的错误:
var url = 'https://raw.githubusercontent.com/bahamas10/css-color-names/master/css-color-names.json';
$.getJSON(url, function(data) {
console.log(data);
});
编辑:我还应该补充一点,这个确切的示例在Google Chrome中使用Chrome扩展程序时效果很好。
任何帮助表示赞赏。
答案 0 :(得分:0)
与Chrome和Firefox不同,Microsoft Edge不会忽略网站CSP扩展规则。
有关未解决的问题,请参阅https://developer.microsoft.com/en-us/microsoft-edge/platform/issues/11320214/。
我知道的唯一可行的解决方法,我自己也测试过,是使用browser.webRequest.onHeadersReceived
动态更改CSP响应标头,幸运的是Edge中很好地支持。
注意:此代码改编自这篇精彩的文章,该文章还更详细地解释了问题:https://transitory.technology/browser-extensions-and-csp-headers/
代码将您的扩展名添加到每个CSP标头和指令的允许URL中,它应该在后台页面中执行,后台页面应设置为persistent
。
请务必将webRequest
和webRequestBlocking
权限添加到manifest.json
。
const cspHeaderNames = [
'content-security-policy',
'content-security-policy-report-only',
'x-webkit-csp'
];
// @see https://developer.mozilla.org/en-US/docs/Web/Security/CSP/CSP_policy_directives
const cspSources = [
'connect-src',
'default-src',
'font-src',
'frame-src',
'img-src',
'media-src',
'object-src',
'script-src',
'style-src',
'child-src',
'form-action',
];
const url = browser.extension.getURL("").slice(0, -1); // (remove trailing "/")
browser.webRequest.onHeadersReceived.addListener(details => {
details.responseHeaders.forEach(header => {
const isCspHeader = cspHeaderNames.indexOf(header.name.toLowerCase()) >= 0;
if (isCspHeader) {
let newValue = header.value;
cspSources.forEach(source => {
newValue = newValue.replace(source, source + ' ' + url);
});
header.value = newValue;
}
});
return {
responseHeaders: details.responseHeaders
};
}, {
urls: ['<all_urls>'],
types: ['main_frame', "sub_frame"],
}, ["blocking", "responseHeaders"]);