2014-03-01 47 views
1

我的緊迫問題是如何在JSP Web窗體中最好地處理這個異常,但是我相信下面的代碼也可以提供答案。NumberFormatException - 驗證JSP文件中的表單提交?

我一直在搞一個java項目,我已經實現了一個applet/JFrame和一個通過JSP的web窗體。在最後一堂課(本質上是Java 1)中,當用戶輸入數據時,我通過ActionListener中的try/catch塊處理了異常處理方法,如NumberFormatException

例子:

private ActionListener L_Weight() { 
    return new ActionListener() { 
     @Override 
     public void actionPerformed(ActionEvent ae) { 
      double weight = Person.DEFAULT_WEIGHT; 
      try { 
       weight = Double.parseDouble(ae.getActionCommand()); 
      } 
      catch (NumberFormatException e) { 
       //e.printStackTrace(); 
      } 
      person = new Person(
        person.getGender(), 
        weight, 
        person.getAge(), 
        person.getNumberOfDrinks(), 
        person.getHoursSinceFirstDrink()); 
      view.updatePerson(person); 
     } 

    }; 
} 

儘管這適用於小程序/ JFrame的,它似乎因此不喜歡的try/catch的最佳用法,我不知道如何處理以外的NumberFormatException的做忽略它,它在網頁表單上對我沒有任何幫助。

所以在網絡方面,我發現了處理異常/錯誤的各種想法,但沒有一個看起來像是最好的選擇。我目前的最愛是將onsubmit="return checkForm(this)"添加到我的表單提交中,其中checkForm()是JavaScript代碼,如果提交有效數據,它將返回true。這仍然看起來像一個無關的步驟,但除了聲明變量作爲字符串和解析它們作爲雙打,以便我可以嘗試/ catch錯誤處理在java端,我不知道我可以驗證提交。

所以我實現了checkForm()函數,它的工作,只是想知道,這是在JSP表單驗證一個很好的做法:

<form name="Name Input Form" action="index.jsp" method="POST" onsubmit="return checkForm(this)"> 

<script type="text/javascript"> 
    function checkForm(form) { 
     var result = true; 
     var numbers = /^[0-9|\.]+$/; 
     var checkFields = new Array(
       form.age, 
       form.weight, 
       form.drinks, 
       form.hours); 

     for (i=0; i < checkFields.length; i++) { 
      if (!checkFields[i].value.match(numbers)) { 
       alert(checkFields[i].name + " field must be a number"); 
       checkFields[i].focus(); 
       result = false; 
       break; 
      } 
     } 
     return result; 
    } 

    function optionChange(form) { 
     if (checkForm(form)) { 
      form.submit(); 
     } 

    } 

我也做了性別選擇它調用optionChange下拉功能:

<select name="gender" id="gender" onchange="optionChange(this.form)"> 
    <option value="Male">Male</option> 
    <option value="Female">Female</option> 
</select> 

歡迎你檢查出web appsource


編輯:

發佈這個問題我知道我也有與此相關的另一個問題後,這將是一個糟糕的選擇,以創建Person類更是把性別,體重構造,年齡,飲料和小時數作爲字符串參數,然後將轉換處理爲各自的類型?我可以把錯誤處理放在try/catch塊中,但是我會(正如我所看到的那樣)利用錯誤處理來強制驗證。從這裏我不需要擔心驗證,因爲java代碼會期望字符串,但這看起來像是不必要的重構工作。

回答

0

雖然xp500提供了一些有用的信息,可以使我的HTML代碼更好,但我相信終於在提交表單後驗證用戶輸入,而不必接受所有輸入作爲字符串,然後將它們轉換爲適當的數據類型。

所以我的研究的一部分,導致研究taglets和腳本以及這樣的,據我可以告訴使用JSTL標籤庫是與一個accepted practice

所以說,這裏是我已經改變實現(注意,您可以看到應用程序對HerokuGitHub一個工作版本的源:


首先,我創建了一個名爲FormValidation.java的servlet,源可以看到在GitHub上,但它的要點是,我的表單現在提交給這個servlet,然後參數驗證並解析並作爲響應返回。

FormValidation的Servlet

public class FormValidation extends HttpServlet { 

    @Override 
    public void doGet(HttpServletRequest request,HttpServletResponse response) 
      throws ServletException, IOException { 

     String gender = request.getParameter("gender"); 
     String age_s = request.getParameter("age"); 
     String weight_s = request.getParameter("weight"); 
     String drinks_s = request.getParameter("drinks"); 
     String hours_s = request.getParameter("hours"); 
     String gender_s; 
     int age_i; 
     double weight_d, drinks_d, hours_d; 

     if (gender.toLowerCase().equals("male") || 
       gender.toLowerCase().equals("female")) { 
      gender_s = gender; 
     } 
     else { 
      gender_s = Person.DEFAULT_GENDER; 
     } 

     try { 
      age_i = Integer.parseInt(age_s); 
     } 
     catch (NumberFormatException e) { 
      age_i = Person.DEFAULT_AGE; 
     } 
     try { 
      weight_d = Double.parseDouble(weight_s); 
     } 
     catch (NumberFormatException e) { 
      weight_d = Person.DEFAULT_WEIGHT; 
     } 
     try { 
      drinks_d = Double.parseDouble(drinks_s); 
     } 
     catch (NumberFormatException e) { 
      drinks_d = Person.DEFAULT_DRINKS; 
     } 
     try { 
      hours_d = Double.parseDouble(hours_s); 
     } 
     catch (NumberFormatException e) { 
      hours_d = Person.DEFAULT_HOURS; 
     } 

     request.setAttribute("gender", gender_s); 
     request.setAttribute("age", age_i); 
     request.setAttribute("weight", weight_d); 
     request.setAttribute("drinks", drinks_d); 
     request.setAttribute("hours", hours_d); 
     request.getRequestDispatcher("/index.jsp").forward(request, response); 

    } 


    @Override 
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { 
     doGet(req, resp); 
    } 

} 

接下來這個servlet添加到我的web.xml:

<servlet> 
    <servlet-name>FormValidation</servlet-name> 
    <servlet-class>drunkstuff.view.FormValidation</servlet-class> 
</servlet> 
<servlet-mapping> 
    <servlet-name>ErrorHandler</servlet-name> 
    <url-pattern>/ErrorHandler</url-pattern> 
</servlet-mapping> 
<servlet-mapping> 
    <servlet-name>FormValidation</servlet-name> 
    <url-pattern>/FormValidation</url-pattern> 
</servlet-mapping> 

從那裏我修改index.jsp文件以使用新的屬性,並設置豆的初始默認值:

<jsp:useBean id="WebViewBean" scope="session" class="drunkstuff.view.WebView" /> 
<c:set var="gender" scope="session" value="${WebViewBean.gender}" /> 
<c:set var="age" scope="session" value="${WebViewBean.age}" /> 
<c:set var="weight" scope="session" value="${WebViewBean.weight}" /> 
<c:set var="drinks" scope="session" value="${WebViewBean.drinks}" /> 
<c:set var="hours" scope="session" value="${WebViewBean.hours}" /> 
<jsp:setProperty name="WebViewBean" property="gender" value="${gender}" /> 
<jsp:setProperty name="WebViewBean" property="age" value="${age}" /> 
<jsp:setProperty name="WebViewBean" property="weight" value="${weight}" /> 
<jsp:setProperty name="WebViewBean" property="drinks" value="${drinks}" /> 
<jsp:setProperty name="WebViewBean" property="hours" value="${hours}" /> 

並提交給servlet:

<form name="Name Input Form" action="./FormValidation" method="GET" onsubmit="return checkForm(this)"> 

我敢肯定,我所做的一切已經做過的工作,但我有很多的麻煩找例子,我可以用做我想要的。還有很多使用scriptlet的答案,我不認爲我應該使用它。所以我很想看看如何改進,這樣我可以瞭解更多關於java web項目的知識,但是到目前爲止,我非常開心。我肯定可以對錶單驗證進行一些更改,以便在需要時更改該行爲,並且可能會返回表單,並提供有關我更改值的信息,但主要原因是如果有人在URL中輸入參數字符串,他們將得到驗證。

1

您可以使用JQuery's change函數。因此,您爲每個文本字段添加一個偵聽器,並且每次更改時都可以檢查文本是否爲有效數字(如果不是,則顯示某種紅色內聯消息)。

您也可以爲您的數字字段使用html5輸入類型編號。

+0

非常感謝你,不知道那些。我猜一般的想法是,我應該在HTML端進行驗證而不是java? –

+0

@akevit你應該做的兩個。在客戶端,這樣你就不會重載驗證這些東西的服務器。並在服務器上,以防有人繞過客戶端並直接發送數據到服務器(例如手動GET或POST) – xp500

+0

所以我想我的問題是如何在服務器端做到這一點,而不必將變量類型更改爲字符串?看起來,我可以做錯誤檢查的唯一方法是將預期的輸入類型更改爲字符串,然後使用大量的投射來使其工作。我對使用JSP非常陌生,Bean對變量使用默認的get/set方法。 –