Calling Script Directly (works)
// ==UserScript==
// @name Example
// @version 0.1
// @description Script from a website
// @author You
// @match *://*.example.com/*
// @grant none
// @require https://cdnjs.cloudflare.com/ajax/libs/socket.io/2.0.4/socket.io.js
// @require https://code.jquery.com/jquery-3.2.1.min.js
// ==/UserScript==
/* script here: */
Calling Script Externally (doesn't work)
// ==UserScript==
// @name Example
// @version 0.1
// @description Script from a website
// @author You
// @match *://*.example.com/*
// @grant GM_xmlhttpRequest
// @require https://cdnjs.cloudflare.com/ajax/libs/socket.io/2.0.4/socket.io.js
// @require https://code.jquery.com/jquery-3.2.1.min.js
// @run-at document-start
// ==/UserScript==
GM_xmlhttpRequest({
method : "GET",
url : "http://example.com/script.js",
onload : (e) => {
eval(e.responseText);
}
});
我需要使用tampermonkey将从单独网站存储的JavaScript文件直接加载到网站。将代码直接加载到tampermonkey文档中是可行的,除非从站点调用它即可。
直接将代码加载到tampermonkey文档中是可行的,除非您从站点调用它。
我理解您的陈述,您试图从页面的脚本中调用某些GM加载的函数。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Userscript-Test</title>
</head>
<body>
<button id="test-btn">injected script</button>
<script>
// invoke testFunction() which is loaded by the user-script.
document.getElementById('test-btn').addEventListener('click', ev => testFunction());
</script>
</body>
</html>
您的第二个用户脚本实际上确实起作用,但是,根据当前TamperMonkey版本的默认设置,如果该域与same-origin-policy不匹配,将要求用户允许该域的跨域获取。如果允许,您可以通过eval
执行该脚本后从您的用户脚本中访问动态加载的脚本。
当然,脚本是在TamperMonkey沙箱中评估的。因此,您无权访问该页面。
您需要inject脚本到页面中,以使其也可用于页面的脚本。例如。您可以动态创建一个<script>
标签。
// ==UserScript==
// @name Example
// @version 0.1
// @description Script from a website
// @author You
// @match *://*.example.com/*
// @grant GM_xmlhttpRequest
// @run-at document-start
// ==/UserScript==
GM_xmlhttpRequest({
method : "GET",
// from other domain than the @match one (.org / .com):
url : "http://example.org/script.js",
onload : (ev) =>
{
let e = document.createElement('script');
e.innerText = ev.responseText;
document.head.appendChild(e);
}
});
为了与较早的用户脚本扩展兼容,您可能需要使用unsafeWindow.document.head
和@grant unsafeWindow
。 (但是,请注意安全问题。)
您可能还希望@run-at document-start
在所有其他脚本之前要求扩展名尽快运行该脚本。 DOM可能尚未准备好。您可以确定何时准备插入DOM。请注意,某些插件不能保证用户脚本的实际启动时间。
如果动态加载的脚本不经常更改,请考虑在安装时使用@resource
预取它,然后从本地存储中加载它。另请参阅GM.getResourceUrl。您可以使用该URL来获取GM_xmlhttpRequest
。