How does spring3mvc bind the checkbox value to the int Data Type of the model object?

Source: Internet
Author: User
[Java]View plaincopy

  1. Model object: User. Java:

[Java]View plaincopy

  1. Public class user {
  2. Private int ID;
  3. Private string name;
  4. // 0: male, 1: female, displayed as radiobutton
  5. Private int gender;
  6. Private int age;
  7. // 0: not graduated; 1: Graduated; displayed as checkbox on the page
  8. Private int graduted;
  9. // 0: Not married; 1: Married; displayed as checkbox on the page
  10. Private int married;
  11. }

Form:
<Form: Form ID = "user" modelattribute = "user" Action = "Save. Do">
<Table>
<Tr> <TD> User name: </TD> <form: Input Path = "name"/> </TD> </tr>
<Tr> <TD> Gender: </TD> <TD> male: <form: radiobutton Path = "gender" value = "0"/>
Female: <form: radiobutton Path = "gender" value = "1"/> </TD>
</Tr>
<Tr> <TD> Age: </TD> <form: Input Path = "Age"/> </TD> </tr>
<! -- Attribute 'value' is required when binding to non-boolean values -->
<Tr> <TD> others: </TD> <TD> graduation: <form: checkbox Path = "graduted" value = "1"/> Marital status: <form: checkbox Path = "married" value = "1"/> </TD>
</Tr>
<Tr> <TD colspan = "2"> <input type = "Submit" value = "Submit"> </TD> </tr>
</Table>
</Form: Form>

[Java]View plaincopy

  1. Usercontroller:
  2. @ Controller
  3. @ Requestmapping ("/user ")
  4. Public class usercontroller {
  5. Private Static class inteditor extends customnumbereditor {
  6. Public inteditor (){
  7. Super (integer. Class, true );
  8. }
  9. Public void setastext (string text) throws illegalargumentexception {
  10. If (text = NULL | text. Trim (). Equals ("")){
  11. // Treat empty string as null value.
  12. Setvalue (0 );
  13. } Else {
  14. // Use default valueof methods for parsing text.
  15. Setvalue (integer. parseint (text ));
  16. }
  17. }
  18. }
  19. @ Initbinder
  20. Public void initbinder (webdatabinder binder ){
  21. Binder. registercustomeditor (Int. Class, null, new inteditor ());
  22. }
  23. @ Requestmapping (value = "/Add ")
  24. Public modelandview add (httpservletrequest request ){
  25. Modelandview MAV = new modelandview ("useradd ");
  26. // Neither bindingresult nor plain target object for bean name 'user' available as request attribute
  27. Mav. addobject ("user", new user ());
  28. Return MAV;
  29. }
  30. @ Requestmapping (value = "/Save ")
  31. Public modelandview save (httpservletrequest request,
  32. @ Modelattribute ("user") User user ){
  33. Modelandview MAV = new modelandview ("Redirect: list. Do ");
  34. System. Out. println (User );
  35. Return MAV;
  36. }
  37. }

Enter http: // localhost: 8080/sp3form/user/Add in the browser. do, the input page will pop up. If neither of the two checkboxes is selected, an error will be reported during submission:

Org. springframework. Web. util. nestedservletexception: Request Processing failed; Nested exception is org. springframework. validation. bindexception: org. springframework. validation. beanpropertybindingresult: 2 errors
Field error in object 'user' on field 'graduted': rejected value [null]; codes [typemismatch. user. graduted, typemismatch. graduted, typemismatch.int, typemismatch]; arguments [Org. springframework. context. support. defaultmessagesourceresolvable: codes [user. graduted, graduted]; arguments []; default message [graduted]; default Message [failed to convert property value of Type 'null' to required type 'int' for property 'gradted'; Nested exception is Java. lang. illegalargumentexception: cannot convert value of Type [null] to required type [int] for property 'graduted': propertyeditor [Org. springframework. beans. propertyeditors. customnumbereditor] returned inappropriate value]
Field error in object 'user' on field 'married': rejected value [null]; codes [typemismatch. user. married, typemismatch. married, typemismatch.int, typemismatch]; arguments [Org. springframework. context. support. defaultmessagesourceresolvable: codes [user. married, married]; arguments []; default message [married]; default Message [failed to convert property value of Type 'null' to required type 'int' for property 'married'; Nested exception is Java. lang. illegalargumentexception: cannot convert value of Type [null] to required type [int] for property 'married': propertyeditor [Org. springframework. beans. propertyeditors. customnumbereditor] returned inappropriate value]
Org. springframework. Web. servlet. frameworkservlet. processrequest (frameworkservlet. Java: 863)

Specifically, null cannot be converted to int.

 

Then, there are basically two solutions for accessing Google over the Internet:
(1) Use integer instead of Int. null cannot be converted to int, but can be converted to integer. Although there is no problem with this conversion, if you want to insert the model object to the database, you have to change null to 0, which is troublesome!
(2) Add an initbinder and rewrite the setastext () method. As in the code above, an error is still returned! At first, it was suspected that the setastext method was not called, but the debug found that there were two values that actually called setastext, but the checkbox was not called. That is to say, an error has occurred before setastext!

Everyone copied me to copy you. None of them can solve the problem. The so-called wall-down, running by everyone, was originally intended to be a little lazy, but you have to rely on yourself in the key!

Then, start debugging to see how the source code is handled. The first solution was to override the getemptyvalue method in webdatabinder:

[Java]View plaincopy

  1. Protected object getemptyvalue (string field, class fieldtype ){
  2. If (fieldtype! = NULL & Boolean. Class. Equals (fieldtype) | Boolean. Class. Equals (fieldtype )){
  3. // Special handling of boolean property.
  4. Return Boolean. False;
  5. }
  6. Else if (fieldtype! = NULL & fieldtype. isarray ()){
  7. // Special handling of array property.
  8. Return array. newinstance (fieldtype. getcomponenttype (), 0 );
  9. } Else if (fieldtype = int. Class | fieldtype = long. Class ){
  10. Return 0;
  11. }
  12. Else {
  13. // Default value: Try null.
  14. Return NULL;
  15. }
  16. }

 

In this way, the problem is solved from the source, but it seems unsatisfactory to modify the source code of spring.

Continue Debug:
Typeconverterdelegate:

[Java]View plaincopy

  1. /**
  2. * Convert the given text value using the given property editor.
  3. * @ Param oldvalue the previous value, if available (may be <code> null </code>)
  4. * @ Param newtextvalue the proposed text value
  5. * @ Param editor the propertyeditor to use
  6. * @ Return the converted value
  7. */
  8. Protected object doconverttextvalue (Object oldvalue, string newtextvalue, propertyeditor Editor ){
  9. Try {
  10. Editor. setvalue (oldvalue );
  11. }
  12. Catch (exception ex ){
  13. If (logger. isdebugenabled ()){
  14. Logger. debug ("propertyeditor [" + editor. getclass (). getname () + "] does not support setvalue call", ex );
  15. }
  16. // Swallow and proceed.
  17. }
  18. Editor. setastext (newtextvalue );
  19. Return editor. getvalue ();
  20. }

It is found that spring first calls the setvalue of the custom editor and then calls setastext. Therefore:

[Java]View plaincopy

  1. Public void setastext (string text) throws illegalargumentexception {
  2. If (text = NULL | text. Trim (). Equals ("")){
  3. // Treat empty string as null value.
  4. Setvalue (0 );
  5. } Else {
  6. // Use default valueof methods for parsing text.
  7. Setvalue (integer. parseint (text ));
  8. }
  9. }

This method does not work at all!
Now that we have found the cause, we have found a solution. We need to rewrite setvalue instead of setastext:

[Java]View plaincopy

  1. Private Static class inteditor extends customnumbereditor {
  2. Public inteditor (){
  3. Super (integer. Class, true );
  4. }
  5. @ Override
  6. Public void setvalue (object Value ){
  7. If (value = NULL ){
  8. Super. setvalue (0 );
  9. } Else {
  10. Super. setvalue (value );
  11. }
  12. }
  13. }
  14. @ Initbinder
  15. Public void initbinder (webdatabinder binder ){
  16. Binder. registercustomeditor (Int. class, "graduted", new inteditor ());
  17. Binder. registercustomeditor (Int. class, "married", new inteditor ());
  18. }

 

The world has been cleaned up!

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.