Liferay XSS filters

Applications are vulnerable to Java script injections. In this tutorial, we will see possible ways to restrict the JS injections in input fields.

There are two ways to protect from JS injections

 Use Escape HTML to prevent JS execution

  • In this approach, applications will entering Java script, but white displaying JS execution can be prevented.
  • In controller classs, use  HtmlUtil.escape(html), or escapeJS to convert into Unicode format.
    •     String value = ParamUtil.getString(actionRequest,”data”);
    •     String escapedValue =  HtmlUtil.escape(value )
  • Use <%= HtmlUtil.escape(value)%> on JSP’s also to prevent JS execution

Restrict JS injection in input fields

  • Create XSSFitler class that will be executed for each action/render request. As shown below create XSSFilter.java class and take every paramter in the action request.
  • Now map filter in portlet.xml file for portlet and menion life cycle as ACTION_PHASE to execute filter for action request only
    • <filter>
      <filter-name>XSSFilter</filter-name>
      <filter-class>com.filter.XSSFilter</filter-class>
      <lifecycle>ACTION_PHASE</lifecycle>
      </filter>
      <filter-mapping>
      <filter-name>XSSFilter</filter-name>
      <portlet-name>test-portlet</portlet-name>
      </filter-mapping>
  • Add error message in via SessionErrors class
  • Display the error message on JSP using liferay-ui:error tag

XSS Java code

import java.io.IOException;
import java.util.Enumeration;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
 import javax.portlet.ActionRequest;
import javax.portlet.ActionResponse;
import javax.portlet.PortletException;
import javax.portlet.filter.ActionFilter;
import javax.portlet.filter.FilterChain;
import javax.portlet.filter.FilterConfig;
import com.liferay.portal.kernel.servlet.SessionErrors;
import com.liferay.portal.kernel.upload.UploadPortletRequest;
import com.liferay.portal.kernel.util.ParamUtil;
import com.liferay.portal.util.PortalUtil;

 public class XSSFilter implements ActionFilter {

                 @Override
                public void destroy() {
                }
                @Override
               public void init(FilterConfig arg0) throws PortletException {
                }

                @Override
                public void doFilter(ActionRequest actionRequest,
                                                ActionResponse actionResponse, FilterChain filterChain)
                                                throws IOException, PortletException {

                                boolean foundXSS = false;
                                UploadPortletRequest ur = PortalUtil.getUploadPortletRequest(actionRequest);
                                Enumeration<String> params = ur.getParameterNames();
                                while (params.hasMoreElements()) {
                                              String param = params.nextElement();
                                               String value = ur.getParameter(param);;
                                                if(foundXSS){
                                                      break;
                                                }
                                                foundXSS = containsJS(value);
                                     }

                                if (!foundXSS) {
                                               filterChain.doFilter(actionRequest, actionResponse);
                                } else {
                                         System.out.println("Action Request is more prone to XSS attack");
                                         SessionErrors.add(actionRequest, "xss.error");
                                }
                 }

                 public boolean containsJS(String value){
                                boolean foundXSS = false;
                                if(value == null || value.isEmpty()){
                                                return false;
                                }
                              Pattern scriptPattern = Pattern.compile("<script>(.*?)</script>", Pattern.CASE_INSENSITIVE);
                                Matcher scriptMat = scriptPattern.matcher(value);
                                if (scriptMat.find()) {
                                          foundXSS = true;
                                }
                        scriptPattern = Pattern.compile("<script>",Pattern.CASE_INSENSITIVE);
                        scriptMat = scriptPattern.matcher(value);
                                if (scriptMat.find()) {
                                     foundXSS = true;
                                }
                               scriptPattern = Pattern.compile("javascript:",Pattern.CASE_INSENSITIVE);
                                scriptMat = scriptPattern.matcher(value);
                                if (scriptMat.find()) {
                                               foundXSS = true;
                                }
                                scriptPattern = Pattern.compile("javascript",Pattern.CASE_INSENSITIVE);
                                scriptMat = scriptPattern.matcher(value);
                                if (scriptMat.find()) {
                                               foundXSS = true;
                                }
                                return foundXSS;
                }

}
  1. You can use above code

Leave a Comment

Your email address will not be published. Required fields are marked *