<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    MDA/MDD/TDD/DDD/DDDDDDD
    posts - 536, comments - 111, trackbacks - 0, articles - 0
      BlogJava :: 首頁 :: 新隨筆 :: 聯系 :: 聚合  :: 管理

    使用commons fileupload的零碎筆記

    Posted on 2007-08-27 11:58 leekiang 閱讀(30341) 評論(6)  編輯  收藏 所屬分類: fileupload
    我對表單上傳的理解(可能有誤):
    ?<form action="" method="post" enctype="multipart/form-data">
    ?最大上傳2G.
    通過 http 協議上傳文件(rfc1867協議概述,jsp 應用舉例,客戶端發送內容構造)
    ?服務器接收到上傳的流,自己其實是不作任何處理的,那個request還是原裝的,誰來處理這個request呢,一般采用第三方的工具,這里以commons fileupload為例.
    ?
    DiskFileItemFactory?factory?=?new?DiskFileItemFactory();
    factory.setSizeThreshold(
    4096);//?設置緩沖,這個值決定了是fileinputstream還是bytearrayinputstream
    factory.setRepository(new File("d:\\temp"));//設置臨時存放目錄,默認是new File(System.getProperty("java.io.tmpdir"))
    ServletFileUpload?sfu?=?new?ServletFileUpload(factory);
    sfu.setSizeMax(
    100*1024*1024);//100M
    List items?=?sfu.parseRequest(request);//傳入的這個request還是原裝的
    ?見上面的代碼,commons fielupload通過ServletFileUpload類的parseRequest(request)方法處理這個原始流。而ServletFileUpload又會調用其爺爺類FileUploadBase的parseRequest(request)方法,然后又會調return parseRequest(new ServletRequestContext(request)),代碼如下

    ????????
    try?{
    ????????????FileItemIterator?iter?
    =?getItemIterator(ctx);
    ????????????List?items?
    =?new?ArrayList();
    ????????????FileItemFactory?fac?
    =?getFileItemFactory();
    ????????????
    if?(fac?==?null)?{
    ????????????????
    throw?new?NullPointerException(
    ????????????????????
    "No?FileItemFactory?has?been?set.");
    ????????????}
    ????????????
    while?(iter.hasNext())?{
    ????????????????FileItemStream?item?
    =?iter.next();
    ????????????????FileItem?fileItem?
    =?fac.createItem(item.getFieldName(),
    ????????????????????????item.getContentType(),?item.isFormField(),
    ????????????????????????item.getName());
    ????????????????
    try?{
    ????????????????????Streams.copy(item.openStream(),?fileItem.getOutputStream(),
    ????????????????????????????
    true);
    ????????????????}?
    catch?(FileUploadIOException?e)?{
    ????????????????????
    throw?(FileUploadException)?e.getCause();
    ????????????????}?
    catch?(IOException?e)?{
    ????????????????????
    throw?new?IOFileUploadException(//報錯經常在這里
    ????????????????????????????
    "Processing?of?"?+?MULTIPART_FORM_DATA
    ????????????????????????????
    +?"?request?failed.?"?+?e.getMessage(),?e);
    ????????????????}
    ????????????????
    if?(fileItem?instanceof?FileItemHeadersSupport)?{
    ????????????????????
    final?FileItemHeaders?fih?=?item.getHeaders();
    ????????????????????((FileItemHeadersSupport)?fileItem).setHeaders(fih);
    ????????????????}
    ????????????????items.add(fileItem);
    ????????????}
    ????????????
    return?items;
    ????????}?
    catch?(FileUploadIOException?e)?{
    ????????????
    throw?(FileUploadException)?e.getCause();
    ????????}?
    catch?(IOException?e)?{
    ????????????
    throw?new?FileUploadException(e.getMessage(),?e);
    ????????}
    ????

    ?這里注意,上傳的<input type=file
    >標記一定要有name,如果沒有,commons fielupload不作處理
    ?commons fielupload會把上傳的文件以流的方式寫入到temp文件夾,臨時文件夾可以自己設定,如果不手動設置,則是Servlet容器為web應用分配的臨時目錄,tomcat可能就是%TOMCAT_HOME%\temp,我用weblogic時,是C:\DOCUME~1\yourname\LOCALS~1\Temp\。這些臨時文件以"upload"開頭,格式是.tmp,例如"upload_47fdc3_11c9eb678b0__8000_00000043.tmp"
    ?在上傳過程中commons fielupload才知道上傳的文件的大小,如果你定義允許的最大附件為100M,然后你上傳一個200M的文件,那么只有實際傳輸了100M以后,commons fielupload才知道超過了,然后拋出一個異常(org.apache.commons.fileupload.FileUploadBase.SizeLimitExceededException)。
    ?commons fielupload處理完了以后(處理過程全在parseRequest(request)方法里),返回一個List,里面的每一項已被封裝為FileItem,你通過fileItem.isFormField()判斷出是普通的表單屬性呢,還是一個文件,如果是文件,你可以從fileItem.getInputStream()獲得輸入流,這個輸入流其實是一個FileInputStream.當然,如果文件很小,則是ByteArrayInputStream.那么如何區分?這兩者的區別是由factory.setSizeThreshold(4096)確定的。大于4K,為FileInputStream,小于4K為ByteArrayInputStream

    這樣就可以解釋struts用ActionForm的方式處理上傳附件的一些問題了,struts接收到enctype="multipart/form-data"的post請求后,會看那個對應的action有沒有配置actionform,如果配置了,就會作一些處理,所以你在action里得到的request已經不是一個普通的request了,而是一個被封裝過的request。如果想得到原始的request,就不要struts-config.xml里給action類配置actionform

    tempDir指定的目錄中可能會隨著時間推移出現很多后綴為"tmp"的垃圾文件,commons-fileupload1.2提供了一個不錯的解決方法,就是把下面的代碼加入到web.xml中即可。
    <listener>
    <listener-class>
    org.apache.commons.fileupload.servlet.FileCleanerCleanup
    </listener-class>
    </listener>
    來源:http://fratemity1314.spaces.live.com/Blog/cns!E3BCC13A1E72BB4F!222.entry

    Q:I'm using FileUpload in an Action, but it's not working. Why?

    A:Struts recognises multipart requests, and parses them automatically, presenting the request parameters to your code in the same manner as if they were regular request parameters. Since struts has already processed the request, and made it available in your form bean, the input stream is no longer available for parsing, so attempting to do so with FileUpload will fail.

    Q:But I need to parse the request myself. How can I do that?

    A:Struts parses multipart a request as a part of the process of populating your form bean from that request. If, for some reason, you need to have full control over the multipart parsing, you can do so by configuring your action mapping without an associated form bean. (A better way of doing this, however, is to replace the default multipart handler with your own. See the struts documentation for details.)



    1,直接用commons fileupload而不用struts的ActionForm時,表單里的屬性值不能用request.getParameter()獲取了,而url里的queryString可以。
    2,? 獲取form里的屬性值的代碼


    ????????????????????String?formname?
    =?fi.getFieldName();//?獲取form中的名字
    ????????????????????String?formcontent?=?fi.getString();
    ????????????????????
    if?(formname.equals("id"))?{
    ????????????????????????id?
    =?formcontent;
    ????????????????????}
    ?else?if?(formname.equals("title"))?{
    ????????????????????????title?
    =?formcontent;
    ????????????????????}
    ?else?if?(formname.equals("memo"))?{
    ????????????????????????memo?
    =?formcontent;
    ????????????????????}

    ????????????????

    3, 表單里的file控件的name不能為空。
    4,上傳大文件(190多M)時報異常
    org.apache.commons.fileupload.FileUploadException: ? Processing ? of ? multipart/form-data ? request ? failed. ? EOF ? after ? reading ? only: ? "3567789 " ? of: ? "203323339 " ? promised ? bytes, ? out? of ? which ? at ? least: ? "0 " ? were ? already ? buffered
    http://forums.bea.com/thread.jspa?threadID=200033356
    http://dev2dev.bea.com.cn/bbs/thread.jspa?forumID=121&threadID=20060&start=0&tstart=0
    http://thisisxy.blogcn.com/diary,204014352.shtml
    http://www.80diy.com/home/20050527/17/4040711.html

    5,
    org.apache.commons.fileupload.FileUploadException: Processing of multipart/form-data request failed. Read timed out
    HTTP活動超時限制的時間太短 HTTP Keep-Alive Timeout.

    6,InputStream is =formFile.getInputStream() ;? //formFile是org.apache.struts.upload.FormFile
    上傳的文件小時這個輸入流是java.io.ByteArrayInputStream,上傳比較大的文件時這個輸入流是FileInputStream

    7,設置表單里的上傳路徑為只讀
    <input type=file id="uploadfile" name="uploadfile" style="display: none;">
    <input type=text id=tempfile readonly="true">
    <input type=button
    onClick="uploadfile.click();tempfile.value=uploadfile.value;" value="瀏覽..">

    10,
    http://eastpoint.javaeye.com/blog/99084
    http://topic.csdn.net/u/20080131/13/649c57c7-204e-4bb6-9b09-49cca39f00b8.html
    http://blog.niwota.com/nb/chenchuang?cat_self_id=291075

    評論

    # re: 使用commons fileupload的零碎筆記  回復  更多評論   

    2008-10-31 15:27 by leekiang
    對于post和get的參數,好像commons fileupload的處理是不一樣的,get參數可以直接通過request.getParameter()的方式獲取,而post的不行,待驗證。

    # re: 使用commons fileupload的零碎筆記  回復  更多評論   

    2009-07-23 10:24 by 尹偉杰
    我現在就遇到了這樣的問題

    # re: 使用commons fileupload的零碎筆記  回復  更多評論   

    2009-07-23 10:27 by 尹偉杰
    一次性上傳衛星照片4個 大于2G weblogic報錯 超時 但是 改成4個form分開
    一個form 965m 也報錯 都暈了,你當時是怎么解決的???
    我的qq是838303967

    # re: 使用commons fileupload的零碎筆記  回復  更多評論   

    2009-07-23 10:29 by 尹偉杰
    Processing of multipart/form-data request failed. EOF after reading only: '38535168' of: '967898783' promised bytes, out of which at least: '0' were already buffered 報的錯!!!

    # re: 使用commons fileupload的零碎筆記  回復  更多評論   

    2009-07-28 18:49 by 尹偉杰
    哥們你趕快上線啊!!我的快瘋了!!!我的電話是13146277259 qq是838303967!!!

    # re: 使用commons fileupload的零碎筆記  回復  更多評論   

    2010-08-30 21:58 by gogoes
    throw new IOFileUploadException(//報錯經常在這里
    "Processing of " + MULTIPART_FORM_DATA
    + " request failed. " + e.getMessage(), e);


    我現在處理大量用戶數據時,老是這里出錯,出錯信息如下:
    Caused by: org.apache.commons.fileupload.FileUploadException: Processing of multipart/form-data request failed. Stream ended unexpectedly
    at com.alibaba.service.upload.patch.ServletFileUpload.parseRequest(ServletFileUpload.java:162)
    at com.alibaba.service.upload.patch.ServletFileUpload.parseRequest(ServletFileUpload.java:40)
    at com.alibaba.service.upload.DefaultUploadService.parseRequest(DefaultUploadService.java:165)

    能幫看看,有什么解決的辦法嗎?
    主站蜘蛛池模板: 一本大道一卡二大卡三卡免费| 亚洲国产精品乱码一区二区| jlzzjlzz亚洲jzjzjz| 波多野结衣免费一区视频 | 免费黄色网址网站| 久久精品蜜芽亚洲国产AV | 97视频热人人精品免费| 亚洲永久中文字幕在线| 久久久久久久91精品免费观看| 亚洲成综合人影院在院播放| 久久精品国产免费观看| 亚洲人成在线精品| 大学生a级毛片免费观看| 国产成人亚洲综合a∨| 亚洲高清偷拍一区二区三区| 一区二区免费国产在线观看| 亚洲午夜久久久久久久久电影网| 999zyz**站免费毛片| 亚洲国产高清视频| 成人黄色免费网站| 亚洲爆乳大丰满无码专区| 国产三级免费观看| 一级黄色毛片免费看| 亚洲国产精品一区二区久久hs| 8x8×在线永久免费视频| 亚洲一区免费在线观看| 日韩免费无砖专区2020狼| eeuss影院免费92242部| 亚洲国产女人aaa毛片在线| 人成午夜免费视频在线观看| 亚洲国产精品无码久久98| 亚洲视频在线精品| 久久99国产乱子伦精品免费| 亚洲日本乱码卡2卡3卡新区| 免费一级e一片在线播放| 很黄很污的网站免费| 四虎必出精品亚洲高清| 国产精品xxxx国产喷水亚洲国产精品无码久久一区| 99re6在线精品免费观看| 中文字幕亚洲码在线| 久久精品国产亚洲精品|