Pressing the enter key receive extra invalid data

Pressing the enter key at the jsp page receive extra invalid data at the ProdController.java.
The alertgroupStr receive “unack” as expected.
However, I do not understand why alertgroupStr receive the extra invalid “null” later.
Debug log:
11:14:52,187 DEBUG com.systems.monitoring.war.ProdController:54 - alertgroupStr unack

11:14:52,187 DEBUG com.systems.monitoring.war.ProdController:54 - alertgroupStr null

ProdController.java:


@Override
public ModelAndView handleRequestInternal(HttpServletRequest request,
   HttpServletResponse response) throws Exception {
  String alertgroupStr = request.getParameter("alertgroup");
  logger.debug("alertgroupStr " + alertgroupStr);

Jsp page:

<?xml version="1.0" encoding="UTF-8" ?>
<&#37;@ include file="/WEB-INF/jsp/includeTaglibs.jsp"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
                      "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<link rel="stylesheet" type="text/css" media="all"
	href="/static/css/style.css" />
<link rel="stylesheet" type="text/css" media="all"
	href="/static/css/tablist.css" />
<script type="text/javascript" src="/static/js/prototype.js"></script>
<script type="text/javascript" src="js/util.js"></script>
<title>Hw Monitoring
<%@page import="org.springframework.beans.*" %>
<%@page import="org.springframework.context.*" %>
<%@page import="org.springframework.web.servlet.support.*" %>
</title>

<style type="text/css"> 
.pageNumber {
float:left;
padding: 3px 0;
margin-left: 0;
margin-bottom: 0;
margin-top: 0.1em;
font: bold 12px Verdana;
}
.pageNumber .noLink{
float:left;
padding: 3px 0.5em;
margin-right: 3px;
margin-top: 3px;
border: 1px solid white;
border-bottom: 1px solid white;
background: white;
}
.pageNumber a{
float:left;
text-decoration: none;
padding: 3px 0.5em;
margin-right: 3px;
margin-top: 3px;
border: 1px solid #778;
border-bottom: 1px solid gray;
background: white;
}
.pageNumber a:hover{
border-color: navy;
background-color: #8dd8f8;
color: #FFF;
}
.rowPerPage {
float:left;
padding: 3px 0;
margin-left: 0;
margin-bottom: 0;
margin-top: 0.1em;
font: bold 12px Verdana;
}
</style> 

</head>

<script type="text/javascript">

  function init()
  {
  }
  
  function isEmpty(v) {
	 return (v == null) || (v.length == 0);
  }

  function isInteger(v) {
     return !isEmpty(v) && !/[^\\d]/.test(v);
  }

  function setalertgroup() {
    var alertgroup = 'all';
    var elem = document.getElementsByName("alertradio");
    for (var i = 0; i < elem.length; i++) {
       if (elem[i].checked) {
            alertgroup = elem[i].value;
       }
    }
alert('alertgroup ' + alertgroup);
    var rowsPerPageElem = document.getElementById("rowsPerPage");
	var rowsPerPage = rowsPerPageElem.value;
alert(' rowsPerPage ' + rowsPerPage);
	if (!isInteger(rowsPerPage)) {
	   alert('Rows per page should be an integer.  It is set to the default value of 20');
	   rowsPerPage = 20;
	}
	var chkelem = document.getElementById("includingUnassignedTags");
	var includingUnassignedTags = chkelem.checked;
alert(' includingUnassignedTags ' + includingUnassignedTags);
  	window.location = "Prod?rowsPerPage=" + rowsPerPage +
            "&includingUnassignedTags=" + includingUnassignedTags  + "&alertgroup=" + alertgroup;
   }  
  
   function setUnassignedTags()
   {
      setalertgroup();
      return false;
   }
  
   function postCheckbox(id, boxid, labelid) {
     var elem = document.getElementById(labelid);
     var checked = document.getElementById(boxid).checked;
     new Ajax.Request("ProdManager", {
        method: "post",
        parameters: {
            id: id,
            boxchecked: checked
        },
        onComplete: function(){}
     });

	 if (checked)
		 elem.style.color = 'green';
	 else
         elem.style.color = 'red';
   }  
  
  function refresh() {
     window.location.reload(true);
  }

  function timedRefresh(timeoutPeriod) {
    setTimeout("refresh();", timeoutPeriod);
  }
</script>

<body onload="init()">

<div id="mainmenu">
<h1><spring:message code="Hw.header"/></h1>
<div id="Logo"><img src="/static/img/Logo.jpg" width="63" height="63" alt=" Sytems"></div>
</div>
  <ul id="tablist">
	<li class="sprite1 active"><a href="/Hw/Prod"><spring:message
		code="menu.alerts"/></a></li>
	<li class="sprite1"><a href="/MonitoringDBWeb/listReaders"><spring:message
		code="menu.locators"/></a></li>
	<li class="sprite1"><a href="/MonitoringDBWeb/listAssets"><spring:message
		code="menu.assets"/></a></li>
	<li class="sprite1"><a href="/MonitoringDBWeb/listCategories"><spring:message
		code="menu.categories"/></a></li>
	<li class="sprite1"><a href="/MonitoringDBWeb/dbadmin"><spring:message
		code="menu.administration"/></a></li>
	<li class="sprite1"><a href="/MonitoringDBWeb/displayReadMe"><spring:message
		code="menu.readme"/></a></li>
  </ul>

<form name="alertform" method="get">
<spring:message code="alert.choice"/>
  <c:choose>
  <c:when test="${alertgroup == 'all'}">
    <input type="radio" name="alertradio" value="all" CHECKED onClick="setalertgroup()" /> <spring:message code="alert.all"/>
    <input type="radio" name="alertradio" value="ack" onClick="setalertgroup()" /> <spring:message code="alert.ack"/>
    <input type="radio" name="alertradio" value="unack" onClick="setalertgroup()" /> <spring:message code="alert.unack"/>
  </c:when>
  <c:when test="${alertgroup == 'ack'}">
    <input type="radio" name="alertradio" value="all" onClick="setalertgroup()" /> <spring:message code="alert.all"/>
    <input type="radio" name="alertradio" value="ack" CHECKED onClick="setalertgroup()" /> <spring:message code="alert.ack"/>
    <input type="radio" name="alertradio" value="unack" onClick="setalertgroup()" /> <spring:message code="alert.unack"/>
  </c:when>
  <c:when test="${alertgroup == 'unack'}">
    <input type="radio" name="alertradio" value="all" onClick="setalertgroup()" /> <spring:message code="alert.all"/>
    <input type="radio" name="alertradio" value="ack" onClick="setalertgroup()" /> <spring:message code="alert.ack"/>
    <input type="radio" name="alertradio" value="unack" CHECKED onClick="setalertgroup()" /> <spring:message code="alert.unack"/>
  </c:when>
  <c:otherwise>
    <input type="radio" name="alertradio" value="all" CHECKED onClick="setalertgroup()" /> <spring:message code="alert.all"/>
    <input type="radio" name="alertradio" value="ack" onClick="setalertgroup()" /> <spring:message code="alert.ack"/>
    <input type="radio" name="alertradio" value="unack" onClick="setalertgroup()" /> <spring:message code="alert.unack"/>
  </c:otherwise>
  </c:choose>

  <c:set var="untagchk" value="" />  
  <c:if test="${includingUnassignedTags}">
    <c:set var="untagchk" value="checked" />
  </c:if>
  &nbsp;&nbsp;&nbsp;&nbsp;
  <input type="checkbox" name="includingUnassignedTags" id="includingUnassignedTags" ${untagchk} onClick="setUnassignedTags()"><spring:message code="alert.unassignedtags"/>
  &nbsp;&nbsp;&nbsp;&nbsp;
  <spring:message code="alert.number"/>${totalalerts}
<c:if test="${numPages > 0}">
    &nbsp;&nbsp;&nbsp;&nbsp;<spring:message code="alert.page"/>${pageNumber} <spring:message code="alert.of"/> ${numPages}
</c:if>
<table class="resizable">
	<thead>
		<tr>
			<th><spring:message code="alert.id"/></th>
			<th><spring:message code="alert.date"/></th>
			<th><spring:message code="alert.time"/></th>
			<th><spring:message code="alert.reader"/></th>
			<th><spring:message code="alert.asset"/></th>
			<th><spring:message code="alert.description"/></th>
			<th><spring:message code="alert.alert"/><br></br>
			    <spring:message code="alert.acknowledgement"/></th>
		</tr>
	</thead>
	<tbody>
		<c:set var="boxindex" value="0" />
		<c:forEach items="${alerts}" var="alert">
			<tr>
				<c:forEach items="${alert}" var="alertvalue" begin="0" end="5"
					step="1">
					<td>${alertvalue}</td>
				</c:forEach>
				<!-- ${alert[0]} : ID -->
				<!-- ${alert[6]} : the checked attribute -->
				<c:set var="spanid" value="span${alert[0]}" />
				
				<c:if test="${alert[6] == 'checked'}">
					<c:set var="format_start" value="<span id='${spanid}' class='fg-green'>" />
				</c:if>
				<c:if test="${alert[6] == 'unchecked'}">
					<c:set var="format_start" value="<span id='${spanid}' class='fg-red'>" />
				</c:if>
				<td><c:set var="boxindex" value="${boxindex+1}" />
				    <c:set var="boxid" value="box${alert[0]}" />
				    <c:out value="${format_start}" escapeXml="false" />
				<input type="checkbox" name="checkboxChoice" id="${boxid}"
					value="${alert[0]}"
					${alert[6]} onClick="postCheckbox(${alert[0]}, '${boxid}', '${spanid}');">
			    	<spring:message code="alert.ack"/>
				</span></td>
			</tr>
		</c:forEach>

	</tbody>
</table>
</form>

  <c:if test="${numPages > 1}">
    <div class="pageNumber">
      <span class="noLink"><spring:message code="alert.page"/> </span>
      <c:forEach begin="1" end="${numPages}" varStatus="status">
        <c:choose>
        <c:when test="${status.index==pageNumber}"><span class="noLink">${status.index}</span></c:when>
        <c:otherwise><a href="Prod?page=${status.index}&alertgroup=${alertgroup}&includingUnassignedTags=${includingUnassignedTags}&rowsPerPage=${rowsPerPage}">${status.index}</a></c:otherwise>
        </c:choose>
      </c:forEach>
    </div>
  </c:if>

<div id="rowPerPageDiv">
<form name="tagform" onsubmit="setUnassignedTags()" method="get">
  <input type="hidden" name="currPage" value="${currPage}"/>
  <spring:message code="alert.rowsperpage"/><input type="text" name="rowsPerPage" id="rowsPerPage" value="${rowsPerPage}" />
  <input type="submit" value="Apply"><br>
</form>
</div>

<hr><center><font size="-1"><spring:message code="Hw.trademark"/></font> <a href="http://www.systems.com/" title="Hw">
<img border="0" src="/static/img/systems.gif" title="Hw"
	alt=" Systems"></a> </center>
</body>
</html>

I’m not sure what you meant by “null” later.

Also have no idea why you’re doing this
<%@page import=“org.springframework.beans." %>
<%@page import="org.springframework.context.
” %>
<%@page import=“org.springframework.web.servlet.support.*” %>

ProdManager.htm (created from ProdManager.jsp) is for http post. Redirect from ProdManager.htm then to Prod.htm is to avoid the double submit problem.
I comment out the code in postCheckbox (no posting to ProdManager.jsp) still has the same invalid null problem.

Prod-servlet.xml:

	<bean id="ProdManagerController" class="com.systems.monitoring.war.ProdManagerController" >
		<property name="cacheSeconds" value="0"/>
        <property name="viewName" value="redirect:Prod"/>

The more I look at this…the more stranger it looks

Your ajax is going to ProdManager.htm then to Prod.htm ? Why? Try testing w/o redirect to prod.htm

I really don’t understand why your AJAX response content needs to jump from one html to another html… very strange… more likely you probably didn’t want static content. About 99.9999% of the time your AJAX is calling a servlet/jsp to the server. Anyways, G’luck.

I didn’t look super close, but are is the button that is being pressed with the enter key inside the form?

If so both the form and the listener on the submit button might be both being triggered. Which would submit the form twice.

You can test this by adding code to your javascript that will add data to the form that is being submitted and then on the server side look to see what data is coming back in both requests.

Also, I see that you’re using AJAX in this matter.

You can combine Spring MVC + Spring Web Flow + Tiles to do your AJAX.
http://www.springbyexample.org/examples/dynamic-tiles-spring-mvc-module.html

If you do this then when JavaScript is disabled then your view will still be valid. This is Spring’s preferred way of doing AJAX.

I had included them in my actual page but not my posted page here (these are boilerplate codes which should not cause my problem):

<%@ page session="false"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ taglib prefix="fmt" uri="http://java.sun.com/jsp/jstl/fmt" %>
<%@ taglib prefix="spring" uri="http://www.springframework.org/tags" %>
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form"%>

I prefer to fix the current bug instead of reimplement the page with some other technology (which may introduce bugs by me anyway).
I use javascript to pass the rowsPerPage, includingUnassignedTags and alertgroup parameters to the server.
The server send the parameters to the database to get new data for display.

Yes, pressing “return” button once and will get 2 log messages.
The ParameterizableViewController class supports only the method handleRequestInternal which returns ModelAndView.

I see. So, I’m assuming you press “return” button once and you’re getting 2 log messages? am I correct? In this case, my programming sense is telling me that you’re using “redirect”. Still, don’t get why you need to do those imports. Also, I’d advise using Model to capture inputs then relying on HttpServletRequest for testing purpose.

postCheckbox() post to
ProdManager.htm which “redirect” to Prod.htm.
Pressing the enter key calls setalertgroup() which deal with Prod.htm which has no “redirect”.

I am sorry but there’s something fundamentally wrong if you’re using “redirect” to avoid the double submit. Actually, I have no idea how that’s even possible. Are we talking about the same “redirect”. So when you redirect, do you get HTTP code 301?

Your code must be very magical. You’re using c taglib, spring taglib… yet you haven’t defined it in your JSP. At the same time, you’re doing unnecessary import for your page. And it works? I’m surprised that you’re actually getting a result of “null”

So, are you using “redirect”?

Yes, the button that is being pressed with the enter key is inside the form, so I moved the button outside the form as follows, but still get the same extra invalid null problem.
My javascript alerts inside setUnassignedTags() are executed only once which are expected.

<div id="rowPerPageDiv">
<form name="tagform" onsubmit="setUnassignedTags()" method="get">
  <input type="hidden" name="currPage" value="${currPage}"/>
  <spring:message code="alert.rowsperpage"/><input type="text" name="rowsPerPage" id="rowsPerPage" value="${rowsPerPage}" />
</form>
  <input type="submit" value="Apply"><br>
</div>

The “null” refers to the debug log output
alertgroupStr null
which is generated from the logger.debug statement in ProdController.java.

The imports are required for using the Spring framework to create the web page.