Uploadify + Struts2 應用之分析與詳解

fmms 12年前發布 | 59K 次閱讀 Uploadify Struts2 文件上傳

Uploadify是一個Jquery框架下處理批量文件上傳的插件,支持多種服務器端軟件。遺憾的是,官網(www.uploadify.com)的說明文檔做得很不完善,著重于說明Js部分的配置,而沒有對服務端的數據接口進行詳細說明。而且由于與服務器端進行數據交互的部分被封裝在swf文件中,也很難從源代碼進行分析。

 

1) 分析

基于此,為了探索Uploadify在Struts2下的應用接口數據,編寫了個小工具程序RequestObserver如下:

 

package utils;

import java.util.Enumeration; import java.util.Iterator; import java.util.Map;

import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpSession;

import com.opensymphony.xwork2.ognl.OgnlValueStack;

public class RequestObserver { private HttpServletRequest request;

public RequestObserver(HttpServletRequest request) {
    this.request = request;
}

public void observe() {
    String name,pvalue;
    Object avalue;
    Enumeration enum1;

    System.out.println("/***************** Request Observer (Author: Alex Nie)**************/");

    // observe Request Header
    enum1 = request.getHeaderNames();
    System.out.println("Request Header:");
    while (enum1.hasMoreElements()) {
        name = (String)enum1.nextElement();
        pvalue = request.getHeader(name);
        System.out.println("  " + name + " ---- " + pvalue);
    }
    enum1 = request.getParameterNames();

    // observe Request Parameters
    System.out.println("Request Parameters:");
    while (enum1.hasMoreElements()) {
        name = (String)enum1.nextElement();
        pvalue = request.getParameter(name);
        System.out.println("  " + name + " ---- " + pvalue);
    }
    enum1 = request.getAttributeNames();

    // observe Request Attributes
    System.out.println("Request Attributes:");
    while (enum1.hasMoreElements()) {
        name = (String)enum1.nextElement();
        avalue = request.getAttribute(name);
        System.out.println("  " + name + " ---- " + avalue);

        // observe OgnlValueStack bind by Struts 2
        if (avalue instanceof OgnlValueStack) {
            avalue = (OgnlValueStack)avalue;
            Map<String,Object> m = ((OgnlValueStack) avalue).getContext();
            System.out.println("  >> OgnlValueStack:");
            Iterator it = m.keySet().iterator();
            Object key;
            while (it.hasNext()) {
                key = it.next();
                System.out.println ("        " + key + " ---- " + m.get(key));
            }
        }
    }

    // observe Request Session
    HttpSession session = request.getSession(false);
    System.out.println("session: " + session);
    if (session!=null)
    {
        System.out.println("  sessionId: " + session.getId());
        enum1 = session.getAttributeNames();
        System.out.println("Session Attributes:");
        while (enum1.hasMoreElements()) {
            name = (String)enum1.nextElement();
            avalue = session.getAttribute(name);
            System.out.println("  " + name + " ---- " + avalue);
        }
    }
    System.out.println("/***************** End of Request Observer (Author: Alex Nie)**************/");

}

}</pre>

 

在按照官網的說明進行簡單配置后,從瀏覽器觸發上傳文件操作,在服務器端的Action中接收到相應的Request后,利用上述工具程序輸出分析Request中的數據,發現如下:

 

分析結果

在進行批量文件上傳時,Uploadify為每一個上傳文件發起一次服務器連接。

 

在每一次連接中,Uploadify向服務器端傳遞了7個參數,其中通過request parameters傳遞了4個String類型參數

Filename: 待上傳的文件原名, 內容與后述的xxxxFileName相同

fileext: 允許上傳的文件類型,由客戶段Js代碼中指定的fileExt參數指定

folder: 上傳文件在服務期上的保存路徑,由客戶段Js代碼中指定的folder參數指定

Upload:  暫無用處

 

通過request attributes 傳遞了3個參數

xxxx : 文件類型,上傳的文件內容,xxxx由客戶段Js代碼中指定的fileDataName參數指定

xxxxFileName: 字符串類型,上傳的文件的原名,xxxx由客戶段Js代碼中指定的fileDataName參數指定,內容與前述的Filename相同
uploadifyContentType: 暫無用處

 

以上7個參數在服務器端都被Struts2封裝,在Action都可直接使用。要注意的是參數名稱的大小寫和Js端的大小寫并不完全相同,有的在 Js中小寫服務器端大寫,有的剛好相反。此外有兩個參數內容相同,這些大約是Uploadify未來在代碼風格與約定方面可以改進的地方。

 

清楚了數據接口,Struts2下對應Uploadify的Action該怎么寫就很清楚了,接下來以批量上傳照片為例進行說明。

 

 

2) 應用詳解


html

<input id="file_upload" name="photo" type="file"/>

<div id="fileQueue"></div></pre>

 

 

Javascript

引入jquery-1.4.2.min.js, swfobject.js, jquery.uploadify.v2.1.4.min.js

引入自己的上傳用Js代碼如下(精簡說明版):

      $(document).ready(function() {
        $('#file_upload').uploadify({

        // 頁面相關
        'uploader'       : '/js/uploadify/uploadify.swf', //組件自帶的flash,路徑根據情況自行調整
        'cancelImg'      : '/js/uploadify/cancel.png',//取消上傳文件的按鈕圖片

        'queueID'        : 'fileQueue', //放置上傳文件及上傳進度的Html元素Id

        'queueSizeLimit' : 10, //一次最多選擇多少個文件上傳



        // 控制開關

        'auto'           : false, //是否選取文件后自動上傳,建議關閉
        'multi'          : true, //多文件上傳必須打開



        // 服務器腳本

        'script'         : 'uploadify.action', //Struts2下處理上傳的action路徑
        'scriptData'     : {'userid': '12345', 'username': 'Alex Nie'}, //自身業務需要向服務器端傳遞的數據



        // 傳遞給服務器參數

        'folder'         : '/upload', //上傳文件的目錄,將作為'folder'參數傳遞給服務器
        'fileDataName'   : 'photo', //它決定了最重要的兩個上傳參數名稱,本例中將為文件'photo'和文件名'photoFileName'

        'fileExt'        : '*.gid;*.jpg;*.jpeg', //允許的文件類型,在客戶端約束用戶的文件選擇,并將作為'fileext'參數傳遞給服務器供校驗用



        // 其它

        'fileDesc'       : '*.gif;*.jpg;*.jpeg', //顯示在本地選擇文件對話框的文件類型下拉框中
        'sizeLimit'      : 100*1024 // 單個文件的最大尺寸(字節為單位)
    });
  });



    function uploadFile(){//上傳文件
     jQuery('#file_upload').uploadifyUpload();
    }</pre> <p></p>

 

 

Java

在此不列出具體代碼了,只說明一下服務器端UploadifyAction程序的大致流程:

定義以下變量,且生成它們的get和set方法

    private File photo;
    private String photoFileName,fileext,folder;

1) 分析'fileext',分解出允許的所有文件類型;

2) 校驗photoFileName是否在允許的文件類型中

3) 校驗文件photo的大小是否超標(遺憾的是,Uploadify不會把Js中定義的'sizeLimit'傳遞給服務器,服務器端必須自行定義)

4) 校驗folder指定的路徑是否合法

5) 在folder指定的路徑下保存文件photo,根據業務需要可能要為它取名而不是用原文件名photoFileName

6) 向response寫入成功或失敗返回信息,供頁面使用

注:如果信任瀏覽器端的文件類型和文件尺寸約束校驗,也可以省略第2、第3步和第4步,不過為了防止惡意的客戶端偽裝,最好不要省略它們。

 

 

其它幾個值得使用的Uploadify選項

            'removeCompleted': false //完成上傳后是否自動清除網頁上的文件列表

            'displayData'    : 'percentage',//有speed和percentage兩種選擇,一個顯示速度,一個顯示完成百分比

            'buttonImg'      : '/images/mybutton.jpg', 可用圖片替換掉頁面上傳按鈕的英文文字顯示,避開直接替換成中文文字會遇到的編碼問題。

 

 

解決Uploadify缺省的英文提示窗問題

編輯jquery.uploadify.v2.1.4.min.js,查找'alert'和'confirm'調用,把提示信息從英文改成中文。

 

轉自:http://blog.csdn.net/alexandertech/article/details/6428366

 本文由用戶 fmms 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!