views:

1838

answers:

5

Hi,

I have a user form. If the user types in a string with ' or " as part of it I have no problem. The form is submitted and saved correctly to the DB. My problem is when I reload the page (all entries can be modified and are loaded into a list in the jsp before being displayed). On loading the page I get an error saying:

missing ) after argument list 'Caroline's message', \n

Any ideas what I need to do to escape this string for displaying it on the frontend.

Here is the code I am using on th frontend to read in the data and store it in a javascript object. Not fully sure where I need to escape. The field causing the problem is c.getComName:

communications[<%=i%>][1] = new CommObject('<%=c.getComId()%>', '<%=c.getComName()%>');

UPDATED WITH HTML GENERATED:

communications[0][1] = new CommObject('101', 'Caroline's Message');

Thanks in advance

A: 
OscarRyz
I'll try but I suspect it will then work for ' but not for "
Caroline
it actually doesn't fix it which is a surprise to me!
Caroline
:-o I guess you'll need to preprocess the name before delivering it back to the front end. :(
OscarRyz
A: 

When you return the HTML from the CommObject class add in the \" instead of the ' and before the name (e.g. Caroline's message)

Like this: return "\"" + comName + "\"";

amischiefr
I'll try this now, thanks
Caroline
Still no joy, I get missing ) after argument list '"Caroline's message"', \n. Just to confirm I need to escape both ' and "
Caroline
No, just escape the ", and leave out the single quote
amischiefr
+2  A: 

Use the Apache StringEscapeUtils.escapeJavaScript function.

Escapes the characters in a String using JavaScript String rules.

Escapes any values it finds into their JavaScript String form.
Deals correctly with quotes and control-chars (tab, backslash, cr, ff, etc.)

So a tab becomes the characters '\\' and 't'.
Kevin Hakanson
Thanks Kevin, this works perfectly!
Caroline
+2  A: 

I know this is an old, answered question but I wanted to add a bit on how I handle this. I prefer to avoid scriptlets in the middle of my page, and was having to use them (increasingly often) to escape strings when used in JS code. What I wanted was an EL way of escaping the strings. I created a very small custom taglib that I use for just this purpose:

Utilities.java:

package com.mycom.taglibs;

import org.apache.commons.lang.StringEscapeUtils;

public class Utilities {
    public static String escapeJS(String value) {
        return StringEscapeUtils.escapeJavaScript(value);
    }
}

mytaglib.tld:

<?xml version="1.0" encoding="UTF-8" ?>
<taglib xmlns="http://java.sun.com/xml/ns/j2ee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-jsptaglibrary_2_0.xsd"
version="2.0">

  <description>My Tag Library</description>
  <display-name>Tag Utils</display-name>
  <tlib-version>1.1</tlib-version>
  <short-name>myt</short-name>

  <function>
    <description>
        JavaScript Escape function
    </description>
    <name>escapeJS</name>
    <function-class>com.mycom.taglibs.Utilities</function-class>
    <function-signature>java.lang.String escapeJS(java.lang.String)</function-signature>
  </function>
</taglib>

And, in the JSP page:

<%@ taglib prefix="myt" uri="/WEB-INF/mytaglib.tld" %>
The escaped string is: ${myt:escapeJS(variableHoldingTheString)}

My apologies if there's a typo in there somewhere... I switched up some names to remove some things.

RHSeeger
A: 

Just use JSTL <c:out> tag to escape HTML entities. Here's a basic example, assuming that you're inside a loop and that ${communications} refers a List<Communication> in the back end:

<script type="text/javascript">
    var communications = [];
    <c:forEach items="${communications}" var="c" varStatus="loop">
        communications[<c:out value="${loop.index}" />] = [];
        communications[<c:out value="${loop.index}" />][1] = 
            new CommObject('<c:out value="${c.comId}" />', '<c:out value="${c.comName}" />');
    </c:forEach>
</script>

Also use <c:out> everywhere in your template pages where you're about to display user-controlled input. This will also prevent your webapp from Cross Site Scripting (XSS).

That said, do not use scriptlets in JSP. Use taglibs to control template flow and output and use EL to access back end data. Keep Java code in Java classes. A Servlet is intented to be used for that.

BalusC