bad*_*mar 9 .net asp.net file-upload multipartform-data task-parallel-library
我有一个POST ASP.Net Web Api方法,它改编自ASP.NET Web API RTM中的异步文件上传指南.
我遇到了故障任务问题,在第一个请求被触发并完成后触发了所有请求.
这是一个场景:我有一个示例页面,它将文件和其他参数一起发布到Web API Post方法.它第一次工作正常,文件上传.但是,所有后续请求都会在故障状态下结束任务.我得到"MIME多部分流的意外结束.MIME多部分消息不完整."任何想法为什么?
下面粘贴的是我的Post方法的源代码,示例html表单和Aggregate Exception.
public Task<HttpResponseMessage> Post([FromUri]string memberNumber)
{
// Check if the request contains multipart/form-data.
if (!Request.Content.IsMimeMultipartContent())
{
throw new HttpResponseException(HttpStatusCode.UnsupportedMediaType);
}
string root = HttpContext.Current.Server.MapPath("~/App_Data");
var provider = new MultipartFormDataStreamProvider(root);
// Read the form data and return an async task.
var task = Request.Content.ReadAsMultipartAsync(provider).
ContinueWith(t =>
{
if (t.IsFaulted || t.IsCanceled)
{
throw new HttpResponseException(Request.CreateErrorResponse(HttpStatusCode.InternalServerError, t.Exception));
}
return Request.CreateResponse(HttpStatusCode.OK, new MyModel());
});
return task;
}
Run Code Online (Sandbox Code Playgroud)
我正在使用这样的示例表单来触发此web api:
<form name="form1" method="post" enctype="multipart/form-data" action="api/claims/asd123" style="margin:auto;width:500px;">
<div>
<label for="HCPracticeNumber">HC Pratice Number:</label>
<input type="text" name="HCPracticeNumber" id="HCPracticeNumber"/>
</div>
<div>
<label for="ServiceDate">Service/Treatment date:</label>
<input type="text" name="ServiceDate" id="ServiceDate"/>
</div>
<div>
<label for="AmountClaimed">Amount Claimed:</label>
<input type="text" name="AmountClaimed" id="AmountClaimed"/>
</div>
<div>
<label for="Image">Image Attachment:</label>
<input name="Image" type="file" />
</div>
<div>
<input type="submit" value="Submit" />
</div>
</form>
Run Code Online (Sandbox Code Playgroud)
返回的AggregateException如下:
<Error>
<Message>An error has occurred.</Message>
<ExceptionMessage>One or more errors occurred.</ExceptionMessage>
<ExceptionType>System.AggregateException</ExceptionType>
<StackTrace/>
<InnerException>
<Message>An error has occurred.</Message>
<ExceptionMessage>
Unexpected end of MIME multipart stream. MIME multipart message is not complete.
</ExceptionMessage>
<ExceptionType>System.IO.IOException</ExceptionType>
<StackTrace>
at System.Net.Http.Formatting.Parsers.MimeMultipartBodyPartParser.<ParseBuffer>d__0.MoveNext() at System.Net.Http.HttpContentMultipartExtensions.MoveNextPart(MultipartAsyncContext context)
</StackTrace>
</InnerException>
</Error>
Run Code Online (Sandbox Code Playgroud)
更新:
在Filip在他的博客网站上提出建议后,我修改了post方法,将流位置重置为0,如下所示:
Stream reqStream = Request.Content.ReadAsStreamAsync().Result;
if (reqStream.CanSeek)
{
reqStream.Position = 0;
}
var task = Request.Content.ReadAsMultipartAsync(provider).
ContinueWith(t =>
{
if (t.IsFaulted || t.IsCanceled)
{
throw new HttpResponseException(
Request.CreateErrorResponse(HttpStatusCode.InternalServerError,
t.Exception));
}
return Request.CreateResponse(HttpStatusCode.OK, new MyModel());
});
Run Code Online (Sandbox Code Playgroud)
但是,这是非常有气质的代码.它的工作有时它不会在其他时间.换句话说,它并没有完全解决问题.
bad*_*mar 14
事实证明,正如Filip在评论中所建议的那样,我改编自实现消息处理程序以跟踪您的ASP .net Web API用法的Web API使用处理程序正在读取内容正文,因此当流程中的位置搜索器搞乱时请求正在我的POST方法中处理.
因此,如果请求的类型为IsMimeMultipartContent,我向WebApiUsageHandler添加了一个条件语句,以便不读取请求体.这解决了这个问题.
更新
我想用Filip通过电子邮件向我建议的另一个选项更新答案,以便记录:
如果您在API使用处理程序中使用此代码,则在读取正文之前:
//read content into a buffer
request.Content.LoadIntoBufferAsync().Wait();
request.Content.ReadAsStringAsync().ContinueWith(t =>
{
apiRequest.Content = t.Result;
_repo.Add(apiRequest);
});
Run Code Online (Sandbox Code Playgroud)
请求将被缓冲,并且可以读取两次,因此可以在管道中进一步上传.希望这可以帮助.
| 归档时间: |
|
| 查看次数: |
22387 次 |
| 最近记录: |