[英]How do I inject javascript to a page on IE 8?
假设我有以下标记:
<div id="placeHolder"></div>
我有一个 JavaScript 变量jsVar
,其中包含一些标记和一些 JavaScript。
通过使用 Mootools 1.1,我可以将 JavaScript 内容注入占位符,如下所示:
$('placeHolder').setHTML(jsVar);
这适用于 Firefox、Opera,甚至 Safari,生成的标记如下所示:
<div id="placeHolder">
<strong>I was injected</strong>
<script type="text/javascript">
alert("I was injected too!");
</script>
</div>
但是,在 IE 8 上,我得到以下信息:
<div id="placeHolder">
<strong>I was injected</strong>
</div>
有没有办法在 IE 8 上注入 JavaScript 或者它是否安全 model 完全禁止我这样做?
我尝试了 Luca Matteis 的使用建议
document.getElementById("placeHolder").innerHTML = jsVar;
而不是 MooTools 代码,我得到了相同的结果。 这不是 MooTools 问题。
这篇MSDN 帖子专门讨论了如何使用 innerHTML 将 javascript 插入页面。 你是对的:IE 确实认为这是一个安全问题,所以需要你跳过某些环节才能注入脚本......大概黑客可以像我们一样阅读这个 MSDN 帖子,所以我很茫然为什么 MS 认为这个额外的间接层是“安全的”,但我离题了。
来自 MSDN 文章:
<HTML>
<SCRIPT>
function insertScript(){
var sHTML="<input type=button onclick=" + "go2()" + " value='Click Me'><BR>";
var sScript="<SCRIPT DEFER>";
sScript = sScript + "function go2(){ alert('Hello from inserted script.') }";
sScript = sScript + "</SCRIPT" + ">";
ScriptDiv.innerHTML = sHTML + sScript;
}
</SCRIPT>
<BODY onload="insertScript();">
<DIV ID="ScriptDiv"></DIV>
</BODY>
</HTML>
如果可能的话,您可能希望考虑使用document.write
注入脚本加载标签来提高安全性并减少跨浏览器的不兼容性。 我知道这可能是不可能的,但值得考虑。
大约一年前,我们就是这样在我们的网站上做的,让它在 IE 中运行。 以下是步骤:
function set_html( id, html ) { // create orphan element set HTML to var orphNode = document.createElement('div'); orphNode.innerHTML = html; // get the script nodes, add them into an arrary, and remove them from orphan node var scriptNodes = orphNode.getElementsByTagName('script'); var scripts = []; while(scriptNodes.length) { // push into script array var node = scriptNodes[0]; scripts.push(node.text); // then remove it node.parentNode.removeChild(node); } // add html to place holder element (note: we are adding the html before we execute the scripts) document.getElementById(id).innerHTML = orphNode.innerHTML; // execute stored scripts var head = document.getElementsByTagName('head')[0]; while(scripts.length) { // create script node var scriptNode = document.createElement('script'); scriptNode.type = 'text/javascript'; scriptNode.text = scripts.shift(); // add the code to the script node head.appendChild(scriptNode); // add it to the page head.removeChild(scriptNode); // then remove it } } set_html('ph', 'this is my html. alert("alert");');
我在 IE8(和 IE7)中遇到了同样的问题 我可以动态注入脚本(使用 src)的唯一方法是使用计时器:
source = "bla.js";
setTimeout(function () {
// run main code
var s = document.createElement('script');
s.setAttribute('src', source);
document.getElementsByTagName('body')[0].appendChild(s);
}, 50);
如果您有要注入的内联代码,您可以删除计时器并为脚本元素使用“文本”方法:
s.text = "alert('hello world');";
我知道我的答案来得太晚了; 但是,迟到总比没有好:-)
对不起,也许我在这里遗漏了一些东西——但这是一个 mootools 1.11 的问题,你为什么不使用 assets.js?
// you can also add a json argument with events, etc.
new Asset.javascript("path-to-script.js", {
onload: function() {
callFuncFromScript();
},
id: "myscript"
});
这难道不是我们使用框架不必重新发明轮子的原因之一吗……
就“其他”内容而言,您是如何获得的? 如果通过请求 class,它可以通过使用选项很好地完成您想要的事情:
{
update: $("targetId"),
evalScripts: true,
evalResponse: false
}
我不确定 MooTools,但您尝试过 innerHTML 吗?
document.getElementById("placeHolder").innerHTML = jsVar;
您可能需要评估 script 标签的内容。 这将需要解析以在您的 jsVar 和 eval(whatsBetweenTheScriptTags) 中查找脚本。
由于 IE 默认拒绝插入内容,您必须自己执行它,但您至少可以欺骗 IE 为您进行解析。
只需使用string.replace()
将所有<script>
标签交换为<textarea class="myScript" style="display:none">
,保留内容。 然后将结果粘贴到 div 的innerHTML
中。
完成后,您可以使用
div.getElementsByTagName("textarea")
要获取所有文本区域,请遍历它们并查找您的标记 class (在本例中为"myScript"
),以及您关心的eval(textarea.value)
或(new Function(textarea.value))()
。
我从来没有尝试过,它只是浮现在我的脑海......你可以试试以下:
var script = document.createElement('script');
script.type = 'text/javascript';
script.innerHTML = '//javascript code here'; // not sure if it works
// OR
script.innerText = '//javascript code here'; // not sure if it works
// OR
script.src = 'my_javascript_file.js';
document.getElementById('placeholder').appendChild(script);
您可以使用相同的技术 (DOM) 插入 HTML 标记。
当您说它在其他浏览器中“有效”时,您的意思是您会收到alert
弹出消息,还是只是意味着<script>
标记使其进入 DOM 树?
如果您的目标是前者,请意识到使用嵌入的<script>
注入 html 的行为非常依赖于浏览器。 例如在最新的 MooTools 我可以尝试:
$(element).set('html', '<strong>Foo</strong><script>alert(3)</script>')
而且我没有得到弹出窗口,没有在 IE(7) 中,也没有在 FF(3) 中(但是我确实将<script>
节点成功地放入了 DOM)。 要让它在所有浏览器中发出alert
,您必须按照此答案进行操作。
我的评论真的很晚,但它也是这里最准确的评论 - 您没有看到<script>
内容运行的原因是因为您没有将defer
属性添加到<script>
标记。 MSDN 文章特别指出您需要这样做才能使<script>
标记运行。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.