在业务中,可能因为表单内容过于庞大,字段过于繁杂,如果人为去拼接的话 ,需要耗费大量的时间和精力,与此同时,代码看上去也是冗余不堪。
所以,提交表单的时候如果能整个表单数据整体提交,那是非常开心的事情。
同时,有时候会有需求在前台提交给后台数据之后,希望后台能在处理之后返回数据给前台,可能是标识也好,可能是具体的数据也罢。
这时候又需要使用ajax去提交数据。【因为使用jQuery的submit()方法是没有回调函数的,那个函数只是当表单发生提交时,要同时执行的函数而已,例如:$("#poFromId").submit()】
那能不能使用ajax进行局部页面刷新的同时将整个表单的数据提交呢?
答案肯定是可以的,
首先,咱们把整个的一圈代码给出来:
1.jsp页面
1 <form action="../department/addPosition.htmls" method="post" role="form" id="poFromId" > 2 <div class="form-group"> 3 <label class="col-md-3 control-label">职位名称</label> 4 <div class="col-md-9" style="width: 77%"> 5 <input type="hidden" name="positionId" /> 6 <input type="hidden" name="positionCre" /> 7 <input type="text" class="form-control" name="positionName" placeholder="eq:软件开发工程师" data-bv-trigger="keyup" /> 8 </div> 9 </div> 10 <div class="form-group"> 11 <label class="col-lg-3 control-label">职位所属等级</label> 12 <select class="selectpicker input input-big" name="positionGrade"> 13 <option value="专员">专员</option> 14 <option value="经理">经理</option> 15 <option value="总监">总监</option> 16 </select> 17 </div> 18 <hr/> 19 <div class="form-group center"> 20 <button type="button" class="btn btn-success positionUp">提交职务</button> 21 22 <button type="reset" class="btn btn-warning">重置页面</button> 23 </div> 24 </form>
2.js 表单整体使用ajax提交部分
1 /** 2 * 提交职位 3 */ 4 $(".positionUp").click(function(){ 5 $("input[name='positionId']").val(UUID()); 6 $("input[name='positionCre']").val(parent.departmentId); 7 var position = $("#poFromId").serialize(); 8 9 $.getJSON("../department/addPosition.htmls?"+position,function(data){ 10 if(data){ 11 layer.msg('添加成功', { 12 icon: 1, 13 time: 2000 14 }, function(){ 15 }); 16 parent.layer.close(parent.positionAdd); 17 } 18 }); 19 20 });
3.controller后台接收部分
1 @RequestMapping("addPosition") 2 @ResponseBody 3 public boolean addPosition(Position position){ 4 position.setCreateDate(new Timestamp(System.currentTimeMillis())); 5 position.setUpdateDate(new Timestamp(System.currentTimeMillis())); 6 //操作人 未插入 7 positionService.save(position); 8 9 return true; 10 }
4.上面表单中name对应的实体Position
1 package com.agen.entity; 2 3 import java.sql.Timestamp; 4 import java.util.HashSet; 5 import java.util.Set; 6 7 import javax.persistence.CascadeType; 8 import javax.persistence.Column; 9 import javax.persistence.Entity; 10 import javax.persistence.FetchType; 11 import javax.persistence.GeneratedValue; 12 import javax.persistence.Id; 13 import javax.persistence.OneToMany; 14 import javax.persistence.Table; 15 16 import org.hibernate.annotations.GenericGenerator; 17 18 import com.fasterxml.jackson.annotation.JsonIgnoreProperties; 19 20 /** 21 * Position 岗位表 22 */ 23 @Entity 24 @Table(name = "position", catalog = "performance") 25 @JsonIgnoreProperties(value = {"positionchanges"}) 26 public class Position implements java.io.Serializable { 27 28 // Fields 29 30 private String positionId; 31 private String positionName; //岗位名称 32 private String positionGrade; //岗位对应等级 33 private Timestamp createDate; 34 private Timestamp updateDate; 35 private String operation; 36 private String positionCre; //岗位所属部门 37 private Set<Positionchange> positionchanges = new HashSet<Positionchange>(0); 38 39 // Constructors 40 41 /** default constructor */ 42 public Position() { 43 } 44 45 /** full constructor */ 46 public Position(String positionName, String positionGrade, 47 Timestamp createDate, Timestamp updateDate, String operation, 48 String positionCre, Set<Positionchange> positionchanges) { 49 this.positionName = positionName; 50 this.positionGrade = positionGrade; 51 this.createDate = createDate; 52 this.updateDate = updateDate; 53 this.operation = operation; 54 this.positionCre = positionCre; 55 this.positionchanges = positionchanges; 56 } 57 58 // Property accessors 59 //@GenericGenerator(name = "generator", strategy = "uuid.hex") 60 @Id 61 //@GeneratedValue(generator = "generator") 62 @Column(name = "positionID", unique = true, nullable = false, length = 36) 63 public String getPositionId() { 64 return this.positionId; 65 } 66 67 public void setPositionId(String positionId) { 68 this.positionId = positionId; 69 } 70 71 @Column(name = "positionName", length = 30) 72 public String getPositionName() { 73 return this.positionName; 74 } 75 76 public void setPositionName(String positionName) { 77 this.positionName = positionName; 78 } 79 80 @Column(name = "positionGrade", length = 20) 81 public String getPositionGrade() { 82 return this.positionGrade; 83 } 84 85 public void setPositionGrade(String positionGrade) { 86 this.positionGrade = positionGrade; 87 } 88 89 @Column(name = "createDate", length = 0) 90 public Timestamp getCreateDate() { 91 return this.createDate; 92 } 93 94 public void setCreateDate(Timestamp createDate) { 95 this.createDate = createDate; 96 } 97 98 @Column(name = "updateDate", length = 0) 99 public Timestamp getUpdateDate() { 100 return this.updateDate; 101 } 102 103 public void setUpdateDate(Timestamp updateDate) { 104 this.updateDate = updateDate; 105 } 106 107 @Column(name = "operation", length = 36) 108 public String getOperation() { 109 return this.operation; 110 } 111 112 public void setOperation(String operation) { 113 this.operation = operation; 114 } 115 116 @Column(name = "positionCre", length = 500) 117 public String getPositionCre() { 118 return this.positionCre; 119 } 120 121 public void setPositionCre(String positionCre) { 122 this.positionCre = positionCre; 123 } 124 125 @OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, mappedBy = "position") 126 public Set<Positionchange> getPositionchanges() { 127 return this.positionchanges; 128 } 129 130 public void setPositionchanges(Set<Positionchange> positionchanges) { 131 this.positionchanges = positionchanges; 132 } 133 134 }
接下来,咱们要细细谈一谈这上面需要注意的小细节:
1.首先,如果你想使用js控制提交整个表单,那最起码的,页面中不能存在元素的name=submit的,当然最下面的提交按钮也不能使用type=submit了,因为你想在js中处理之后再去使用js提交表单数据嘛!!
2.其次,js中,获取整体的表单数据,使用了var position = $("#poFromId").serialize();序列化的方法去获取整个表单的数据!!
3.再者说,既然你讲前后台表单数据传输交给spring去管理了,那最起码的要求,你得在form表单中将实体中规定不能为null的字段值都给上,同样的,如果你想前台传递给后台,后台直接拿到的就是一个字段都比较完整的实体对象,那表单中的name就要尽量多的和实体中的字段值保持一致;
4.对于第3点中,可能会出现,实体中的某个属性也是个实体,例如:【注册的时候,User实体需要选择是哪个部门的,而Department实体在注册页面上,也就是个下拉框,也就是个departmentId而已,对于这种情况,我们可以将name设置为其他的,在后台单独接收这个name对应的值,然后将departmentId实例化成Department对象,再赋值给User实体】
5.注意ajax中,data部分是:$.getJSON("../department/addPosition.htmls?"+position,拼接的,而不是$.getJSON("../department/addPosition.htmls",{position:position},给出的。这就需要试验一下,两种方式最后请求的地址是什么样子的;
6.Controller中,这里需要返回数据给前台,才使用了@ResponseBody这个注解;而就算你返回是void的,不希望给前台返回值,也需要@ResponseBody。不然,spring会认为你要去找那一串地址,会无休止的找下去,就会报错。
这里接着说:
上面那个表单,数据量很小,如果提交的是个大表单,那么就不能采用上面这种ajax的写法了,而是:
1 var xmlDocument = [create xml document]; 2 $.ajax({ 3 url: "page.php", 4 processData: false, 5 data: xmlDocument, 6 success: handleResponse 7 });
使用jQuery中最原始的ajax的写法,这样就可以保证大量的数据传递给后台了。