. net core webapi + Axios + Vue to realize download and download progress bar

Time:2021-1-19

The beginning of the story

The boss said: the system is very slow and can’t be downloaded for half an hour. Do you want to consider compressing it first and then downloading it to users?

                     

 

Originally, it has been compressed, but the first reaction should be that there are a large number of users, resulting in a large number of compressed packages. Then I found out in my own test that it was just waiting for a long time, and it was still in the download state, not that the system was slow, but the user experience must be the most intuitive. It was really that we did not do well enough, just pop up the mask layer to show the cold “desperately loading” ……” It’s not friendly enough for users. Well, if you know the actual situation, you can start to improve the user experience.

Solve it

design sketch:

 

 

Vue+ElementUI

Axios

downloadTask(index,row) {
      let own =this;
      this.fullscreenLoading = true;
      this.axios({
        method: 'post',
        url: this.baseUrl + '/api/Task/DownLoad',
        data: {id: row.id},
        Responsetype: 'blob' // knock on the blackboard
        onDownloadProgress (progress) {
          own.dlProgress=Math.round(progress.loaded / progress.total * 100);
        }
      })
      .then((res) => {
        this.fullscreenLoading = false;
        let fileName = decodeURI(res.headers["content-disposition"].split("=")[1]);
        let url = window.URL.createObjectURL(new Blob([res.data]));
        let link = document.createElement('a');
        link.style.display = 'none';
        link.href = url;
        link.setAttribute('download', fileName);
        document.body.appendChild(link);
        link.click();     document.body.removeChild(link); 
        this.$ message.success ('download successful ');
      })
      .catch(() => {
        this.fullscreenLoading = false;
      });
    },

Download:

Fragment Download

. net core webapi + Axios + Vue to realize download and download progress bar. net core webapi + Axios + Vue to realize download and download progress bar

public static class HttpContextExtension
    {
        /// 
        ///Get customer IP
        /// 
        /// 
        /// 
        public static string GetClientUserIp(this HttpContext context)
        {
            var ip = "";
            if (context.Request.Headers.ContainsKey("X-Forwarded-For"))
            {
                ip = context.Request.Headers["X-Forwarded-For"].ToString();
            }
            if (string.IsNullOrEmpty(ip) && context.Request.Headers.ContainsKey("X-Real-IP"))
            {
                ip = context.Request.Headers["X-Real-IP"].ToString();
            }
            if (string.IsNullOrEmpty(ip))
            {
                ip = context.Connection.RemoteIpAddress.MapToIPv4().ToString();
            }
            if (string.IsNullOrEmpty(ip))
                return ip;
            var sp = ip.RemoveSpacing().Split(',');
            return sp[0];
        }

        /// 
        ///Download files through file stream
        /// 
        /// 
        ///File full path
        ///Visit here https://tool.oschina.net/commons 
        public static void DownLoadFile(this HttpContext context,string filePath, string contentType= "application/octet-stream")
        {
            var fileName = Path.GetFileName(filePath);

            int bufferSize = 1024; 
            context.Response.ContentType = contentType;
            context.Response.Headers.Append("Content-Disposition", "attachment;filename=" + HttpUtility.UrlEncode(fileName));
            context.Response.Headers.Append("Charset", "utf-8");
            context.Response.Headers.Append("Access-Control-Expose-Headers", "Content-Disposition");
            //context.Response.Headers.Append("Access-Control-Allow-Origin", "*");
            //Use the file stream to start the loop to read the contents of the file to be downloaded
            using (FileStream fs = new FileStream(filePath, FileMode.Open, FileAccess.Read))
            {
                using (context.Response.Body) 
                {
                    long contentLength = fs.Length; 
                    context.Response.ContentLength = contentLength;

                    byte[] buffer;
                    long hasRead = 0;  
                    while (hasRead < contentLength)
                    {
                        if (context.RequestAborted.IsCancellationRequested)
                        {
                            break;
                        }

                        buffer = new byte[bufferSize];
                        //Read the buffer size (1024 bytes) from the download file into the server memory
                        int currentRead = fs.Read(buffer, 0, bufferSize);
                        context.Response.Body.Write(buffer, 0, currentRead);
                        context.Response.Body.Flush();
                        hasRead += currentRead;
                    }
                    context.Response.Body.Close();
                }
                fs.Close();
            }
        }

        /// 
        ///Download files through file stream
        /// 
        /// 
        ///File full path
        ///Visit here https://tool.oschina.net/commons 
        public static void DownLoadFile(this HttpContext context,string fileName, byte[] fileByte, string contentType = "application/octet-stream")
        {
            int bufferSize = 1024;
            
            context.Response.ContentType = contentType;
            context.Response.Headers.Append("Content-Disposition", "attachment;filename=" + HttpUtility.UrlEncode(fileName));
            context.Response.Headers.Append("Charset", "utf-8");
            context.Response.Headers.Append("Access-Control-Expose-Headers", "Content-Disposition");
         
            //context.Response.Headers.Append("Access-Control-Allow-Origin", "*");
            //Use the file stream to start the loop to read the contents of the file to be downloaded
            using (Stream fs = new MemoryStream(fileByte))
            {
                using (context.Response.Body)
                {
                    long contentLength = fs.Length;
                    context.Response.ContentLength = contentLength;

                    byte[] buffer;
                    long hasRead = 0;
                    while (hasRead < contentLength)
                    {
                        if (context.RequestAborted.IsCancellationRequested)
                        {
                            break;
                        }
                        
                        buffer = new byte[bufferSize];
                        //Read the buffer size (1024 bytes) from the download file into the server memory
                        int currentRead = fs.Read(buffer, 0, bufferSize);
                        context.Response.Body.Write(buffer, 0, currentRead);
                        context.Response.Body.Flush();
                        hasRead += currentRead;
                    }
                }
            }
        }
    }

View Code

Perfect~