36、上傳檔案
學習目標:
1、掌握檔案上傳的方法
2、為什麼要學習Java語言
學習過程:
這節課講解一些如何上傳檔案,這裡我們為使用者表新增一個頭像屬性
一、修改資料庫表
首先我們要儲存使用者上傳檔案的資訊,所有要修改資料庫,但是我們不是使用資料庫儲存檔案的,檔案儲存在web伺服器的目錄下,資料庫只是儲存檔案的路徑就可以了,所以我們在tb_user表中新增一個新的屬性header,使用varchar格式就可以了,同時修改UserDao的程式碼,這些程式碼比較簡單,這裡就不列出來了。
二、修改頁面
這裡我們可以使用html的input控制元件,type型別為file就可以了,同時表單的method方法必須是post,還需要修改enctype屬性值為:"multipart/form-data"。
<form action="admin/userServlet?op=add" method="post" enctype="multipart/form-data"> 使用者名稱:<input name="username" /> <br /> 密碼:<input name="pass" type="password" /> <br /> 性別:<input type="radio" value="1" name="sex" checked="checked" />男 <input type="radio" value="0" name="sex" />女 <br /> 頭像:<input type="file" name="header" /> <br /> <input type="submit" value="註冊" /> </form>
三、在程式中實現上傳功能
1、匯入第三方包
實現檔案上傳有很多種方式,這裡我們使用第三方commons-fileupload,你可以到網上下載這個包,這個只有一個核心包,不過它需要依賴commons-io包,所有我們匯入這兩個包就可以了。
commons-fileupload.jar
commons-io.jar
2、開啟示例程式,參考示例程式完成程式碼
java的第三方包支援的技術很多,這也是java流行的原因,而且文件也非常詳細,我們可以在這個包的site目錄下,找到index.html檔案,並開啟就可以看到非常詳細的文件了,進入文件,點選User Guide就有一個非常詳細的入門示例,你可以參考這個示例完成檔案的上傳操作。
開啟servlet修改新增使用者的操作,完成程式碼如下:
else if (op.equals("add")) {
Map<String, String> data = new HashMap<String, String>();
boolean isMultipart = ServletFileUpload.isMultipartContent(request);
String savefilename = null;
try {
if (isMultipart) {
// Create a factory for disk-based file items
FileItemFactory factory = new DiskFileItemFactory();
// Create a new file upload handler
ServletFileUpload upload = new ServletFileUpload(factory);
// Parse the request
List<FileItem> items = upload.parseRequest(request);
// Process the uploaded items
Iterator iter = items.iterator();
while (iter.hasNext()) {
FileItem item = (FileItem) iter.next();
if (item.isFormField()) {
// processFormField(item);
// 處理原來原始的表單
String name = item.getFieldName();
String value = item.getString();
data.put(name, value);
} else {
// processUploadedFile(item);
// 處理上傳檔案
String fieldName = item.getFieldName();
String fileName = item.getName();
String contentType = item.getContentType();
boolean isInMemory = item.isInMemory();
long sizeInBytes = item.getSize();
// System.out.println(fieldName+":"+fileName+":"+contentType+":"+isInMemory+":"+sizeInBytes);
// 圖片上傳
// 如何獲得伺服器的檔案路徑
String strDirPath = request.getSession()
.getServletContext().getRealPath("/header");
savefilename = UUID.randomUUID()
+ fileName.substring(fileName
.lastIndexOf("."));
File uploadedFile = new File(strDirPath + "//"
+ savefilename);
item.write(uploadedFile);
}
}
// 儲存在資料庫中
User user = new User();
user.setUsername(data.get("username"));
user.setPass(data.get("pass"));
user.setSex(Integer.parseInt(data.get("sex")));
user.setHeader(savefilename);
int result = userDao.addUser(user);
if (result > 0) {
response.sendRedirect("userServlet?op=list");
} else {
response.sendRedirect("error.jsp");
}
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
從上面的程式碼可以看到對於普通控制元件和檔案控制元件是分開處理的,普通控制元件的值我們定義了一個Map格式全部儲存起來,檔案控制元件我們就儲存在伺服器的header目錄下,這裡需要動態的獲得伺服器的路徑使用的方法是:
String strDirPath = request.getSession().getServletContext().getRealPath("/header");
為了保證上傳圖片的檔名的唯一性,這裡我們使用UUID生成一個唯一性的名稱,程式碼是:
UUID.randomUUID()
這樣功能就完成了,你可以嘗試上傳一下,然後去tomcat伺服器的header目錄下就可以見到這個檔案了。
四、在列表中顯示頭像
我們要子列表中顯示頭像,因為資料庫中只是儲存了檔名稱,所有我們需要自己寫書路徑了,既然是頭像,我們當然需要使用img控制元件顯示圖片了。程式碼如下:
<td><img alt="" src="header/${user.header }" width="50"
height="50"></td>