要解決的問題:javascript
viewMessage: function (messageId) { console.info('viewMessage'); // 經過 id 獲取完整數據對象 var message = $.grep($messageDatagrid.datagrid('getRows'), function (n, i) { return n.messageId == messageId })[0]; console.info(message); // 若是該條記錄是「未讀」則更新爲「已讀」 if (message.isReaded == YesOrNoEnum.No) { var updateReadState = { isReaded: YesOrNoEnum.Yes, messageIds: [messageId] }; $.ajax({ data: JSON.stringify(updateReadState), url: UrlEnum.UpdateReadState, type: "POST", dataType: "json", contentType: 'application/json;charset=utf-8', //「參數爲泛型集合 @RequestBody List<> 時」需設置請求頭信息 success: function (result) { console.info('updateReadState success,返回數據以下:↓'); console.info(result); if (result.success) { $.messager.show({ title: '提示', // 頭部面板上顯示的標題文本。 msg: result.message }); $messageDatagrid.datagrid('load'); // 確保沒有任何緩存痕跡(必不可少) $messageDatagrid.datagrid('clearChecked'); $messageDatagrid.datagrid('clearSelections'); } else { if (result.operationType == operationTypeEnum.CookieTimeout) { result.message = decodeURIComponent(result.message); } $.messager.alert('提示', result.message, 'warning'); } }, error: function (result) { } }); // end ajax } // isReaded = no }
在傳遞複雜類型的數據時,注意 Ajax 方法的 data 和 contentType 兩個參數的設置。在 data 屬性中用到了 JSON.stringify(),目的是將 data 屬性轉化爲「JSON字符文本」形式,也是防止 jQuery 內部把 data 屬性轉化成了「查詢字符串」格式(key1=valu1&key2=value2),假若如此 SpringMVC 就很差識別解析了。java
public class BaseMessageUpdateReadState extends BaseEntity { private List<Integer> messageIds; private Integer isReaded; public List<Integer> getMessageIds() { return messageIds; } public void setMessageIds(List<Integer> messageIds) { this.messageIds = messageIds; } public Integer getIsReaded() { return isReaded; } public void setIsReaded(Integer isReaded) { this.isReaded = isReaded; } }
該實體類就是一個複雜形式的實體類,把實體類 BaseMessageUpdateReadState 的字段與客戶端的 JSON 對象 updateReadState 做比較,可見兩者是如此一致,需注意一下的是 js 中的數組與 Java 中的泛型集合 List
@RequestMapping(value = "/UpdateReadState", method = RequestMethod.POST) @ResponseBody public TransactionResult UpdateReadState(@RequestBody BaseMessageUpdateReadState baseMessageUpdateReadState, @CookieValue(value = "base_cookieKey", required = false) CookieObject cookieObject) { baseMessageUpdateReadState.setCookieObject(cookieObject); TransactionResult result = null; try { result = iBaseMessageService.UpdateReadState(baseMessageUpdateReadState); return result; } catch (RuntimeException e) { result = new TransactionResult(false); if (e.getMessage() == null) { ByteArrayOutputStream buf = new java.io.ByteArrayOutputStream(); e.printStackTrace(new java.io.PrintWriter(buf, true)); String expMessage = buf.toString(); try { buf.close(); } catch (IOException e1) { e1.printStackTrace(); } result.setMessage(expMessage); } else { result.setMessage(e.getMessage()); } return result; } }
在控制器方法中,參數 BaseMessageUpdateReadState 前面必須帶上 @RequestBody,它負責將 JSON 格式的複雜參數轉化爲 Java 實體類,很是的方便。json
接口:數組
int affectedRows = iBaseMessageDao.UpdateReadState(baseMessageUpdateReadState);
XML映射器:緩存
<!-- 批量更新閱讀狀態 --> <update id="UpdateReadState" parameterType="baseMessageUpdateReadState" timeout="20" flushCache="true"> Update BaseMessage Set IsReaded = #{isReaded} Where 1=1 and MessageId in <foreach collection="messageIds" index="index" item="item" open="(" close=")" separator=","> #{item} </foreach> </update>
着重看看 #{isReaded} 和 collection="messageIds",這裏也是跟 Java 實體類逐個對應,十分趁心。
值得一說的是
foreach 元素的屬性主要有 item、index、collection、open、separator、close。mybatis
其中在指定「collection」屬性時比較容易出錯:app