【问题标题】:How to get % of data uploaded to server如何获取上传到服务器的数据百分比
【发布时间】:2020-06-22 07:46:19
【问题描述】:

我有一个包含以下参数的模型

 public class FileExchangeDetails
{
    public Guid SenderId { get; set; }
  
    public List<Files> Files { get; set; }

    public Guid Id { get; set; }
}

public class Files
{
    public string FilePath { get; set; }

    public string FileName { get; set; }

    public byte[] FileBytes { get; set; }

    public string FileType { get; set; }
}

我正在使用FileExchangeDetails 发送文件数据(图像或文件)

 public static async Task<string> PostFilesToToApi(string apiUrl, FileExchangeDetails exchangeDetails)
    {
        

        try
        {
            
            using (var httpreqclient = new httpclient())
            {
                httpreqclient.baseaddress = new uri(string.format(apiurls.weburl, application.current.properties["currentsitename"]));

                httpreqclient.defaultrequestheaders.add("authorization", "bearer " + applicationcontext.accesstoken);

                httpreqclient.defaultrequestheaders.accept.add(new mediatypewithqualityheadervalue("application/json"));//accept header

                var content = jsonconvert.serializeobject(exchangedetails, formatting.none);

                var stringcontentinput = new stringcontent(content, encoding.utf8, "application/json");

                var response = await httpreqclient.postasync(new uri(string.format(apiurls.weburl, application.current.properties["currentsitename"]) + apiurl), stringcontentinput);

                var stringasync = await response.content.readasstringasync();

                if (response.issuccessstatuscode)
                {
                    var responsejson = stringasync;

                    return responsejson;
                }
            }
        }
        catch (Exception exception)
        {
            LoggingManager.Error(exception, "PostFilesToToApi", "ApiWrapper");
        }

        return null;
    }

功能上一切正常,但现在我需要在上传到服务器时显示文件上传的百分比。

我对 web 客户端几乎没有指导方针,但参数只有字节 [] 或字符串。

如何使用 httpclient 获取该 % 数据。有人可以帮我解决这个问题吗?

【问题讨论】:

    标签: file xamarin.forms file-upload


    【解决方案1】:

    您可以创建一个自定义 HttpContent,如下所示

    internal class ProgressableStreamContent : HttpContent
    {
        private const int defaultBufferSize = 4096;
    
        private Stream content;
        private int bufferSize;
        private bool contentConsumed;
        private Download downloader;
    
        public ProgressableStreamContent(Stream content, Download downloader) : this(content, defaultBufferSize, downloader) {}
    
        public ProgressableStreamContent(Stream content, int bufferSize, Download downloader)
        {
            if(content == null)
            {
                throw new ArgumentNullException("content");
            }
            if(bufferSize <= 0)
            {
                throw new ArgumentOutOfRangeException("bufferSize");
            }
    
            this.content = content;
            this.bufferSize = bufferSize;
            this.downloader = downloader;
        }
    
        protected override Task SerializeToStreamAsync(Stream stream, TransportContext context)
        {
            Contract.Assert(stream != null);
    
            PrepareContent();
    
            return Task.Run(() =>
            {
                var buffer = new Byte[this.bufferSize];
                var size = content.Length;
                var uploaded = 0;
    
                downloader.ChangeState(DownloadState.PendingUpload);
    
                using(content) while(true)
                {
                    var length = content.Read(buffer, 0, buffer.Length);
                    if(length <= 0) break;
    
                    downloader.Uploaded = uploaded += length;
    
                    stream.Write(buffer, 0, length);
    
                    downloader.ChangeState(DownloadState.Uploading);
                }
    
                downloader.ChangeState(DownloadState.PendingResponse);
            });
        }
    
        protected override bool TryComputeLength(out long length)
        {
            length = content.Length;
            return true;
        }
    
        protected override void Dispose(bool disposing)
        {
            if(disposing)
            {
                content.Dispose();
            }
            base.Dispose(disposing);
        }
    
    
        private void PrepareContent()
        {
            if(contentConsumed)
            {
                // If the content needs to be written to a target stream a 2nd time, then the stream must support
                // seeking (e.g. a FileStream), otherwise the stream can't be copied a second time to a target 
                // stream (e.g. a NetworkStream).
                if(content.CanSeek)
                {
                    content.Position = 0;
                }
                else
                {
                    throw new InvalidOperationException("SR.net_http_content_stream_already_read");
                }
            }
    
            contentConsumed = true;
        }
    }
    

    参考:C#: HttpClient, File upload progress when uploading multiple file as MultipartFormDataContent

    【讨论】:

    • 感谢@Lucas Zhang - MSFT 的回复,我会试试这个。
    猜你喜欢
    • 2021-02-02
    • 1970-01-01
    • 2015-06-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-21
    • 2014-12-16
    相关资源
    最近更新 更多