使用 HttpClient 在发布到 Web API 时收到空值
received null value in Posting to a Web API using HttpClient
我尝试向服务器发送一个对象,但我意识到如果我的对象大于大约 250 Kb 服务器接收到的对象是 null
。
我在 asp web api
中的 Post 操作
// POST: api/ImagesModels
[ResponseType(typeof(ImagesModel))]
public IHttpActionResult PostImagesModel(ImagesModel imagesModel)
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState);
}
db.ImagesModels.Add(imagesModel);
db.SaveChanges();
return CreatedAtRoute("DefaultApi", new { id = imagesModel.ID }, imagesModel);
}
和我的上传方法在UWP
private async void Upload_image(object sender, RoutedEventArgs e)
{
ImagesModel model = new ImagesModel();
model.CategoryId = Convert.ToInt32(catgoryIdtxb.Text);
model.IsNew = true;
model.IsPayed = IsPayedchbx.IsChecked.Value;
model.Name = ImageNameTxb.Text;
model.PixelHeight = _imagePicWB.PixelHeight;
model.PixelWidth = _imagePicWB.PixelWidth;
model.ThumbnailPixelHeight = _imageThumWB.PixelHeight;
model.ThumbnailPixelWidth = _imageThumWB.PixelWidth;
model.Date = ImadeDate.Date.Date;
using (Stream stream = _imagePicWB.PixelBuffer.AsStream())
{
using (MemoryStream memoryStream = new MemoryStream())
{
stream.CopyTo(memoryStream);
model.Picture = memoryStream.ToArray();
}
}
using (Stream stream = _imageThumWB.PixelBuffer.AsStream())
{
using (MemoryStream memoryStream = new MemoryStream())
{
stream.CopyTo(memoryStream);
model.Thumbnail = memoryStream.ToArray();
}
}
httpClient = new HttpClient();
httpClient.BaseAddress = new Uri("http://localhost:33134/");
httpClient.DefaultRequestHeaders.Accept.Clear();
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/bson"));
MediaTypeFormatter bsonFormatter = new BsonMediaTypeFormatter();
HttpResponseMessage response = await httpClient.PostAsync("api/ImagesModels", model, bsonFormatter);
response.EnsureSuccessStatusCode();
}
并且我试图在 web.config
中增加 maxAllowedContentLength
的限制
<system.webServer>
<security>
<requestFiltering>
<requestLimits maxAllowedContentLength="2147483648" />
</requestFiltering>
</security>
</system.webServer>
注意:我使用 visual studio 2015
maxAllowedContentLength 是一个 32 位整数,因此最大值应该是 2,147,483,647 而不是 2,147,483,648
private async void Upload_image(object sender, RoutedEventArgs e)
{
ImagesModel model = new ImagesModel();
model.CategoryId = Convert.ToInt32(catgoryIdtxb.Text);
model.IsNew = true;
model.IsPayed = IsPayedchbx.IsChecked.Value;
model.Name = ImageNameTxb.Text;
model.PixelHeight = _imagePicWB.PixelHeight;
model.PixelWidth = _imagePicWB.PixelWidth;
model.ThumbnailPixelHeight = _imageThumWB.PixelHeight;
model.ThumbnailPixelWidth = _imageThumWB.PixelWidth;
model.Date = ImadeDate.Date.Date;
using (Stream stream = _imagePicWB.PixelBuffer.AsStream())
{
using (MemoryStream memoryStream = new MemoryStream())
{
stream.CopyTo(memoryStream);
model.Picture = memoryStream.ToArray();
}
}
using (Stream stream = _imageThumWB.PixelBuffer.AsStream())
{
using (MemoryStream memoryStream = new MemoryStream())
{
stream.CopyTo(memoryStream);
model.Thumbnail = memoryStream.ToArray();
}
}
httpClient = new HttpClient();
httpClient.BaseAddress = new Uri("http://localhost:33134/");
httpClient.DefaultRequestHeaders.Accept.Clear();
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/bson"));
MediaTypeFormatter bsonFormatter = new BsonMediaTypeFormatter();
HttpResponseMessage responceMessage = client.PostAsync("ApiUrl", new StringContent(
new JavaScriptSerializer().Serialize(model), Encoding.UTF8, "application/json")).Result;
response.EnsureSuccessStatusCode();
}
只需要在你的代码中更改 1 行,即 HttpResponseMessage 响应
更改您的网络 API 方法以便手动读取文件和其他图像属性。
你可以查看这个 link 来解释如何:
https://www.asp.net/web-api/overview/advanced/sending-html-form-data-part-2
我不确定你是否将图像模型作为参数保留,它是否会被绑定,但你可以尝试
代码:
public Task<HttpResponseMessage> PostImagesModel()
{
// Check if the request contains multipart/form-data.
if (!Request.Content.IsMimeMultipartContent())
{
throw new HttpResponseException(HttpStatusCode.UnsupportedMediaType);
}
var provider = new MultipartFormDataStreamProvider(root);
// Read the form data and return an async task.
var task = Request.Content.ReadAsMultipartAsync(provider).
ContinueWith<HttpResponseMessage>(t =>
{
if (t.IsFaulted || t.IsCanceled)
{
Request.CreateErrorResponse(HttpStatusCode.InternalServerError, t.Exception);
}
// This illustrates how to get the file names data and you can copy it to your image model.
foreach (MultipartFileData file in provider.FileData)
{
Trace.WriteLine(file.Headers.ContentDisposition.FileName);
Trace.WriteLine("Server file path: " + file.LocalFileName);
}
//here you can set the other properties of the image
foreach (var key in provider.FormData.AllKeys)
{
foreach (var val in provider.FormData.GetValues(key))
{
Trace.WriteLine(string.Format("{0}: {1}", key, val));
}
}
return Request.CreateResponse(HttpStatusCode.OK);
});
return task;
}
终于解决了这个问题
ASP.NET 运行时有自己的文件大小限制,位于 web.config 的 httpRuntime 元素下。
所以我除了设置 maxAllowedContentLength
我还需要设置 maxRequestLength
.
<system.web>
<httpRuntime maxRequestLength="102400" targetFramework="4.6.2" />
</system.web>
和
<system.webServer>
<security>
<requestFiltering>
<!-- limit post size to 10mb, query string to 256 chars, url to 1024 chars -->
<requestLimits maxQueryString="256" maxUrl="1024" maxAllowedContentLength="104857600" />
</requestFiltering>
</security>
</system.webServer>
我尝试向服务器发送一个对象,但我意识到如果我的对象大于大约 250 Kb 服务器接收到的对象是 null
。
我在 asp web api
// POST: api/ImagesModels
[ResponseType(typeof(ImagesModel))]
public IHttpActionResult PostImagesModel(ImagesModel imagesModel)
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState);
}
db.ImagesModels.Add(imagesModel);
db.SaveChanges();
return CreatedAtRoute("DefaultApi", new { id = imagesModel.ID }, imagesModel);
}
和我的上传方法在UWP
private async void Upload_image(object sender, RoutedEventArgs e)
{
ImagesModel model = new ImagesModel();
model.CategoryId = Convert.ToInt32(catgoryIdtxb.Text);
model.IsNew = true;
model.IsPayed = IsPayedchbx.IsChecked.Value;
model.Name = ImageNameTxb.Text;
model.PixelHeight = _imagePicWB.PixelHeight;
model.PixelWidth = _imagePicWB.PixelWidth;
model.ThumbnailPixelHeight = _imageThumWB.PixelHeight;
model.ThumbnailPixelWidth = _imageThumWB.PixelWidth;
model.Date = ImadeDate.Date.Date;
using (Stream stream = _imagePicWB.PixelBuffer.AsStream())
{
using (MemoryStream memoryStream = new MemoryStream())
{
stream.CopyTo(memoryStream);
model.Picture = memoryStream.ToArray();
}
}
using (Stream stream = _imageThumWB.PixelBuffer.AsStream())
{
using (MemoryStream memoryStream = new MemoryStream())
{
stream.CopyTo(memoryStream);
model.Thumbnail = memoryStream.ToArray();
}
}
httpClient = new HttpClient();
httpClient.BaseAddress = new Uri("http://localhost:33134/");
httpClient.DefaultRequestHeaders.Accept.Clear();
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/bson"));
MediaTypeFormatter bsonFormatter = new BsonMediaTypeFormatter();
HttpResponseMessage response = await httpClient.PostAsync("api/ImagesModels", model, bsonFormatter);
response.EnsureSuccessStatusCode();
}
并且我试图在 web.config
maxAllowedContentLength
的限制
<system.webServer>
<security>
<requestFiltering>
<requestLimits maxAllowedContentLength="2147483648" />
</requestFiltering>
</security>
</system.webServer>
注意:我使用 visual studio 2015
maxAllowedContentLength 是一个 32 位整数,因此最大值应该是 2,147,483,647 而不是 2,147,483,648
private async void Upload_image(object sender, RoutedEventArgs e)
{
ImagesModel model = new ImagesModel();
model.CategoryId = Convert.ToInt32(catgoryIdtxb.Text);
model.IsNew = true;
model.IsPayed = IsPayedchbx.IsChecked.Value;
model.Name = ImageNameTxb.Text;
model.PixelHeight = _imagePicWB.PixelHeight;
model.PixelWidth = _imagePicWB.PixelWidth;
model.ThumbnailPixelHeight = _imageThumWB.PixelHeight;
model.ThumbnailPixelWidth = _imageThumWB.PixelWidth;
model.Date = ImadeDate.Date.Date;
using (Stream stream = _imagePicWB.PixelBuffer.AsStream())
{
using (MemoryStream memoryStream = new MemoryStream())
{
stream.CopyTo(memoryStream);
model.Picture = memoryStream.ToArray();
}
}
using (Stream stream = _imageThumWB.PixelBuffer.AsStream())
{
using (MemoryStream memoryStream = new MemoryStream())
{
stream.CopyTo(memoryStream);
model.Thumbnail = memoryStream.ToArray();
}
}
httpClient = new HttpClient();
httpClient.BaseAddress = new Uri("http://localhost:33134/");
httpClient.DefaultRequestHeaders.Accept.Clear();
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/bson"));
MediaTypeFormatter bsonFormatter = new BsonMediaTypeFormatter();
HttpResponseMessage responceMessage = client.PostAsync("ApiUrl", new StringContent(
new JavaScriptSerializer().Serialize(model), Encoding.UTF8, "application/json")).Result;
response.EnsureSuccessStatusCode();
}
只需要在你的代码中更改 1 行,即 HttpResponseMessage 响应
更改您的网络 API 方法以便手动读取文件和其他图像属性。 你可以查看这个 link 来解释如何:
https://www.asp.net/web-api/overview/advanced/sending-html-form-data-part-2
我不确定你是否将图像模型作为参数保留,它是否会被绑定,但你可以尝试
代码:
public Task<HttpResponseMessage> PostImagesModel()
{
// Check if the request contains multipart/form-data.
if (!Request.Content.IsMimeMultipartContent())
{
throw new HttpResponseException(HttpStatusCode.UnsupportedMediaType);
}
var provider = new MultipartFormDataStreamProvider(root);
// Read the form data and return an async task.
var task = Request.Content.ReadAsMultipartAsync(provider).
ContinueWith<HttpResponseMessage>(t =>
{
if (t.IsFaulted || t.IsCanceled)
{
Request.CreateErrorResponse(HttpStatusCode.InternalServerError, t.Exception);
}
// This illustrates how to get the file names data and you can copy it to your image model.
foreach (MultipartFileData file in provider.FileData)
{
Trace.WriteLine(file.Headers.ContentDisposition.FileName);
Trace.WriteLine("Server file path: " + file.LocalFileName);
}
//here you can set the other properties of the image
foreach (var key in provider.FormData.AllKeys)
{
foreach (var val in provider.FormData.GetValues(key))
{
Trace.WriteLine(string.Format("{0}: {1}", key, val));
}
}
return Request.CreateResponse(HttpStatusCode.OK);
});
return task;
}
终于解决了这个问题
ASP.NET 运行时有自己的文件大小限制,位于 web.config 的 httpRuntime 元素下。
所以我除了设置 maxAllowedContentLength
我还需要设置 maxRequestLength
.
<system.web>
<httpRuntime maxRequestLength="102400" targetFramework="4.6.2" />
</system.web>
和
<system.webServer>
<security>
<requestFiltering>
<!-- limit post size to 10mb, query string to 256 chars, url to 1024 chars -->
<requestLimits maxQueryString="256" maxUrl="1024" maxAllowedContentLength="104857600" />
</requestFiltering>
</security>
</system.webServer>