C# 请求和处理以字节[]形式包含文件的Web API响应的最佳方法?
我正试图从RESTAPI返回一个pdf文件,并向控制器集合添加了一个ReportController,如下所示C# 请求和处理以字节[]形式包含文件的Web API响应的最佳方法?,c#,asp.net-web-api,azure-storage,C#,Asp.net Web Api,Azure Storage,我正试图从RESTAPI返回一个pdf文件,并向控制器集合添加了一个ReportController,如下所示 public class ReportController : ApiController { public HttpResponseMessage Get(int id) { var result = new HttpResponseMessage(HttpStatusCode.OK); string fileName = id.ToS
public class ReportController : ApiController
{
public HttpResponseMessage Get(int id)
{
var result = new HttpResponseMessage(HttpStatusCode.OK);
string fileName = id.ToString();
MemoryStream memoryStream = GetStreamFromBlob(fileName);
result.Content = new ByteArrayContent(memoryStream.ToArray());
result.Content.Headers.ContentType = new MediaTypeHeaderValue("application/pdf");
return result;
}
}
其他控制器都可以正常工作,但是这是第一个设置为返回HttpResponseMessage而不是可序列化对象或对象集合的控制器
但是,我很难从客户端使用它。我们已经尝试了许多版本的代码来实现这一点,但是控制器代码从未被击中,而且似乎很少有成功调用此功能的完整示例。以下是我当前的版本:-
public async Task<string> GetPdfFile(int id)
{
string fileName = string.Format("C:\\Code\\PDF_Client\\{0}.pdf", id);
using (HttpClient proxy = new HttpClient())
{
string url = string.Format("http://localhost:10056/api/report/{0}", id);
HttpResponseMessage reportResponse = await proxy.GetAsync(url); //****
byte[] b = await reportResponse.Content.ReadAsByteArrayAsync();
System.IO.File.WriteAllBytes(fileName, b);
}
return fileName;
}
public异步任务GetPdfFile(int-id)
{
string fileName=string.Format(“C:\\Code\\PDF\{0}.PDF”,id);
使用(HttpClient proxy=new HttpClient())
{
字符串url=string.Format(“http://localhost:10056/api/report/{0}”,id);
HttpResponseMessageReportResponse=wait proxy.GetAsync(url)//****
byte[]b=wait reportResponse.Content.ReadAsByteArrayAsync();
System.IO.File.writealBytes(文件名,b);
}
返回文件名;
}
但是,行**
失败,显示消息无法建立连接,因为目标计算机主动拒绝它127.0.0.1:10056
正如我所说,http://localhost:10056/api/
工作正常
这是从WEBAPI服务器方法获取文件的正确方法吗
对于代码的其他方面,如使用wait/async或控制器返回文件的更好方法,您有什么建议吗?我遇到了同样的问题,希望将PDF写入ApicController操作的输出 这个链接帮助了我: 我编写了自己的MediaTypeFormatter,用于从字节数组编写PDF
public class PdfFormatter : MediaTypeFormatter
{
#region Constants and Fields
private const int ChunkSizeMax = 1024 * 10;
#endregion
#region Constructors and Destructors
public PdfFormatter()
{
SupportedMediaTypes.Add(MediaTypeHeaderValue.Parse("application/pdf"));
}
#endregion
#region Public Methods
public override bool CanReadType(Type type)
{
return false; // can't read any types
}
public override bool CanWriteType(Type type)
{
return type == typeof(byte[]);
}
public override Task WriteToStreamAsync(
Type type, object value, Stream writeStream, HttpContent content, TransportContext transportContext)
{
Task t = new Task(() => WritePdfBytes(value, writeStream));
t.Start();
return t;
}
#endregion
#region Methods
private static void WritePdfBytes(object value, Stream writeStream)
{
byte[] buffer = value as byte[];
int offset = 0;
while (offset < buffer.Length)
{
int chunkSize = Math.Min(buffer.Length - offset, ChunkSizeMax);
writeStream.Write(buffer, offset, chunkSize);
offset += chunkSize;
}
}
#endregion
}
我的ApiController Get方法的相关部分如下所示:
private void SetupFormatters()
{
GlobalConfiguration.Configuration.Formatters.Add(new PdfFormatter());
}
public HttpResponseMessage Get(string url, string title)
{
byte[] pdfBytes;
/* generate the pdf into pdfBytes */
string cleanTitle = new Regex(@"[^\w\d_-]+").Replace(title, "_");
string contentDisposition = string.Concat("attachment; filename=", cleanTitle, ".pdf");
HttpResponseMessage response = Request.CreateResponse(HttpStatusCode.OK, pdfBytes, MediaTypeHeaderValue.Parse("application/pdf"));
response.Content.Headers.ContentDisposition = ContentDispositionHeaderValue.Parse(contentDisposition);
return response;
}
您的目标是打开客户端\从浏览器保存文件吗?您看到了吗?您看到的错误与一般连接问题有关,但我看到您也在说它与其他控制器配合良好…检查以下描述错误的内容:…您的代码在我看来很好,但是,是的,它可以提高性能,尽管…@StudyTowel-不,我想在我的客户端代码中检索该文件,并将其保存到磁盘上,同时查看它。谢谢你的链接,但我的第一个问题是“目标机器主动拒绝”错误。@KiranChalla-谢谢你的链接,但是正如你所注意到的,我的客户端应用程序在此之前刚刚访问了其他控制器,所以我忍不住认为这个控制器在某处有一个bug。可能是不正确的情况,或者在这种情况下不允许使用“报告”一词?正如我所说,这是我第一次返回HttpResponseMessage的控制器,所以这是我的第一个想法。可能需要方法上的属性?我尝试了一个Get()方法,该方法只返回一个byte[]而不是一个HttpResponseMessage,但也无法使其正常工作。很遗憾,这样行吗?