asp.net core webapi文件上傳功能的實現

最近開發一個新項目,使用瞭asp.net core 2.0,采用webapi開發後臺,postgresql為數據庫。最先來的問題就是上傳文件的問題。

POST文件的一些坑

使用默認模板創建webapi的controller後,post請求,默認有

 // POST api/values
  [HttpPost]
  public void Post([FromBody]string value)
  {
  }

請求使用瞭[FromBody]標記,用來指示用請求體裡獲得數據。

對於文件上傳請求,直接在這個Post函數裡使用Request.Form.Files是不行的,無法成功路由。
典型上傳,需要設置前端發送的請求Content-Typemultipart/form-data,然後在控制器類加上特性修飾:

 [Produces("application/json")]
 [Consumes("application/json", "multipart/form-data")]//此處為新增
 [Route("api/[controller]")]
 public class FileController : Controller

指示該controller能夠接受multipart/form-data形式的數據。對應的,修改post的代碼如下:

 // POST: api/File
  [HttpPost]
  public Task<ActionResult> Post(IFormCollection files)

這裡需要註意,使用的是IFormCollection。這是IForm的類型集合,實際上就是Request.Form

註意,很多地方寫瞭可以使用IFormFile,直接寫成

// POST: api/File
  [HttpPost]
  public Task<ActionResult> Post(IFormFile file)

實際測試沒有辦法獲取到對象,file常態為null,或者是我方法不對。

然後就可以在post方法裡面使用files.Files來枚舉文件瞭,每個文件都是一個IFormFile對象,可以靈活使用FileName, Name,Length等常用屬性。當然,我們也可以不帶參數:

// POST: api/File
  [HttpPost]
  public Task<ActionResult> Post()

直接使用Request.Form.Files獲得文件數據。

P.S. 對於IFormFile,與System.IO.File對象不同,IFormFile缺少很多方法,隻提供OpenReadStream()方法,該方法返回一個stream對象。很多讀文件的API都可以接受stream作為FilePath的替代。

同時上傳其他數據

一般的文件上傳請求,不單上傳文件數據,通常還需要上傳其他文件信息數據(比如文件類型,上傳者等等)。修改一下post方法,改成這樣:

 [HttpPost]
  public Task<ActionResult> Post([FromBody]string type,IFormCollection files)

將type都打包進請求,再次發送。發現……type是null。

MSDN說瞭,The reason for this rule is that the request body might be stored in a non-buffered stream that can only be read once.

所以,[FromBody]隻能加一個,但是我這確實也隻加瞭一個,有問題?很明顯,那個IFormCollection也是默認通過[FromBody]解析的,所以正確的方法是不加[FromBody]瞭。

 [HttpPost]
  public Task<ActionResult> Post(string type,IFormCollection files)

後記

回想起當年做WebService的時候,上傳文件寫的
多平臺上傳
,感觸頗多,以前是轉碼到base64,通過string發送,現在是直接類型識別…

到此這篇關於asp.net core webapi文件上傳的文章就介紹到這瞭,更多相關asp.net core webapi文件上傳內容請搜索WalkonNet以前的文章或繼續瀏覽下面的相關文章希望大傢以後多多支持WalkonNet!

推薦閱讀: