文件上傳中form表單的enctype="multipart/form-data" 爲二進制文件傳輸
在struts2中 表單取值比較簡單 因爲框架已經幫我們做好的表單域的取值
但是在非框架中 取值就相對麻煩了 不能通過request.getParameter(name) 去取值
不過我們可以使用相關的jar去實現文件的上傳和下載 比如 DiskFileUpload
前段時間 在做文件上傳的時候 需要傳遞一個複選框的值 以及 相同名字的幾個textarea的值
在非上傳中 我們可以通過request.getParameterValues(name)方法 把需要的值變爲一個字符串數組
但是DiskFileUpload中沒有相關的方法 通過參考項目中以前的方法 再加以修改 實現了相關功能
boolean success = false;
Map pMap = new LinkedHashMap();//form Field map
request.setCharacterEncoding("GBK");
try {
//通過FileUpload組建封裝表單值到map對象中
DiskFileUpload fu = new DiskFileUpload();
fu.setSizeMax(30 * 1024 * 1024);// 設置最大文件尺寸,這裏是14MB
fu.setSizeThreshold(1024 * 64);// 設置緩衝區大小,這裏是64kb
List fileItems = fu.parseRequest(request);// 得到所有的field
Iterator itor = fileItems.iterator();
// 依次處理每一個field
while (itor.hasNext()) {
FileItem fi = (FileItem) itor.next();
if (fi.isFormField()){//表單處理
if(pMap.get(fi.getFieldName())!=null){
pMap.put(fi.getFieldName(),pMap.get(fi.getFieldName())+"$"+org.apache.commons.lang.StringEscapeUtils.escapeSql(fi.getString("GBK")));
}else{
pMap.put(fi.getFieldName(),org.apache.commons.lang.StringEscapeUtils.escapeSql(fi.getString("GBK")));
}
} else {//附件處理
if (fi.getName() != null) {
if (fi.getName().indexOf(".") != -1) {//有擴展名的指定類型文件
pMap.put(fi.getFieldName(), fi);
}
}
}
}
通過DiskFileUpload中的fu.parseRequest(request)方法 把request中的表單屬性 轉化爲List對象
然後遍歷fileItems 把對應表單的值放在map對象中 判斷map是否存在某個key 存在就拼接value
if(pMap.get(fi.getFieldName())!=null){
pMap.put(fi.getFieldName(),pMap.get(fi.getFieldName())+"$"+org.apache.commons.lang.StringEscapeUtils.escapeSql(fi.getString("GBK")));
}else{
pMap.put(fi.getFieldName(),org.apache.commons.lang.StringEscapeUtils.escapeSql(fi.getString("GBK")));
}
這樣我們就實現了表單中相同name的標籤的取值問題
接下來就是取值 封裝在實體類中
int exam_year = Integer.parseInt(pMap.get("exam_year").toString());
String name = pMap.get("exam_year").toString();
按照正常的思路我們需要這樣進行取值 假如表單的屬性就幾個還好 假如很多呢?
而且表單中有的屬性可以爲空 在取值封裝到實體類中時候 如果map的取值爲空 就會報錯
因此還要對map對象進行判斷
if(pMap.get("q_paper_type")!=null){
q_paper_type =Integer.parseInt(pMap.get("q_paper_type").toString());
}
非常的麻煩
參考以前的項目 發現apache commons 的一個jar commons-beanutils-1.7.0.jar
使用BeanUtils輕鬆實現實體類對象的封裝
引用<%@ page import="org.apache.commons.beanutils.BeanUtils" %>
question 是我們的實體類對象
BeanUtils.populate(question, pMap);
就是這麼簡單 而且會初始化對應的字段 map中某些屬性爲空時 也不會報錯
附上文件的操作:
//附件上傳
if(pMap.get("file")!=null){
FileItem fi = (FileItem) pMap.get("file");
String attachExtName = org.apache.commons.lang.StringUtils.lowerCase(fi.getName().substring(fi.getName().lastIndexOf(".")));
if (!".zip".equals(attachExtName)) {
out.print("<script>alert('文件類型錯誤,請上傳zip格式文件!');history.go(-1);</script>");
return; //解壓縮,格式錯誤,非zip文件
}
if(fi.getSize()>3*1024*1024){
out.print("<script>alert('zip文件不能超過3M!');window.close();</script>");
return; //解壓縮,格式錯誤,非zip文件
}
question.setBodyPackage(fi.getInputStream());
}
-------------------------------------------------------
下面是一個公用方法 任何實體類都可以複製這段代碼
public static void paramPrepare(Object q, HttpServletRequest request) throws Exception {
// request 變量和附件處理,生成q對象
Map pMap = new HashMap();// form Field map
Enumeration enu = request.getParameterNames();
while (enu.hasMoreElements()) {
Object key = enu.nextElement();
pMap.put(key, ParamUtils.getParameter(request, (String) key));
}
BeanUtils.copyProperties(q, pMap);
}
User u = new User();
User.paramPrepare(user,request);
把request的信息封裝到實體對象裏面