天天看點

Applet結合Struts2實作檔案上傳

由于項目的需要,使用Applet實作檔案上傳被提上日程,作者關于applet實作檔案上傳google了N次,baidu了m次,終于搞定。最大的感觸就是網上的資料有時候會誤導你,需要不停的做實驗,不停地尋找出現問題的解決方案。作者由于幾個比較關鍵的地方網上的資料未提供,在此作為記錄,希望能對新手提供一些有用的參考。

關于檔案上傳的原理,可以baidu一下,網上的資料說得比較明白,在這裡略微提一下,檔案通過html上傳需要設定送出form表單的表單元素的enctype=” multipart/form-data” 原理是,通過為表單元素設定enctype=”multipart/form-data”屬性,讓表單送出的資料以二進制編碼的方式送出,在接收此請求的Servlet中用二進制流來擷取内容,就可以取得上傳檔案的内容,進而實作檔案的上傳。檔案上傳後在伺服器端得表示如下(選擇文本):

當上面檔案執行以後會産生如下結果:(選擇的上傳檔案不同,結果類似)

(1) -----------------------------7d45a76025c 

(2) Content-Disposition: form-data; name="text1"; filename=" D:\1.txt" 

(3) Content-Type: text/plain 

(4) 

(5) public static void main(String[] args) { 

(6) FileUtil.makeDir("dir1/dir2/dir3/dir4","c:/java/"); 

(7) } 

(8) } 

(9)

(10) -----------------------------7d45a76025c-- 

其中第一行為分界符,和(10)行一樣,第(10)行作為分界符的結尾,注意,比第一行在最後多出兩個“-“。第4,9行為空行,5-8行為需要寫入二進制檔案或者文本的地方。網上的一些資料沒有講這一部分,需要特别留意。

了解了檔案上傳的格式,就可以使用applet向伺服器端寫入以上格式的内容,就可以實作把檔案上傳到伺服器端了。如果伺服器端使用Struts2,則架構為我們接收了檔案,就不用寫servlet了。Struts2可以處理以POST方式送出的資料。下面講述開發的用戶端代碼,伺服器端的代碼如果不清楚,可以參看Struts2的官方文檔。

假設系統使用UTF-8編碼,用戶端調用Applet上傳檔案的代碼

       String url=http://127.0.0.1:8080/upload.action//接收檔案的action

       HttpURLConnection con = (HttpURLConnection) new URL(url) .openConnection();//打開連接配接

String boundary=”-------------------------123456”;//設定的分解符比實際用的少2個“-“

String twoHypeLine=” -- “;

String lineEnd=”\r\n”;

con.setDoOutput(true);

conn.setUseCaches(false);

   // Use a post method.POST為大寫

        conn.setRequestMethod("POST");

 con.setRequestProperty("Accept", "*/*");

con.setRequestProperty("Accept-Language", "zh-cn");

//設定分隔符

con.setRequestProperty("Content-Type",

                                          "multipart/form-data; boundary="+boundary);

con.setRequestProperty("Accept-Encoding", "gzip, deflate");

con.setRequestProperty("Connection", "Keep-Alive");

con.setRequestProperty("Cache-Control", "no-cache");

              // 設定流式輸出的請求頭和請求尾

String header =( twoHypeLine + twoHypeLine +boundary+lineEnd+

                            + "Content-Disposition: form-data; name=\"upload\"; filename=\"%s\" " +lineEnd+ "Content-Type: application/octet-stream "+ lineEnd+ lineEnd;

//name屬性可以了解為<input type=”file”>中的name屬性,在Struts2中被解析為uploadFileName屬性

//content-type在Struts2中被解析為UploadContentType

byte[] tailbyte =( lineEnd + twoHypeLine +boundary+ twoHypeLine+ lineEnd) .getBytes();

//檔案名種包含中文時,一定要記得使用utf-8

byte[] headByte = String.format(header, file.getName()).getBytes(“utf-8”);

 // 設定請求體的長度(直接輸出,避免在本地進行緩存),同時連接配接伺服器

con.setFixedLengthStreamingMode((int) file.length() + headByte.length+ tailbyte.length);

con.connect();

// 寫檔案流到請求體中

OutputStream dos = con.getOutputStream();

dos.write(headByte); // 寫檔案頭

//file為本地打開的檔案

FileInputStream fis = new FileInputStream(file);

int len = 0;

byte b[] = new byte[blockSize];

while (len != -1) {

       len = fis.read(b);

       if (len > 0) {

              dos.write(b, 0, len);

              dos.flush();

              uploadStatus.upload(len);

       }

}

fis.close();

dos.write(tail);

dos.close();

至此檔案基本上可以正确的寫入到伺服器端,那麼如何從伺服器端讀取哪?上傳之後的檔案可以通過json格式回傳資料,在Struts2中隻需要設定為傳回類型為json即可,

InputStream is = con.getInputStream();

byte[] response = new byte[is.available()];

is.read(response);

JsonObject  jo=new JsonObject(new String(response.getBytes(“UTF-8”)));

由于回傳的資料為UTF-8格式的,必須通過轉碼才能被JSON對象識别,對于傳回的資料,可以做你想做的任何處理,比如在頁面上顯示等等。當然在上傳過程中可以實作進度條。

君好運。

參考網站: http://mupload.googlecode.com

http://blog.csdn.net/Breeze2003/archive/2008/09/22/2962177.aspx

繼續閱讀