0

Is there any way to completely stop any HTTP requests from being executed within a certain script tag in HTML? I own a site where users can set their own "bio" and it allows HTML and JavaScript. It poses a security issue to my site because an admin could visit the site and use the admin to send requests to delete other resources on the site. I want to completely stop all requests within this specific script tag so it can't send requests to other sites or the current site. I've looked into CSP (Content Security Policy) but couldn't find what I was looking for. Anyone know of a way?

Jacob Gunther
  • 351
  • 5
  • 14
  • 10
    Why would you ever allow your users to include JS on your website? – Luca Kiebel Apr 06 '18 at 12:56
  • @Luca It makes my site unique to other sites while offering the ability to use JavaScript. It gives customizability to it. – Jacob Gunther Apr 06 '18 at 12:58
  • 4
    @JacobGunther: It also makes your site uniquely vulnerable. *That's* the reason nobody allows it. Sorry, can't have your cake and eat it, too. – Piskvor left the building Apr 06 '18 at 12:59
  • 2
    So wouldn't it be best to validate the login and permissions of that user before executing anything you might not want to run? – NewToJS Apr 06 '18 at 12:59
  • 4
    I think I know why that is such a unique attribute no other site does… – deceze Apr 06 '18 at 12:59
  • 4
    `window.location="http://your-site.com.phish.rs"` - no http request, but now the user is left sitting on a phishing site clone of your site thinking they need to enter their credentials to continue. – xdumaine Apr 06 '18 at 13:02
  • @xdumaine That's true, see my comment in the answer below. – Jacob Gunther Apr 06 '18 at 13:04
  • @JacobGunther The core reason behind this is that you're enabling one user to run code on many other users's computers. This is inherently dangerous and you cannot protect against all threats, try though you might. Please do not do this. – xdumaine Apr 06 '18 at 13:05
  • @xdumaine Yes, I know. As I said, please look at the comments in the answer below. – Jacob Gunther Apr 06 '18 at 13:06

3 Answers3

1

Kind of, but not really. You could technically override all of the methods that allow for HTTP requests to be made in JavaScript (fetch(), XMLHttpRequest, etc.) but this is easily circumvented.

The golden rule is to never trust the client. You should figure out a way to deal with this server-side. Lock down these endpoints that could trigger deletes and what-not at the server level so they can't make those changes.

Even if you didn't include a bio section, I could easily just use Developer Tools to inject HTML and new scripts onto the page and send HTTP requests as your pages. If there is nothing to stop me at the server level, that'd cause serious issues.

samanime
  • 25,408
  • 15
  • 90
  • 139
  • Ok, thanks. I'll probably just end up disabling the script tag. Also, using Inspect Element and injecting scripts will only work for the current logged in user, and won't be sent as an admin. – Jacob Gunther Apr 06 '18 at 13:02
0

This is really, really hard.

However, you can almost do it. Here are some of the precautions you need to make (not in order of importance):

  1. Use a separate subdomain for the user profiles. Ensure that all content on these subdomains is completely static; this, coupled with CORS, will help to reduce the immediate risk of XSS.

    The subdomain must be on a separate "branch". You can't have example.com as the page that your users log in to and user.example.com as the page that the user content is kept, because then user.example.com will have access to all of the cookies that example.com has stored (such as authentication cookies). Take a leaf out of GitHub's book, and use a completely separate domain (raw.githubusercontent.com) if you aren't using a www. subdomain everywhere.

  2. Create a JavaScript Sandbox. This 2011 question might help somewhat, but things have changed a lot (e.g. the introduction of XMLHttpRequest). Things are often changing on the web so this sandbox would become leaky very quickly. This is only a measure to stop automated spam bots from putting certain types of malicious JavaScript on your site; it won't actually be effective at stopping targeted attacks (read: attacks).
  3. Ensure that your CORS headers are set up correctly. The Access-Control-Allow-Origin header should never be set to allow your user subdomain; this completely defeats the point and allows the malicious page to interact with the logged-in site. If this happens, you have lost.
  4. Beware of social engineering attacks. These can range from popping up a realistic-looking login prompt to quickly changing a "back" link to point to a phishing site just as the user clicks it. If you let users have this much freedom, they will end up tricking the other users into giving away their passwords. You can't really combat this one.
wizzwizz4
  • 6,140
  • 2
  • 26
  • 62
0

You could make a button that displays the bio in an <iframe>. That way, if the admin visits the site, the bio won't appear/run until he presses the button. Also, this can prevent things like pop-ups, constant reloading, etc...

D. Pardal
  • 6,173
  • 1
  • 17
  • 37