• ASP.NET、JAVA跨服务器远程上传文件(图片)的相关解决方案整合


    一、图片提交例:

    A端--提交图片

    protected void Page_Load(object sender, EventArgs e)
            {
                if (!IsPostBack)
                {
                    string url = "http://www./AppWeb/AppService.asmx";
                    string method = "test";
                    string result1 = BuildRequest(url + "/" + method, System.Web.HttpContext.Current.Server.MapPath("~/images/") + "1.png", "UTF-8");
                    Response.Write(result1);
                }
            }
            public static string BuildRequest(string strUrl, string strPicPath, string _input_charset)
            {
                Encoding code = Encoding.GetEncoding(_input_charset);
    
                //把数组转换成流中所需字节数组类型
                byte[] bytesRequestData = SetImgToByte(strPicPath);
    
                //请求远程HTTP
                string strResult = "";
                try
                {
                    //设置HttpWebRequest基本信息
                    HttpWebRequest myReq = (HttpWebRequest)HttpWebRequest.Create(strUrl);
                    myReq.Method = "post";
                    myReq.ContentType = "application/x-www-form-urlencoded";
    
                    //填充POST数据
                    myReq.ContentLength = bytesRequestData.Length;
                    Stream requestStream = myReq.GetRequestStream();
                    requestStream.Write(bytesRequestData, 0, bytesRequestData.Length);
                    requestStream.Close();
    
                    //发送POST数据请求服务器
                    HttpWebResponse HttpWResp = (HttpWebResponse)myReq.GetResponse();
                    Stream myStream = HttpWResp.GetResponseStream();
    
                    //获取服务器返回信息
                    StreamReader reader = new StreamReader(myStream, code);
                    StringBuilder responseData = new StringBuilder();
                    String line;
                    while ((line = reader.ReadLine()) != null)
                    {
                        responseData.Append(line);
                    }
    
                    //释放
                    myStream.Close();
    
                    strResult = responseData.ToString();
                }
                catch (Exception exp)
                {
                    strResult = "报错:" + exp.Message;
                }
    
                return strResult;
            }
            /// <summary>
            /// 将图片转化为长二进制
            /// </summary>
            /// <param name="photopath"></param>
            /// <returns></returns>
            public static Byte[] SetImgToByte(string imgPath)
            {
                FileStream file = new FileStream(imgPath, FileMode.Open, FileAccess.Read);
                Byte[] byteData = new Byte[file.Length];
                file.Read(byteData, 0, byteData.Length);
                file.Close();
                return byteData;
            }

    B端--接收图片

    [WebMethod(Description = "test")]
        public string test()
        {
            if ("POST" == System.Web.HttpContext.Current.Request.RequestType)
            {
                System.IO.Stream sm = System.Web.HttpContext.Current.Request.InputStream;//获取post正文
                int len = (int)sm.Length;//post数据长度
                byte[] inputByts = new byte[len];//字节数据,用于存储post数据
                sm.Read(inputByts, 0, len);//将post数据写入byte数组中
                sm.Close();//关闭IO流
                string fileName = Guid.NewGuid() + ".jpg";
                string strPath = System.Web.HttpContext.Current.Server.MapPath("~/images/") + fileName;
                //此处还需要做文件类型的判断
                using (FileStream fileStream = new FileStream(strPath, FileMode.Create))
                {
                    fileStream.Write(inputByts, 0, inputByts.Length);
                }
    
                return "1";
            }
            return "0";
        }

    二、

    1.通过FTP来上传文件

    首先,在另外一台服务器上设置好FTP服务,并创建好允许上传的用户和密码,然后,在ASP.NET里就可以直接将文件上传到这台 FTP 服务器上了。代码如下:

    <%@ Page Language="C#" EnableViewState="false"%>
    
    <%@ Import Namespace="System.Net" %>
    <%@ Import Namespace="System.IO" %>
    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
    "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    <script runat="server">
      protected void Button1_Click(object sender, EventArgs e)
      {
        //要接收文件的 ftp 服务器地址
        String serverUri = "ftp://192.168.3.1/";
        String fileName = Path.GetFileName(FileUpload1.FileName);
        serverUri += fileName;
    
    FtpWebRequest request = (FtpWebRequest)WebRequest.Create(serverUri);
    request.Method = WebRequestMethods.Ftp.AppendFile;
    request.UseBinary = true;
    request.UsePassive = true;
    
    // ftp 服务器上允许上传的用户名和密码
    request.Credentials = new NetworkCredential("upload""upload");
    Stream requestStream = request.GetRequestStream();
    Byte[] buffer = FileUpload1.FileBytes;
    
    requestStream.Write(buffer, 0, buffer.Length);
    requestStream.Close();
    FtpWebResponse response = (FtpWebResponse)request.GetResponse();
    Label1.Text = response.StatusDescription;
    response.Close();
    }
    </script>
    <html xmlns="http://www.w3.org/1999/xhtml">
    <head runat="server">
    <title>将文件上传到另外一个服务器的方法二</title>
    </head>
    <body>
    <form id="form1" runat="server">
    <asp:FileUpload ID="FileUpload1" runat="server" />
    <asp:Button ID="Button1" runat="server" OnClick="Button1_Click" Text="上传文件" />
    <div><asp:Label ID="Label1" runat="server" Text=""></asp:Label></div>
    </form>
    </body>
    </html> 

    2.通过WebClient来上传文件

    如:现在的开发的web应用程序的虚拟目录是WebAA,另一个应用程序的虚拟目录是WebBB,现在要从WebAA向WebBB下的一个UpLoadFiles文件夹下保存图片

    在WebBB项目下添加一个UploadHandler.ashx文件,代码如下:

    public class UploadHandler : IHttpHandler
    {
        public void ProcessRequest(HttpContext context)
        {
            string filename = context.Request.QueryString["filename"].ToString();
            using (FileStream inputStram = File.Create(context.Server.MapPath("UpLoadFiles/") + filename))
            {
                SaveFile(context.Request.InputStream, inputStram);
            }
    
        }
        protected void SaveFile(Stream stream, FileStream inputStream)
        {
    int bufSize=1024;
    int byteGet=0;
    byte[] buf=new byte[bufSize];
    while ((byteGet = stream.Read(buf, 0, bufSize)) > 0)
    {
    inputStream.Write(buf, 0, byteGet);
    }
    }
    public bool IsReusable
    {
    get
    {
    return false;
    }
    }
    } 

    在WebAA项目中通过WebClient或者WebRequest请求该url,下面以WebClient为例说明。 在WebAA中新建test.aspx页面,上面有FileUpload控件FileUpload1和Button控件Button1,具体事件代码如 下:

    using System.IO;
    using System.Net;
     
    MemoryStream ms;
    protected void wc_OpenWriteCompleted(object sender, OpenWriteCompletedEventArgs e)
    {
        int bufSize = 10;
        int byteGet = 0;
        byte[] buf = new byte[bufSize];
        while ((byteGet = ms.Read(buf, 0, bufSize)) > 0)//循环读取,上传
        {
            e.Result.Write(buf, 0, byteGet);//注意这里
        }
        e.Result.Close();//关闭
        ms.Close();关闭ms
    }
    protected void Button1_Click(object sender, EventArgs e)
    {
        FileUpload fi = FileUpload1;
     
        byte[] bt = fi.FileBytes;//获取文件的Byte[]
        ms = new MemoryStream(bt);//用Byte[],实例化ms
     
        UriBuilder url = new UriBuilder("http://xxxxxxxx/WebBB/UploadHandler.ashx");//上传路径
        url.Query = string.Format("filename={0}", Path.GetFileName(fi.FileName));//上传url参数
        WebClient wc = new WebClient();
        wc.OpenWriteCompleted += new OpenWriteCompletedEventHandler(wc_OpenWriteCompleted);//委托异步上传事件
        wc.OpenWriteAsync(url.Uri);//开始异步上传
    }

    3.通过Web Service来上传文件(与第二种其实原理有些相同)

    首先定义Web Service类,代码如下:

    using System;
    using System.Data;
    using System.Web;
    using System.Collections;
    using System.Web.Services;
    using System.Web.Services.Protocols;
    using System.ComponentModel;
    using System.IO;
     
    namespace UpDownFile
    {
        /**/
        /// <summary>
        /// UpDownFile 的摘要说明
        /// </summary>
        [WebService(Namespace = "http://tempuri.org/")]
        [WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
        [ToolboxItem(false)]
        public class UpDownFile : System.Web.Services.WebService
        {
            //上传文件至WebService所在服务器的方法,这里为了操作方法,文件都保存在UpDownFile服务所在文件夹下的File目录中
            [WebMethod]
            public bool Up(byte[] data, string filename)
            {
                try
                {
                    FileStream fs = File.Create(Server.MapPath("File/") + filename);
                    fs.Write(data, 0, data.Length);
                    fs.Close();
                    return true;
                }
                catch
                {
                    return false;
                }
            }
     
            //下载WebService所在服务器上的文件的方法
            [WebMethod]
            public byte[] Down(string filename)
            {
                string filepath = Server.MapPath("File/") + filename;
                if (File.Exists(filepath))
                {
                    try
                    {
                        FileStream s = File.OpenRead(filepath);
                        return ConvertStreamToByteBuffer(s);
                    }
                    catch
                    {
                        return new byte[0];
                    }
                }
                else
                {
                    return new byte[0];
                }
            }
        }
    }

    在网站中引用上述创建的WEB服务,命名为(UpDownFile,可自行定义),然后在页面DownFile.aspx中分别实现文件上传与下载:

    //上传:
     
    
                //FileUpload1是aspx页面的一个FileUpload控件
                UpDownFile.UpDownFile up = new UpDownFile.UpDownFile();
                up.Up(ConvertStreamToByteBuffer(FileUpload1.PostedFile.InputStream),
                FileUpload1.PostedFile.FileName.Substring(FileUpload1.PostedFile.FileName.LastIndexOf("\") + 1));
    
    //下载:
                UpDownFile.UpDownFile down = new UpDownFile.UpDownFile();
                byte[] file = down.Down(Request.QueryString["filename"].ToString()); //filename是要下载的文件路径,可自行以其它方式获取文件路径
                Response.BinaryWrite(file);
    
    //以下是将文件流转换成文件字节的函数(因为Stream类型的是不能直接通过WebService传输):
     protected byte[] ConvertStreamToByteBuffer(Stream s)
     {
        BinaryReader br = new BinaryReader(stream);
        byte[] fileBytes = br.ReadBytes((int)stream.Length);
        return fileBytes;
    }

    4.通过页面跳转或嵌套页面的方式(这种方法很简单,严格不算跨服务器,且有一定的局限性)

    实现方法:

    1.在需要上传文件的页面加入iframe,iframe的地址指向另一个服务器上传页面,并且页面需包含上传按钮;
    .需要上传时就利用JS的location.href或服务端的Response.redirect跳转至另一个服务器上传页面;

    方法其实还有多很,这里就不一一例举,当然上述方法只是实现上传与下载功能,有时可能还需考虑跨服务器删除文件,这个可能需要考虑安全等方面的问题。

    三、

    跨服务器上传,利用B.com的handler文件,先将文件进行编码,使用POST方式传递到handler,然后handler将文件保存到服务器上,同时返回相应的结果。
    将文件转为Base64:

    string fileName = FileUpload.FileName;
    FileInfo file = new FileInfo(fileName);
    string ext=file.Extension;
    Stream stream = FileUpload.PostedFile.InputStream;
    BinaryReader br = new BinaryReader(stream);
    byte[] fileByte = br.ReadBytes((int)stream.Length);
    string baseFileString = Convert.ToBase64String(fileByte);

    在handler.ashx中做处理:

    /// <summary>
    /// 上传图片
    /// </summary>
    [WebService(Namespace = "http://tempuri.org/")]
    [WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
    public class CrossServerFileUpload : IHttpHandler
    {
        private string _allowFileTypes = "gif,jpg,jpeg,png,bmp";
      
        private HttpContext _context;
        public void ProcessRequest(HttpContext context)
        {
            _context = context;
      
            string src = context.Request.Form["src"];
            if (string.IsNullOrEmpty(src)) return;
      
            src = src.ToLower();
            bool isExtValid = src.EndsWith(".jpg") || src.EndsWith(".png") || src.EndsWith(".gif") || src.EndsWith(".bmp") || src.EndsWith(".jpeg");
            if (isExtValid) {
                context.Response.ContentType = "text/plain";
                string ext = context.Request.Form["ext"];
                string content = context.Request.Form["data"];
      
                Upload(ext, content);
            }
        }
        /// <summary>
        /// 上传类
        /// </summary>
        /// <param name="ext"></param>
        /// <param name="content"></param>
        private void Upload(string ext,string content)
        {
            if (string.IsNullOrEmpty(ext) || string.IsNullOrEmpty(content)) {
                return;
            }
            //保存图片
            string dateNum = DateTime.Now.ToString("yyyyMM");//按月存放
            string fileName = Guid.NewGuid() + ext;
            string currentPath = HttpContext.Current.Request.PhysicalApplicationPath + "upload\" + dateNum + "\";
            string fullPath =currentPath  + fileName;
      
            if (!Directory.Exists(currentPath))
                Directory.CreateDirectory(currentPath);
      
            byte[] buffer = Convert.FromBase64String(content);
            using (FileStream fileStream = new FileStream(fullPath, FileMode.Create)) {
                fileStream.Write(buffer, 0, buffer.Length);
            }
            string host = _context.Request.Url.Host;
            ResponseWrite(string.Format("http://" + host + "/upload/{0}/{1}", dateNum, fileName));//返回图片保存路径
        }
        /// <summary>
        /// 生成http内容
        /// </summary>
        /// <param name="content"></param>
        private void ResponseWrite(string content)
        {
            _context.Response.ClearContent();
            _context.Response.ContentType = "text/plain";
            _context.Response.Write(content);
            _context.Response.End();
        }

    以上是跨服务器处理代码的核心代码,实际应用中还需要考虑权限问题。

    四、可以根据方法一 ,把二进制与字符串转换,在进行传输,这样更方便 加入 文字内容或多文件一起上传(图片转换)

    C#

    //将二进制文件转为Base64
    string baseFileString = Convert.ToBase64String(fileByte);
    //将Base64转为二进制文件
    byte[] buffer = Convert.FromBase64String(content);

    Server端

    string strFile = list.imgContent;
                //将图片字符串转化为2进制数组
                System.Text.UnicodeEncoding converter = new System.Text.UnicodeEncoding();
                byte[] byteImg = converter.GetBytes(strFile);
                //将图片的二进制数据转化为图片
                System.IO.MemoryStream ms = new System.IO.MemoryStream(byteImg);
                System.Drawing.Image img = System.Drawing.Image.FromStream(ms);
                string strSavePath = Server.MapPath("~") + "\images\" + DateTime.Now.ToString("yyyyMMddHHmmss") + ".jpg";
                img.Save(strSavePath, System.Drawing.Imaging.ImageFormat.Bmp);

    二进制与字符串转换--JAVA代码

    public class Test{
        public static void main(String[] args) {
            try{  
                
                // 将图片转换成字符串  
                File f = new File("c:\biao.png");  
                FileInputStream fis = new FileInputStream( f );  
                byte[] bytes = new byte[fis.available()];  
                fis.read(bytes);  
                fis.close();  
                  
                // 生成字符串  
                String imgStr = byte2hex( bytes );  
                System.out.println( imgStr);  
                  
                // 将字符串转换成二进制,用于显示图片  
                // 将上面生成的图片格式字符串 imgStr,还原成图片显示
                OutputStream o = new FileOutputStream("c:\878789.png");  
                byte[] imgByte = hex2byte( imgStr );  
                InputStream in = new ByteArrayInputStream( imgByte );  
                byte[] b = new byte[1024];  
                int nRead = 0;  
                while( ( nRead = in.read(b) ) != -1 ){  
                    o.write( b, 0, nRead );  
                }  
                o.flush();  
                o.close();  
                in.close();  
                  
                  
            }catch(Exception e){  
                e.printStackTrace();  
            }finally{  
            }  
        }
        /**
         * 二进制转字符串
         * @param b byte数组
         * @return 二进制字符串
         */
        public static String byte2hex(byte[] b){
            StringBuffer sb = new StringBuffer();
            String stmp = "";
            for (int n = 0; n < b.length; n++) {
                stmp = Integer.toHexString(b[n] & 0XFF);
                if (stmp.length() == 1) {
                    sb.append("0" + stmp);
                } else {
                    sb.append(stmp);
                }
            }
            return sb.toString();
        }
        /**
         * 字符串转二进制
         * @param str 字符串
         * @return byte数组
         */
        public static byte[] hex2byte(String str) {
            if (str == null)
                return null;
            str = str.trim();
            int len = str.length();
            if (len == 0 || len % 2 == 1)
                return null;
            byte[] b = new byte[len / 2];
            try {
                for (int i = 0; i < str.length(); i += 2) {
                    b[i / 2] = (byte) Integer.decode("0X" + str.substring(i, i + 2)).intValue();
                }
                return b;
            } catch (Exception e) {
                return null;
            }
        }
    }

      五、上传

    private void button1_Click(object sender, System.EventArgs e)
      {
       WebClient myWebClient = new WebClient();
       myWebClient.UploadFile("http://localhost/UploadFileWeb/WebForm1.aspx","POST",@"D:TempJavaJavaStartJavaStart2.exe");
           }

    六、其它案例详解C#

    http://blog.csdn.net/wangxiaona356/article/details/6753986

    七、JAVA经典案例

    1.安卓客户端JAVA上传文件到JAVA网站 https://github.com/kk-java/UploadFile

    2.安卓客户端JAVA上传文件到ASP.NET网站http://www.codicode.com/art/upload_files_from_android_to_a_w.aspx

    3.安卓客户端JAVA上传文件到JAVA网站http://www.cnblogs.com/gzggyy/archive/2011/08/02/2125237.html

    https://github.com/kk-java/UploadFile

  • 相关阅读:
    java.lang.UnsatisfiedLinkError: No implementation found for
    target release 1.5 conflicts with default source release 1.7
    (转)makefile里PHONY的相关介绍
    Hint: A potential Change-Id was found, but it was not in the footer (last paragraph) of the commit message
    linux jdk版本随时切换
    提高Service的优先级
    第一章、数字图像的描述
    gluas图形处理——导读
    图像处理学习过程——网站,视频,书籍(长期更新)
    基数排序
  • 原文地址:https://www.cnblogs.com/elves/p/4530486.html
Copyright © 2020-2023  润新知