2015-06-23 108 views
5

我想使用HTTP PUT動詞來公開一個ASP.Net Web Api 2操作來上傳文件。這與我們的REST模型是一致的,因爲API表示遠程文件系統(類似於WebDAV,但非常簡化),所以客戶端選擇資源名稱(因此PUT是理想的,POST不是合理的選擇)。在ASP.Net Web Api中使用PUT動詞上傳文件2

Web Api文檔描述了how to upload files using multipart/form-data forms,但沒有描述如何使用PUT方法來完成它。

你會用什麼來測試這樣一個API(HTML多部分表單不允許PUT動詞)?將在服務器上執行看起來像the web api documentation描述(使用MultipartStreamProvider)的多執行,還是應該是這樣的:

[HttpPut] 
public async Task<HttpResponseMessage> PutFile(string resourcePath) 
{ 
    Stream fileContent = await this.Request.Content.ReadAsStreamAsync(); 
    bool isNew = await this._storageManager.UploadFile(resourcePath, fileContent); 
    if (isNew) 
    { 
     return this.Request.CreateResponse(HttpStatusCode.Created); 
    } 
    else 
    { 
     return this.Request.CreateResponse(HttpStatusCode.OK); 
    } 
} 

回答

8

經過幾次測試中,它似乎在服務器端代碼我張貼作爲一個例子是正確的。下面是一個例子,剝離出來的任何身份驗證/授權/錯誤處理代碼:

[HttpPut] 
[Route(@"api/storage/{*resourcePath?}")] 
public async Task<HttpResponseMessage> PutFile(string resourcePath = "") 
{ 
    // Extract data from request 
    Stream fileContent = await this.Request.Content.ReadAsStreamAsync(); 
    MediaTypeHeaderValue contentTypeHeader = this.Request.Content.Headers.ContentType; 
    string contentType = 
     contentTypeHeader != null ? contentTypeHeader.MediaType : "application/octet-stream"; 

    // Save the file to the underlying storage 
    bool isNew = await this._dal.SaveFile(resourcePath, contentType, fileContent); 

    // Return appropriate HTTP status code 
    if (isNew) 
    { 
     return this.Request.CreateResponse(HttpStatusCode.Created); 
    } 
    else 
    { 
     return this.Request.CreateResponse(HttpStatusCode.OK); 
    } 
} 

一個簡單的控制檯應用程序就夠了(使用Web API客戶端庫)來測試它:

using (var fileContent = new FileStream(@"C:\temp\testfile.txt", FileMode.Open)) 
using (var client = new HttpClient()) 
{ 
    var content = new StreamContent(fileContent); 
    content.Headers.ContentType = new MediaTypeHeaderValue("text/plain"); 
    client.BaseAddress = new Uri("http://localhost:81"); 
    HttpResponseMessage response = 
     await client.PutAsync(@"/api/storage/testfile.txt", content); 
} 
+1

這將是有趣的是看看如何爲此編寫適當的單元測試,而不是依靠運行HTTP Server。 – James

+0

因爲我一直在收到404錯誤,所以我得到了很多的麻煩。原來你可能需要改變web.config來接受'{filename}。{extension}'形式的文件名。有關詳細信息,請參閱此Stackoverflow問題:http://stackoverflow.com/questions/20998816/dot-character-in-mvc-web-api-2-for-request-such-as-api-people-staff-45287 –