多多色-多人伦交性欧美在线观看-多人伦精品一区二区三区视频-多色视频-免费黄色视屏网站-免费黄色在线

國內最全IT社區平臺 聯系我們 | 收藏本站
阿里云優惠2
您當前位置:首頁 > php開源 > 綜合技術 > Android volley 解析(三)之文件上傳篇

Android volley 解析(三)之文件上傳篇

來源:程序員人生   發布時間:2015-04-03 08:43:51 閱讀次數:6259次

前面我們講了如何通過 volley 實現表單的提交,而這篇文章跟上1篇銜接很大,如果沒有看上1篇 blog 的朋友,建議先去看看 Android Volley解析(2)之表單提交篇
由于文件上傳實質就是表單的提交,只不過它提交的數據包括文件類型,接下來還是依照表單提交的套路來分析。

數據格式

這里我們通過圖片上傳的案例來分析,其他文件也是一樣的實現方式;以下是我在傳圖網傳圖時,上傳的數據格式,先來分析1下

POST http://chuantu.biz/upload.php HTTP/1.1 Host: chuantu.biz Connection: keep-alive Content-Length: 4459 Cache-Control: max-age=0 Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8 Origin: http://chuantu.biz User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/40.0.2214.93 Safari/537.36 Content-Type: multipart/form-data; boundary=----WebKitFormBoundaryS4nmHw9nb2Eeusll Referer: http://chuantu.biz/ Accept-Encoding: gzip, deflate Accept-Language: zh-CN,zh;q=0.8 Cookie: __cfduid=d9215d649e6e648e0eac7688b406a3d911425089350 ------WebKitFormBoundaryS4nmHw9nb2Eeusll Content-Disposition: form-data; name="uploadimg"; filename="spark_bg.png" Content-Type: image/png JFIFC %# , #&')*)-0-(0%()(C (((((((((((((((((((((((((((((((((((((((((((((((((((" }!1AQa"q2#BR$3br %&'()*456789:CDEFGHIJSTUVWXYZcdefghijstuvwxyz w!1AQaq"2B #3Rbr $4%&'()*56789:CDEFGHIJSTUVWXYZcdefghijstuvwxyz?PNG ------WebKitFormBoundaryS4nmHw9nb2Eeusll--

不難發現,這類格式跟表單提交的格式非常接近,不過還是有所差別,這里仔細看還是能看出來總共有加上結尾行,有5行,由于亂碼部份,其實就是圖片的2進制數,全部算1行;下面來分析下:
1、第1行:"--" + boundary + " " ;
前面也說了文件上傳,其實就是表單提交,所以在提交數據的開始標志不變;
2、第2行:Content-Disposition: form-data; name="參數的名稱"; filename="上傳的文件名" + " "
這里比普通的表單多了1個filename=”上傳的文件名”;
3、第3行:Content-Type: 文件的 mime 類型 + " "
這1行是文件上傳必須要的,而普通的文字提交可有可無,mime 類型需要根據文檔查詢;
4、第4行:" "
5、第5行文件的2進制數據 + " "
這里跟普通表單提交1樣;
結尾行:"--" + boundary + "--" + " "
可以看到,文件上傳的詩句格式跟我們上1篇博文中講到的表單提交只有兩個地方不同,1、第2行的時候增加了1個文件名變量,2、增加了1行Content-Type: 文件的 mime 類型 + " "
文件也能夠同時上傳多個文件,上傳多個文件的時候重復1、2、3、4、5步,在最后的1個文件的末尾加上統1的結束行。

文件實體類

這里是對圖片操作所以我建了1個FormImg.java

/** * Created by moon.zhong on 2015/3/3. */ public class FormImage { //參數的名稱 private String mName ; //文件名 private String mFileName ; //文件的 mime,需要根據文檔查詢 private String mMime ; //需要上傳的圖片資源,由于這里測試為了方便起見,直接把 bigmap 傳進來,真正在項目中1般不會這般做,而是把圖片的路徑傳過來,在這里對圖片進行2進制轉換 private Bitmap mBitmap ; public FormImage(Bitmap mBitmap) { this.mBitmap = mBitmap; } public String getName() { // return mName; //測試,把參數名稱寫死 return "uploadimg" ; } public String getFileName() { //測試,直接寫死文件的名字 return "test.png"; } //對圖片進行2進制轉換 public byte[] getValue() { ByteArrayOutputStream bos = new ByteArrayOutputStream() ; mBitmap.compress(Bitmap.CompressFormat.JPEG,80,bos) ; return bos.toByteArray(); } //由于我知道是 png 文件,所以直接根據文檔查的 public String getMime() { return "image/png"; } }

Volley 對文件數據的封裝

/** * Created by gyzhong on 15/3/1. */ public class PostUploadRequest extends Request<String> { /** * 正確數據的時候回掉用 */ private ResponseListener mListener ; /*要求 數據通過參數的情勢傳入*/ private List<FormImage> mListItem ; private String BOUNDARY = "-------------⑸20⑴3⑴4"; //數據分隔線 private String MULTIPART_FORM_DATA = "multipart/form-data"; public PostUploadRequest(String url, List<FormImage> listItem, ResponseListener listener) { super(Method.POST, url, listener); this.mListener = listener ; setShouldCache(false); mListItem = listItem ; //設置要求的響應事件,由于文件上傳需要較長的時間,所以在這里加大了,設為5秒 setRetryPolicy(new DefaultRetryPolicy(5000,DefaultRetryPolicy.DEFAULT_MAX_RETRIES,DefaultRetryPolicy.DEFAULT_BACKOFF_MULT)); } /** * 這里開始解析數據 * @param response Response from the network * @return */ @Override protected Response<String> parseNetworkResponse(NetworkResponse response) { try { String mString = new String(response.data, HttpHeaderParser.parseCharset(response.headers)); Log.v("zgy", "====mString===" + mString); return Response.success(mString, HttpHeaderParser.parseCacheHeaders(response)); } catch (UnsupportedEncodingException e) { return Response.error(new ParseError(e)); } } /** * 回調正確的數據 * @param response The parsed response returned by */ @Override protected void deliverResponse(String response) { mListener.onResponse(response); } @Override public byte[] getBody() throws AuthFailureError { if (mListItem == null||mListItem.size() == 0){ return super.getBody() ; } ByteArrayOutputStream bos = new ByteArrayOutputStream() ; int N = mListItem.size() ; FormImage formImage ; for (int i = 0; i < N ;i++){ formImage = mListItem.get(i) ; StringBuffer sb= new StringBuffer() ; /*第1行*/ //`"--" + BOUNDARY + " "` sb.append("--"+BOUNDARY); sb.append(" ") ; /*第2行*/ //Content-Disposition: form-data; name="參數的名稱"; filename="上傳的文件名" + " " sb.append("Content-Disposition: form-data;"); sb.append(" name=""); sb.append(formImage.getName()) ; sb.append(""") ; sb.append("; filename="") ; sb.append(formImage.getFileName()) ; sb.append("""); sb.append(" ") ; /*第3行*/ //Content-Type: 文件的 mime 類型 + " " sb.append("Content-Type: "); sb.append(formImage.getMime()) ; sb.append(" ") ; /*第4行*/ //" " sb.append(" ") ; try { bos.write(sb.toString().getBytes("utf⑻")); /*第5行*/ //文件的2進制數據 + " " bos.write(formImage.getValue()); bos.write(" ".getBytes("utf⑻")); } catch (IOException e) { e.printStackTrace(); } } /*結尾行*/ //`"--" + BOUNDARY + "--" + " "` String endLine = "--" + BOUNDARY + "--" + " " ; try { bos.write(endLine.toString().getBytes("utf⑻")); } catch (IOException e) { e.printStackTrace(); } Log.v("zgy","=====formImage==== "+bos.toString()) ; return bos.toByteArray(); } //Content-Type: multipart/form-data; boundary=---------⑻888888888888 @Override public String getBodyContentType() { return MULTIPART_FORM_DATA+"; boundary="+BOUNDARY; } }

由于代碼中注解寫的比較詳細,加上很多東西在前面幾篇 blog 已講過了,所以這里直接上代碼。

文件上傳接口

/** * Created by moon.zhong on 2015/3/3. */ public class UploadApi { /** * 上傳圖片接口 * @param bitmap 需要上傳的圖片 * @param listener 要求回調 */ public static void uploadImg(Bitmap bitmap,ResponseListener listener){ List<FormImage> imageList = new ArrayList<FormImage>() ; imageList.add(new FormImage(bitmap)) ; Request request = new PostUploadRequest(Constant.UploadHost,imageList,listener) ; VolleyUtil.getRequestQueue().add(request) ; } }

圖片上傳驗證

上傳類PostUploadActivity.java

/** * Created by moon.zhong on 2015/3/2. */ public class PostUploadActivity extends ActionBarActivity { private TextView mShowResponse ; private ImageView mImageView ; private ProgressDialog mDialog ; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_upload_img); mShowResponse = (TextView) findViewById(R.id.id_show_response) ; mImageView = (ImageView) findViewById(R.id.id_show_img) ; mDialog = new ProgressDialog(this) ; mDialog.setCanceledOnTouchOutside(false); } public void uploadImg(View view){ mDialog.setMessage("圖片上傳中..."); mDialog.show(); Bitmap bitmap = BitmapFactory.decodeResource(getResources(),R.mipmap.logo) ; UploadApi.uploadImg(bitmap,new ResponseListener<String>() { @Override public void onErrorResponse(VolleyError error) { Log.v("zgy","===========VolleyError========="+error) ; mShowResponse.setText("ErrorResponse "+error.getMessage()); Toast.makeText(PostUploadActivity.this,"上傳失敗",Toast.LENGTH_SHORT).show() ; mDialog.dismiss(); } @Override public void onResponse(String response) { response = response.substring(response.indexOf("img src="http://www.vxbq.cn/uploadfile/cj/20150307/)); response = response.substring(8,response.indexOf("/>")) ; Log.v("zgy","===========onResponse========="+response) ; mShowResponse.setText("圖片地址: "+response); mDialog.dismiss(); Toast.makeText(PostUploadActivity.this,"上傳成功",Toast.LENGTH_SHORT).show(); } }) ; } }

測試結果以下:
上傳圖片頁面:
這里寫圖片描述
圖片上傳中
這里寫圖片描述
圖片上傳成功,地址為http://www.chuantu.biz/t/67/1425474351x⑴376440163.png
這里寫圖片描述
通過網頁要求
這里寫圖片描述

可以看到,volley 實現文件上傳的操作還是很方便的,不過,不知道大家看到這里有無覺得哪里有問題呢?其實 volley 實現文件上傳是有1個很大的問題,甚么問題呢,大家自己先想一想,我將會在后續的文章中講到這個問題,并提供解決方案(是后續,不是下1篇)。volley 講到這里為止,對它的功能也講了1大部份,不過還有1個非常有用的知識點沒有講到,那就是volley緩存機制,下1節,將開啟 volley 的緩存之旅,敬請期待!

點擊下載源碼

生活不易,碼農辛苦
如果您覺得本網站對您的學習有所幫助,可以手機掃描二維碼進行捐贈
程序員人生
------分隔線----------------------------

上一篇 泛型

下一篇 Awk的使用

分享到:
------分隔線----------------------------
關閉
程序員人生
主站蜘蛛池模板: 欧美男男作爱gayxxx | 一本大道香蕉中文日本不卡高清二区 | 亚洲天堂视频在线观看免费 | 天天澡天天碰天天狠伊人五月 | 福利片一区 | 尤物免费在线视频 | 中文字幕精品一区二区精品 | 国产片免费 | 欧美日韩视频 | xxxxx免费视频| 亚洲国产精品久久精品成人 | 欧美一区二区三区东南亚 | 国产成人十八黄网片 | 日韩欧美在线第一页 | 黑人一区二区三区中文字幕 | 亚洲天堂aa| 视频在线观看免费播放www | 性欧美巨大 | 欧美一级刺激毛片 | 尤物视频在线播放 | 一级做a爰片性色毛片新版的 | 欧美同性video | 国产午夜人做人免费视频中文 | 亚州三级视频 | 日韩欧美在线第一页 | 国产色a在线观看 | 手机看片一区二区 | 亚洲 校园 春色 另类 激情 | 毛片网此 | 免费观看福利视频 | 在线看www| 羞羞动漫入口 | 国产72av国片精品jk制服 | 亚洲免费在线视频 | 欧美性xxxx另类 | 亚洲伊人久久网 | 日本一区二区三区在线 视频 | 波多野结衣在线观看视频 | 亚洲大片免费观看 | 国产福利在线看 | 亚洲欧美日韩精品久久亚洲区 |