将文件从ASP.NET Core web api发布到另一个ASP.NET Core web api

Dav*_*ave 14 c# asp.net asp.net-core

我们正在构建一个Web应用程序,它包含一个Angular2前端,一个ASP.NET Core web api公共后端和一个ASP.NET Core web api私有后端.

将文件从Angular2上传到公共后端的工作原理.但我们更愿意将它们发布到私有后端.

当前的工作代码

[HttpPost]
public StatusCodeResult Post(IFormFile file)
{
  ...
}
Run Code Online (Sandbox Code Playgroud)

从那里我可以使用file.CopyTo(fileStream)将文件保存到磁盘;

但是,我想重新发送该文件或那些文件,或者理想情况下,将整个请求发送到我的第二个web api核心.

我不知道如何使用asp.net核心的HttpClient类来实现这一点.

我尝试过各种各样的事情

StreamContent ss = new StreamContent(HttpContext.Request.Body);
var result = client.PostAsync("api/Values", ss).Result;
Run Code Online (Sandbox Code Playgroud)

但我的第二个后端得到一个空的IFormFile.

我有一种感觉,可以将文件作为流发送并在另一侧重建它们,但无法使其工作.

解决方案必须使用两个web api核心.

Dav*_*ave 19

DMZ的公共后端

[HttpPost]
public StatusCodeResult Post(IFormFile file)
{
    try
    {
        if (file != null && file.Length > 0)
        {
            using (var client = new HttpClient())
            {
                try
                {
                    client.BaseAddress = new Uri(currentPrivateBackendAddress);

                    byte[] data;
                    using (var br = new BinaryReader(file.OpenReadStream()))
                        data = br.ReadBytes((int)file.OpenReadStream().Length);

                    ByteArrayContent bytes = new ByteArrayContent(data);


                    MultipartFormDataContent multiContent = new MultipartFormDataContent();

                    multiContent.Add(bytes, "file", file.FileName);

                    var result = client.PostAsync("api/Values", multiContent).Result;


                    return StatusCode((int)result.StatusCode); //201 Created the request has been fulfilled, resulting in the creation of a new resource.

                }
                catch (Exception)
                {
                    return StatusCode(500); // 500 is generic server error
                }
            }
        }

        return StatusCode(400); // 400 is bad request

    }
    catch (Exception)
    {
        return StatusCode(500); // 500 is generic server error
    }
}
Run Code Online (Sandbox Code Playgroud)

私人后端

[HttpPost]
public void Post()
{
    //Stream bodyStream = HttpContext.Request.Body;

    if (Request.HasFormContentType)
    {
        var form = Request.Form;
        foreach (var formFile in form.Files)
        {
            var targetDirectory = Path.Combine(_appEnvironment.WebRootPath, "uploads");

            var fileName = GetFileName(formFile);

            var savePath = Path.Combine(targetDirectory, fileName);

            using (var fileStream = new FileStream(savePath, FileMode.Create))
            {
                formFile.CopyTo(fileStream);
            }                   
        }
    }          
}
Run Code Online (Sandbox Code Playgroud)

  • 这个解决方案并不是那么好,因为你在公共后端的内存中加载了整个东西 - 想象一下,如果你的文件超过了你的 RAM 可以容纳...... (4认同)

min*_*elf 6

嗨,我遇到了同样的问题,这对我有用:

我的设置是netCore MVC netCoreApi。

我的MVC控制器看起来像:

[HttpPost("UploadFiles")]
public async Task<IActionResult> Post(List<IFormFile> files)
{
    Sp4RestClient dataPovider = new Sp4RestClient("http://localhost:60077/");

    long size = files.Sum(f => f.Length);

    foreach (var file in files)
    {
       await dataPovider.ImportFile(file);
    }

    return Ok();
}
Run Code Online (Sandbox Code Playgroud)

DataProvider方法:

public async Task ImportFile(IFormFile file)
    {
        RestClient restClient = new RestClient(_queryBulder.BuildImportFileRequest());

        using (var content = new MultipartFormDataContent())
        {
            content.Add(new StreamContent(file.OpenReadStream())
            {
                Headers =
                {
                    ContentLength = file.Length,
                    ContentType = new MediaTypeHeaderValue(file.ContentType)
                }
            }, "File", "FileImport");

            var response = await restClient.Post<IFormFile>(content);
        }
    }
Run Code Online (Sandbox Code Playgroud)

至少我的WebApi控制器:

[HttpPost]
[Route("ImportData")]
public IActionResult Import(IFormFile file)
{         
    return Ok();
}
Run Code Online (Sandbox Code Playgroud)

要查看完整的代码,请参见我的RestClient Post方法:

public async Task<RestResult<T>> Post<T>(HttpContent content)
    {
        using (HttpClient httpClient = new HttpClient())
        {
            HttpResponseMessage response = await httpClient.PostAsync(Endpoint, content);
            if (response.StatusCode == HttpStatusCode.Created)
            {
                T result = JsonConvert.DeserializeObject<T>(await response.Content.ReadAsStringAsync());
                return new RestResult<T> { Result = result, ResultCode = HttpStatusCode.OK };
            }
            RestResult<T> nonOkResult =
                new RestResult<T> { Result = default(T), ResultCode = response.StatusCode, Message = await response.Content.ReadAsStringAsync() };
            return nonOkResult;
        }
    }
Run Code Online (Sandbox Code Playgroud)

//是的,我知道我没有收到HttpStatusCode.Created返回;)

快乐的编码;)