ASP.NET Core实现图片上传下载时出现60%-80%数据缺失问题求解
问题原因
你遇到的图片缺失问题核心出在上传接口读取请求体的逻辑漏洞:
HttpContext.Request.Body是网络流,Stream.ReadAsync的返回值代表本次调用实际读取到的字节数,它不保证一次性读完和缓冲区长度相等的全部数据。网络请求的数据通常分多个数据包到达,单次调用ReadAsync往往只能读到第一批到达的部分数据,剩余未读到的字节在数组中默认是0值,所以最终缓存的图片数据不完整。- 额外风险:如果上传请求的
ContentLength被篡改或者和实际数据不一致,也会导致数组长度不对,进一步加剧数据错误。
解决方案
推荐直接使用MemoryStream的CopyToAsync方法读取全部流数据,无需手动处理循环读取的逻辑,框架会自动处理流的完整读取:
[Route("image")] public class CameraController : ControllerBase { private static byte[] latestImageData; [HttpPost("upload")] public async Task<ActionResult> PostData() { if(HttpContext.Request.ContentType == "image/jpeg") { using var ms = new MemoryStream(); await HttpContext.Request.Body.CopyToAsync(ms); latestImageData = ms.ToArray(); } return NoContent(); } [ResponseCache(Duration = 0, Location = ResponseCacheLocation.None, NoStore = true)] [HttpGet("get")] public ActionResult GetImage() { if (latestImageData != null) { return File(latestImageData, "image/jpeg"); } return NoContent(); } }
如果要保留手动读取的逻辑,就需要循环调用ReadAsync直到读满指定长度:
var contentLength = Convert.ToInt32(HttpContext.Request.ContentLength); latestImageData = new byte[contentLength]; int totalRead = 0; while (totalRead < contentLength) { int read = await HttpContext.Request.Body.ReadAsync(latestImageData.AsMemory(totalRead, contentLength - totalRead)); if (read == 0) break; // 流提前结束可自行补充异常处理逻辑 totalRead += read; }
内容的提问来源于stack exchange,提问作者Felix
相关产品推荐
相关产品推荐

