OWASP / owasp-java-encoder

The OWASP Java Encoder is a Java 1.5+ simple-to-use drop-in high-performance encoder class with no dependencies and little baggage. This project will help Java web developers defend against Cross Site Scripting!

Home Page:https://owasp.org/www-project-java-encoder/

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Backslash inserted when using Encode#forJavaScript to encode a String with a hyphen in it

InfiniteLoop90 opened this issue · comments

When encoding Strings that have hyphens in them using the Encode#forJavaScript method, a backslash is prepended before the hyphen in the output of the encoded String.

For example,

Encode.forJavaScript(String.valueOf(-1));

produces \-1

These causes illegal character errors on resulting HTML and JavaScript files if you try to use the result as a JavaScript Number type.

Encoding values with hyphens in them for all of the other contexts (e.g., forHtml, forCssString, forXml, forCDATA, forJava, etc.) produces the expected values without the backslashes (-1) .

Verified this is how it behaves in all versions of the OWASP Encoder library published to Maven Central (1.1 - 1.2.1).

Sure

For example, on some JSP file we could have something like this:

<%
    Number someNumberValue = (Number)request.getAttribute("someNumberFromRequest");
%>
<script type="text/javascript">
$(document).ready(function() {
    var someJavaScriptNumber = <%= Encode.forJavaScript(String.valueOf(someNumberValue)) %>;
});
</script>

That would be a syntax error.

I see that issue #6 is what you're referring to. Is the assumption that you'd always quote your values and use the JavaScript functions parseInt() and parseFloat() in these scenarios to put Numbers onto the page?

It looks like this is a resolved issue. If you have any more questions either contact us directly or open a new bug. Thanks for using the OWASP Java Encoder and we're always eager to hear other feedback. Aloha!

@jmanico Well, putting quotes around it would mean that I'd be putting it on the page as a JavaScript String and not as a JavaScript Number. My intent was to put it on the page as a number.

For example:

<body>
<%
    Number someNumberValue = Integer.valueOf(-1);
    // In reality this value would have come off of some request attribute but here it's hardcoded for example purposes
%>
    <script type="application/javascript">
        document.addEventListener("DOMContentLoaded", function(event) {
            var someJavaScriptNumber = '<%= Encode.forJavaScript(String.valueOf(someNumberValue)) %>';

            var test1ValueNode = document.getElementById('test1-value');
            var test1TypeNode = document.getElementById('test1-type');
            var test1EqualityTestNode = document.getElementById('test1-equality-test');

            test1ValueNode.textContent = test1ValueNode.textContent.concat(someJavaScriptNumber.toString());
            test1TypeNode.textContent = test1TypeNode.textContent.concat(typeof someJavaScriptNumber);
            test1EqualityTestNode.textContent = test1EqualityTestNode.textContent.concat((-1 === someJavaScriptNumber).toString());
        });
    </script>
    <h1 id="test1-value">The value is </h1>
    <h2 id="test1-type">The type is </h2>
    <h3 id="test1-equality-test">When comparing -1 === someJavaScriptNumber, the returned value is </h3>
</body>

produces the following HTML source (note the escaped hyphen):

<body>

    <script type="application/javascript">
        document.addEventListener("DOMContentLoaded", function(event) {
            var someJavaScriptNumber = '\-1';

            var test1ValueNode = document.getElementById('test1-value');
            var test1TypeNode = document.getElementById('test1-type');
            var test1EqualityTestNode = document.getElementById('test1-equality-test');

            test1ValueNode.textContent = test1ValueNode.textContent.concat(someJavaScriptNumber.toString());
            test1TypeNode.textContent = test1TypeNode.textContent.concat(typeof someJavaScriptNumber);
            test1EqualityTestNode.textContent = test1EqualityTestNode.textContent.concat((-1 === someJavaScriptNumber).toString());
        });
    </script>
    <h1 id="test1-value">The value is </h1>
    <h2 id="test1-type">The type is </h2>
    <h3 id="test1-equality-test">When comparing -1 === someJavaScriptNumber, the returned value is </h3>
</body>

and the output of the page is shown here:
quotednumber

@jeffi Thanks for the explanation! That makes sense.