Javascript/jQuery DOM创建是否安全,直到';文档中添加了什么?

Javascript/jQuery DOM创建是否安全,直到';文档中添加了什么?,javascript,jquery,security,dom,Javascript,Jquery,Security,Dom,请仔细阅读此声明:假设在将任何元素添加到文档之前,已删除$dom中的所有不安全元素。但它们最初是被创造出来的。好的,让我们继续 如果处理了一段用户文本,并且可以像这样加载: var comment = 'I\'m a naughty person!!' + '<script src="http://blah.com/some_naughty_javascript.js">'; var $dom = $('<div>' +

请仔细阅读此声明:假设在将任何元素添加到
文档之前,
已删除$dom中的所有不安全元素。但它们最初是被创造出来的。好的,让我们继续


如果处理了一段用户文本,并且可以像这样加载:

var comment = 'I\'m a naughty person!!' +
              '<script src="http://blah.com/some_naughty_javascript.js">';
var $dom = $('<div>' + comment + '</div>');
这将不自觉地导致浏览器请求所有图像

任何人都将获得赏金

  • 谁能提供一种好的、安全的方式来处理ajax请求而不出现上述问题
  • 理想情况下不提供正则表达式答案。。。i、 如果我们想做
    $(responseHTML).find('img')
    ——用regex删除图像标签不是一个选项,因此需要一种不引人注目的方式来停止src的加载,但仍然具有相同的属性、结构等

    • 好问题。似乎可以插入脚本并在其中放置事件处理程序。我已经使用以下HTML进行了测试:

      <!DOCTYPE html>
      <html lang="en">
          <head>  
              <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1/jquery.min.js"></script>
              <script type="text/javascript"> 
                  <!-- 
                  $(function() {
                      var $dom = $('<script>$(".testbutton").live("click", function() { alert("hi") });</script>');
      
                      $(".firstbutton").click(function() {
                          $("BODY").append($dom);
                      });
                  });
                  -->
              </script>
          </head>
      
          <body style="padding:0">            
              <button class="firstbutton">Click this first</button>
      
              <button class="testbutton">Then this</button>
          </body>
      </html>
      
      
      先点击这个
      那么这个
      
      您可以看到,在单击第一个按钮并将脚本标记添加到DOM之前,第二个按钮没有任何效果

      如果采用用户表单输入并将其动态插入页面,则这可能会被滥用。在这种情况下,应明确使用数据消毒


      这是我从来没有想到过的——感谢您提出它。

      只要脚本没有附加到DOM中,它似乎就无法工作

      $(function ()
      {
          var ss = document.createElement('script');
          var scr = 'alert("bah");';
          var tt = document.createTextNode(scr);
          ss.appendChild(tt);
          var hh = document.getElementsByTagName('head')[0];
          //hh.appendChild(ss);
      });
      

      这本身在任何情况下都是危险的吗 路?我的意思是,你能不能 以某种方式创建DOM的简单行为 注射任何东西,还是仅仅注射 经过加工,结构简单 创造

      简单地创建一个元素而不将其附加到dom不会导致任何脚本运行,因为此时它纯粹是一个对象(HtmlScriptElement)。当脚本元素实际附加到dom中时,浏览器将计算并运行脚本元素。话虽如此,我认为一个非常狡猾的人可能会利用某个框架或浏览器中存在的bug来造成不希望的结果

      考虑这个例子:

      <p>
          <input type="button" value="Store 'The Script' In Variable" id="store"/>
          <input type="button" value="Append 'The Script' To Dom" id="append"/>
      </p>
      <br/>
      <p>
          <input type="button" value="Does nothing"/>
      </p>
      <h1>The Script</h1>
      <pre id="script">
          $(function(){
              function clickIt(){
                  $(this).clone().click(clickIt).appendTo("body");
              }
              $("input[type='button']").val("Now Does Something").click(clickIt);
          });
      </pre>
      
      var theScript;
      
      $("#store").click(function() {
          theScript = document.createElement('script');
          var scriptText = document.createTextNode($("#script").text());
          theScript.appendChild(scriptText);
      });
      
      $("#append").click(function() {
          var head = document.getElementsByTagName('head')[0];
          head.appendChild(theScript);
      });
      
      
      


      剧本 $(函数(){ 函数clickIt(){ $(this).clone()。单击(clickIt).appendTo(“body”); } $(“输入[type='button']).val(“现在做某事”)。单击(clickIt); }); 变量脚本; $(“#存储”)。单击(函数(){ 脚本=document.createElement('script'); var scriptText=document.createTextNode($(“#脚本”).text(); appendChild(脚本文本); }); $(“#追加”)。单击(函数(){ var head=document.getElementsByTagName('head')[0]; head.appendChild(脚本); });
      当您单击
      store
      时,它将创建HtmlScriptElement并将其存储到变量中。您将注意到,即使创建了对象,也不会运行任何操作。只要单击
      append
      ,脚本就会被追加到dom中并立即进行计算,按钮会执行一些不同的操作


      javascript/jquery中的任何函数都可以“监视”元素吗 以这种方式和行为被创造的 在它被剥去坏的 元素并放在文档中

      jQuery在某种程度上已经为您做到了这一点,就像它执行一些内部脚本评估一样


      .append()

      jQuery的所有插入方法都使用 一个domManip函数,内部用于 清洁/处理之前和之后的元件 将它们插入DOM之后。 其中一件事就是多曼尼普 函数的作用是拉出任何脚本 将要插入并运行的元素 通过一个“evalScript例程” 而不是把剩下的注射进去 DOM片段的。它插入 单独编写脚本,对其进行评估, 然后将它们从DOM中删除。

      调用
      append()
      时,您可以改变jQuery的行为以删除所有
      并使用内联javascript
      onclick、mouseover等清理其他元素,但是这只会影响jQuery,因为有人可以轻松地使用普通javascript来追加
      元素

      Dom突变事件

      是否定义了一些Dom突变事件来捕获添加到Dom中的元素?我们将查看事件。但是,它是在添加元素后激发的注意,根据Raynos,这些是当前的

      当节点已启动时激发DomainNodeInserted 已作为另一节点的子节点添加。 此事件在 插入已发生。目标 此事件的名称是正在执行的节点 插入。气泡:是可取消:否 上下文信息:relatedNode保存 父节点

      最后,似乎没有什么可以完全阻止通过其他javascript将
      附加到dom中。(至少我找不到)

      我建议最好的方法是永远不要相信用户输入,因为所有用户输入都是邪恶的。在执行dom操作时,请仔细检查以确保没有禁止的标记,无论是
      还是普通的

      元素,并在持久化之前对所有输入进行清理

      正如John指出的,您需要担心任何可以附加
      onclick
      事件的元素或任何内联javascript事件处理程序。

      这是对第一个示例的强制性响应 因此,以这种方式创建的文档似乎是解析和探索HTML的好沙盒。您甚至可以在不同文档(
      $(doc.body)
      )中的节点周围创建jQuery包装器,并通过jQueryAPI进行探索。找到要查找的节点后,可以将其转换回
      $(function ()
      {
          var ss = document.createElement('script');
          var scr = 'alert("bah");';
          var tt = document.createTextNode(scr);
          ss.appendChild(tt);
          var hh = document.getElementsByTagName('head')[0];
          //hh.appendChild(ss);
      });
      
      $(function ()
      {
          var ss = document.createElement('script');
          var scr = 'alert("bah");';
          var tt = document.createTextNode(scr);
          ss.appendChild(tt);
          var hh = document.getElementsByTagName('head')[0];
          hh.appendChild(ss);
      });
      
      <p>
          <input type="button" value="Store 'The Script' In Variable" id="store"/>
          <input type="button" value="Append 'The Script' To Dom" id="append"/>
      </p>
      <br/>
      <p>
          <input type="button" value="Does nothing"/>
      </p>
      <h1>The Script</h1>
      <pre id="script">
          $(function(){
              function clickIt(){
                  $(this).clone().click(clickIt).appendTo("body");
              }
              $("input[type='button']").val("Now Does Something").click(clickIt);
          });
      </pre>
      
      var theScript;
      
      $("#store").click(function() {
          theScript = document.createElement('script');
          var scriptText = document.createTextNode($("#script").text());
          theScript.appendChild(scriptText);
      });
      
      $("#append").click(function() {
          var head = document.getElementsByTagName('head')[0];
          head.appendChild(theScript);
      });
      
      var comment = 'I\'m a naughty person!!' +
                    '<script src="http://blah.com/some_naughty_javascript.js">';
      var $dom = $('<div>' + comment + '</div>');
      
      var $dom = $('<div>').text(comment);
      
      var doc = document.implementation.createHTMLDocument(''),
          img = doc.createElement('img');
      img.src = 'http://example.com/image.jpg'; // Nothing happens.
      // Alternatively…
      doc.body.innerHTML = '<img src="http://example.com/image.jpg">'; // Nope.
      
      {
          "inputs": [
              '<input …>',
              '<input …>'
          ],
      }