Как отправлять большие файлы в и из ядра dotnet без использования системной памяти - PullRequest
1 голос
/ 15 мая 2019

Я пытаюсь загрузить большие файлы в API из интерфейса ядра dotnet.

Я пытался использовать код от Microsoft здесь https://docs.microsoft.com/en-us/aspnet/core/mvc/models/file-uploads?view=aspnetcore-2.2, но они используют угловой, и я хочучтобы сделать это изнутри .net core httpclient.

У меня все работает, но загрузка использует память системы и не освобождает ее.Я могу ожидать файлы размером несколько ГБ

Мой код выглядит следующим образом.

У меня есть http-клиент, который выглядит примерно так

public async Task<UploadModel> UploadFileAsync(Stream fileStream, string param1, string param2)
        {
            var uri = new Uri("upload", UriKind.Relative);

            try
            {               

                var ch = GetClaimsMessageProcessor();

                var fileStreamContent = new StreamContent(fileStream);

                using (var mfdContent =
             new MultipartFormDataContent("Upload----" + DateTime.Now.ToString()))
                {
                    mfdContent.Add(fileStreamContent);

                    var response = await _restClient.PostAsync(uri, mfdContent, callbacks: new Action<HttpRequestMessage>[] { ch.AddClaims,
                       (x) => {
                           x.Headers.Add("param1",param1);
                           x.Headers.Add("param2",param1);
                        } });

                    var content = await response.Content.ReadAsStringAsync();

                    if (!response.IsSuccessStatusCode)
                    {
                        // log and throw exception etc
                    }

                    return JsonConvert.DeserializeObject<UploadModel>(content);
                }
            }
            catch (Exception e)
            {
                // log etc
            }
        }

И мой API выглядит примерно так

[HttpPost("upload")]
        [Filters.DisableFormValueModelBinding]
        public async Task<IActionResult> Upload()
        {

            if (!MultipartRequestHelper.IsMultipartContentType(Request.ContentType))
            {
                return BadRequest($"Expected a multipart request, but got {Request.ContentType}");
            }

            // Get Header Parameters
            string param1, param2;

            try
            {
                param1 = Request.Headers["param1"][0];
                param2 = Request.Headers["param2"][0];
            }
            catch (Exception e)
            {
                // log and throw exception
            }          

            var filePath = GetFilePath();

            if (!Directory.Exists(filePath))
            {
                Directory.CreateDirectory(filePath);
            }

            var targetFilePath = Path.Combine(filePath , GetFileName());


            var boundary = MultipartRequestHelper.GetBoundary(
                MediaTypeHeaderValue.Parse(Request.ContentType),
                _defaultFormOptions.MultipartBoundaryLengthLimit);
            var reader = new MultipartReader(boundary, HttpContext.Request.Body);

            var section = await reader.ReadNextSectionAsync();
            while (section != null)
            {
                using (var targetStream = System.IO.File.Create(targetFilePath))
                {
                    await section.Body.CopyToAsync(targetStream);
                }

                section = await reader.ReadNextSectionAsync();
            }

            // Validate 

            // Do stuff with uploaded file
            var model = new UploadedModel
            {
                //some properties
            };

            return Ok(model);
        }

Я заметил, что есть только один разделчитать.Я бы предположил, что должно быть несколько?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...