欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

Android上传文件到服务端并显示进度条

程序员文章站 2024-03-02 20:49:16
最近在做上传文件的服务,简单看了网上的教程。结合实践共享出代码。 由于网上的大多数没有服务端的代码,这可不行呀,没服务端怎么调试呢。 ok,先上代码。 android...

最近在做上传文件的服务,简单看了网上的教程。结合实践共享出代码。

由于网上的大多数没有服务端的代码,这可不行呀,没服务端怎么调试呢。

ok,先上代码。

android 上传比较简单,主要用到的是 httpurlconnection 类,然后加一个进度条组件。

private progressbar mpgbar; 
class uploadtask extends asynctask<object,integer,void>{ 
  private dataoutputstream outputstream = null; 
  private string filename; 
  private string uri; 
  private string mlineend = "\r\n"; 
  private string mtwohyphens = "--"; 
  private string boundary = "*****"; 
  file uploadfile ; 
  long mttotalsize ; // get size of file, bytes 
  public uploadtask(string filename,string uri){ 
   this.filename = filename; 
   this.uri = uri; 
   uploadfile= new file(filename); 
    mttotalsize = uploadfile.length(); 
  } 
 
  /** 
   * 开始上传文件 
   * @param objects 
   * @return 
   */ 
  @override 
  protected void doinbackground(object... objects) { 
   long length = 0; 
   int mbytesread, mbytesavailable, mbuffersize; 
   byte[] buffer; 
   int maxbuffersize = 256 * 1024;// 256kb 
   try{ 
 
    fileinputstream fileinputstream = new fileinputstream(new file(filename)); 
 
    url url = new url(uri); 
 
    httpurlconnection con = (httpurlconnection) url.openconnection(); 
 
    //如果有必要则可以设置cookie 
//    conn.setrequestproperty("cookie","jsessionid="+cookie); 
 
    // set size of every block for post 
 
    con.setchunkedstreamingmode(256 * 1024);// 256kb 
 
    // allow inputs & outputs 
    con.setdoinput(true); 
    con.setdooutput(true); 
    con.setusecaches(false); 
 
    // enable post method 
    con.setrequestmethod("post"); 
    con.setrequestproperty("connection", "keep-alive"); 
    con.setrequestproperty("charset", "utf-8"); 
    con.setrequestproperty("content-type", 
      "multipart/form-data;boundary=" + boundary); 
 
    outputstream = new dataoutputstream( 
      con.getoutputstream()); 
    outputstream.writebytes(mtwohyphens + boundary + mlineend); 
    outputstream.writebytes("content-disposition: form-data; name=\"file\"; filename=\"" + filename + "\"" + mlineend); 
    outputstream.writebytes("content-type:application/octet-stream \r\n"); 
    outputstream.writebytes(mlineend); 
 
    mbytesavailable = fileinputstream.available(); 
    mbuffersize = math.min(mbytesavailable, maxbuffersize); 
    buffer = new byte[mbuffersize]; 
 
    // read file 
    mbytesread = fileinputstream.read(buffer, 0, mbuffersize); 
 
    while (mbytesread > 0) { 
     outputstream.write(buffer, 0, mbuffersize); 
     length += mbuffersize; 
 
     publishprogress((int) ((length * 100) / mttotalsize)); 
 
     mbytesavailable = fileinputstream.available(); 
 
     mbuffersize = math.min(mbytesavailable, maxbuffersize); 
 
     mbytesread = fileinputstream.read(buffer, 0, mbuffersize); 
    } 
    outputstream.writebytes(mlineend); 
    outputstream.writebytes(mtwohyphens + boundary + mtwohyphens 
      + mlineend); 
    publishprogress(100); 
 
    // responses from the server (code and message) 
    int serverresponsecode = con.getresponsecode(); 
    string serverresponsemessage = con.getresponsemessage(); 
    fileinputstream.close(); 
    outputstream.flush(); 
    outputstream.close(); 
 
   } catch (exception ex) { 
    ex.printstacktrace(); 
    log.v(tag,"uploaderror"); 
   } 
   return null; 
  } 
 
  @override 
  protected void onprogressupdate(integer... progress) { 
   mpgbar.setprogress(progress[0]); 
  } 
 } 

主要流程为继承asynctask,然后使用httpurlconnection 去上传文件。代码比较简单,就不一一讲解了。
其中要注意的是需要在

复制代码 代码如下:
outputstream.writebytes("content-disposition: form-data; name=\"file\"; filename=\"" +  filename + "\"" + mlineend); 

将name 设置为web 请求的参数名,由于我的服务端是将文件设置为file参数,所以我可以直接填file .所以大家可以根据实际情况作相应修改。

那么接着上服务端代码,服务端主要使用status 2框架作请求。那么我们就需要进行封装。

//上传文件集合 
 private list<file> file; 
 //上传文件名集合 
 private list<string> filefilename; 
 //上传文件内容类型集合 
 private list<string> filecontenttype; 
 
 public list<file> getfile() { 
  return file; 
 } 
 
 public void setfile(list<file> file) { 
  this.file = file; 
 } 
 
 public list<string> getfilefilename() { 
  return filefilename; 
 } 
 
 public void setfilefilename(list<string> filefilename) { 
  this.filefilename = filefilename; 
 } 
 
 public list<string> getfilecontenttype() { 
  return filecontenttype; 
 } 
 
 public void setfilecontenttype(list<string> filecontenttype) { 
  this.filecontenttype = filecontenttype; 
 } 

采用了多文件上传的方法,定义了list 集合。
那么处理文件上传的action ,由于是测试方法。这里就定义为testupload

public string testupload()throws exception{ 
  system.out.println("success"); 
  uploadfile(0); 
  return success; 
 } 

到这里就已经才不多完成动作了,现在需要开始写上传的方法 uploadfile(int index),由于定义file 为多文件上传,而我们上传只上传了一个文件,所以这里参数为0

/** 
  * 上传功能 
  * @param i 
  * @return 
  * @throws filenotfoundexception 
  * @throws ioexception 
  */ 
 private string uploadfile(int i) throws filenotfoundexception, ioexception { 
   
  try { 
   inputstream in = new fileinputstream(file.get(i)); 
 
   //string dir = servletactioncontext.getrequest().getrealpath(uploaddir); 
    
   string dir = "d://uploaddata/"; 
 
   file uploadfile = new file(dir,stringutils.getuuid()+getfile( this.getfilefilename().get(i))); 
 
   outputstream out = new fileoutputstream(uploadfile); 
 
   byte[] buffer = new byte[1024 * 1024]; 
 
   int length; 
   while ((length = in.read(buffer)) > 0) { 
    out.write(buffer, 0, length); 
   } 
 
   in.close(); 
   out.close(); 
   //然后进行计算 
   return uploadfile.getabsolutepath(); 
  } catch (filenotfoundexception ex) { 
   ex.printstacktrace(); 
  } catch (ioexception ex) { 
   ex.printstacktrace(); 
  } 
  return null; 
 } 

上面方法为将缓存区域的文件 然后搞到了d://uploaddata/ 文件中,然后以自己的格式进行命名,这里我使用了电脑的uuid和文件名进行组合,确保我复制过来的文件不重复。
最后上传成功之后返回文件的真实地址。

ok,写到这里上传文件的功能基本上做完了。最后只剩下配置action 动作。

ok,我们打开status.xml 文件进行配置

<!-- 系统常量定义,定义上传文件字符集编码 --> 
 <constant name="struts.i18n.encoding" value="utf-8"></constant> 
 <!-- 系统常量定义,定义上传文件零时存放路径 --> 
 <constant name="struts.multipart.savedir" value="c:\tmp\"></constant> 
 <constant name="struts.multipart.maxsize" value="10000000" /> 

这里主要定义上传文件的临时存放位置,然后大小限制。
大家可以根据实际情况进行配置。

最后上传一张效果图。

Android上传文件到服务端并显示进度条

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。