Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Disabling javascript with javascript by injecting Content-Security-Policy

Edit: if there is another way of disabling javascript with javascript - I'm all ears.

I'm trying to disable javascript using javascript, by "injecting" a

<meta http-equiv="Content-Security-Policy" content="script-src 'none' ">

Into the element. The element IS added, according to Firefox dev tools -> inspector, but is ignored. Why, and how can I make a browser to "notice" it?

<!DOCTYPE html>
<html>
  <head>
    <meta charset="UTF-8">
    <!-- 
      yes, this works, but I want to do this dynamically
      <meta http-equiv="Content-Security-Policy" content="script-src 'none' ">
    -->
  </head>

  <body>
    Just some javascript for tests, I hoped this will stop working, 
    when I'll call the  disableJavaScript() function below. But it
    doesn't stop    
    <script>
      var x =  0;
      setInterval(function(){
        console.log(x++);
      }
      ,1000);
    </script>

    Inserting the meta element:

    <script>
    function disableJavaScript(){
        var newMetaNode = document.createElement("meta");
        newMetaNode.setAttribute('http-equiv','Content-Security-Policy'); 
        newMetaNode.setAttribute('content',"script-src 'none'");
        var headElem = document.getElementsByTagName('head')[0];
        headElem.appendChild(newMetaNode);
      }

    //calling the function after 3 seconds:
    setTimeout(function(){
      disableJavaScript();  
    },3000)  

    </script>

  </body>

</html> 
like image 526
konrados Avatar asked Mar 31 '26 00:03

konrados


1 Answers

script-src policy does NOT disable JavaScript. It disables loading of new content referenced with <script> tags that are inserted into a document after you declare your policy.

Policies in meta elements are not applied to content which precedes them.

https://w3c.github.io/webappsec-csp/#meta-element

You can see it working perfectly fine with new content and stopping output in console after a few successful calls if you change your "testing" tag to:

<script>
  var x =  0;
  setInterval(function(){
    var newNode = document.createElement("script");
    var newText = document.createTextNode("console.log("+ x++ +")")
    var bodyElem = document.getElementsByTagName('body')[0];
    newNode.appendChild(newText)
    bodyElem.appendChild(newNode);
  }
  ,1000);
</script>

CSP does not have means to somehow retroactively "cancel" content that was loaded before it was enforced. You need to look in browser-specifc extension API.

like image 191
Oleg V. Volkov Avatar answered Apr 02 '26 13:04

Oleg V. Volkov



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!