C# Web API HttpResponseMessage内容返回不完整
我想返回使用Web API 5.0从我的数据库生成的csv 它工作正常,只是返回的csv被截断 我想问题出在MemoryBuffer管理上,但我找不到它在哪里 我的代码(已解决):C# Web API HttpResponseMessage内容返回不完整,c#,asp.net-web-api,httpresponse,C#,Asp.net Web Api,Httpresponse,我想返回使用Web API 5.0从我的数据库生成的csv 它工作正常,只是返回的csv被截断 我想问题出在MemoryBuffer管理上,但我找不到它在哪里 我的代码(已解决): IEnumerable masterTripList=\u obsvMasterRepo.GetObsTrips(容器名称、日期年、端口、obsvCode、obsvTripCode、obsvProgCode、lastModifiedDateYear、lastModifiedBy、状态码); IList masterT
IEnumerable masterTripList=\u obsvMasterRepo.GetObsTrips(容器名称、日期年、端口、obsvCode、obsvTripCode、obsvProgCode、lastModifiedDateYear、lastModifiedBy、状态码);
IList masterTripModelList=新列表();
foreach(masterTripList中的MasterObsTrip trip)
masterTripModelList.Add(新的MasterObsTripModel(trip));
var stream=newmemoryStream();
var writer=新的StreamWriter(流);
CsvFileDescription outputFileDescription=新CsvFileDescription
{
分隔符字符=',',//逗号分隔
FirstLineHasColumnNames=true,//第一条记录中没有列名
FileCultureName=“nl nl”//使用荷兰使用的格式
};
CsvContext cc=新的CsvContext();
cc.Write(masterTripModelList、writer、outputFileDescription);
writer.Flush();
流位置=0;
HttpResponseMessage response=新的HttpResponseMessage(HttpStatusCode.OK);
response.Content=新的流内容(stream);
response.Content.Headers.ContentType=新的MediaTypeHeaderValue(“应用程序/八位字节流”);
response.Content.Headers.ContentDisposition=新的ContentDispositionHeaderValue(“附件”);
response.Content.Headers.ContentDisposition.FileName=“ObserverTripList.csv”;
stream.Flush();
返回响应;
谢谢在重置流之前,我会尝试执行writer.Flush()。Position=0 此外,如果您经常需要CSV内容,我还建议您自己创建一个CSV内容类
public class CsvContent<T> : HttpContent
{
private readonly MemoryStream _stream = new MemoryStream();
public CsvContent(CsvFileDescription outputFileDescription, string filename, IEnumerable<T> data)
{
var cc = new CsvContext();
var writer = new StreamWriter(_stream);
cc.Write(data, writer, outputFileDescription);
writer.Flush();
_stream.Position = 0;
Headers.ContentType = new MediaTypeHeaderValue("application/octet-stream");
Headers.ContentDisposition = new ContentDispositionHeaderValue("attachment");
Headers.ContentDisposition.FileName = filename;
}
protected override Task SerializeToStreamAsync(Stream stream, TransportContext context)
{
return _stream.CopyToAsync(stream);
}
protected override bool TryComputeLength(out long length)
{
length = _stream.Length;
return true;
}
}
公共类CsvContent:HttpContent
{
私有只读内存流_stream=新内存流();
公共CSV内容(CsvFileDescription outputFileDescription、字符串文件名、IEnumerable数据)
{
var cc=new CsvContext();
var writer=新的StreamWriter(_stream);
cc.Write(数据、写入器、输出文件描述);
writer.Flush();
_流位置=0;
Headers.ContentType=新的MediaTypeHeaderValue(“应用程序/八位字节流”);
Headers.ContentDisposition=新的ContentDispositionHeaderValue(“附件”);
Headers.ContentDisposition.FileName=文件名;
}
受保护的重写任务SerializeToStreamAsync(流、TransportContext上下文)
{
返回_stream.CopyToAsync(流);
}
受保护的覆盖布尔TryComputeLength(out long length)
{
长度=_stream.length;
返回true;
}
}
然后你的控制器动作减少到
IEnumerable<MasterObsTrip> masterTripList = _obsvMasterRepo.GetObsTrips(vesselName, dateYear, port, obsvCode, obsvTripCode, obsvProgCode, lastModifiedDateYear, lastModifiedBy, statusCode);
IList<MasterObsTripModel> masterTripModelList = new List<MasterObsTripModel>();
foreach (MasterObsTrip trip in masterTripList)
masterTripModelList.Add(new MasterObsTripModel(trip));
CsvFileDescription outputFileDescription = new CsvFileDescription
{
SeparatorChar = ',', // comma delimited
FirstLineHasColumnNames = true, // no column names in first record
FileCultureName = "nl-NL" // use formats used in The Netherlands
};
HttpResponseMessage response = new HttpResponseMessage(HttpStatusCode.OK) {
Content = new CsvContent<MasterObsTripModel> (outputFileDescription,
"ObserverTripList.csv",
masterTripModelList);
}
return response;
IEnumerable masterTripList=\u obsvMasterRepo.GetObsTrips(容器名称、日期年、端口、obsvCode、obsvTripCode、obsvProgCode、lastModifiedDateYear、lastModifiedBy、状态码);
IList masterTripModelList=新列表();
foreach(masterTripList中的MasterObsTrip trip)
masterTripModelList.Add(新的MasterObsTripModel(trip));
CsvFileDescription outputFileDescription=新CsvFileDescription
{
分隔符字符=',',//逗号分隔
FirstLineHasColumnNames=true,//第一条记录中没有列名
FileCultureName=“nl nl”//使用荷兰使用的格式
};
HttpResponseMessage response=新的HttpResponseMessage(HttpStatusCode.OK){
内容=新的CSV内容(outputFileDescription,
“ObserverTripList.csv”,
masterTripModelList);
}
返回响应;
这可以通过在CsvContent类中创建CsvFileDescription来进一步简化。避免调用
stream.Flush()
,因为流的实际写入会在以后发生……尝试看看这是否解决了您的问题。..Thx Kiran,但删除流。Flush不会改变任何事情,好的……我觉得其他的都没问题……只是想确定一下,你有没有试着查看内存流中的实际内容,看看它是否包含全部内容?您可以尝试将此内存流写入磁盘文件,看看它是否确实包含全部内容…是的,我在服务器上生成了该文件,其中包含了我的全部数据ethmm,我不确定发生了什么…您是否可以共享复制?(您使用的是哪个版本的Web API?)有类似这样的讨论-建议使用MediaTypeFormatter序列化(并在需要时反序列化)来自ApiController的返回。好奇的是,如果控制器返回类型是Csv流,您会如何将其与您的方法进行比较?@mishrsud i返回HttpResponseMessage,内容属性设置为CSVContent实例。这允许我访问响应头消息。
public class CsvContent<T> : HttpContent
{
private readonly MemoryStream _stream = new MemoryStream();
public CsvContent(CsvFileDescription outputFileDescription, string filename, IEnumerable<T> data)
{
var cc = new CsvContext();
var writer = new StreamWriter(_stream);
cc.Write(data, writer, outputFileDescription);
writer.Flush();
_stream.Position = 0;
Headers.ContentType = new MediaTypeHeaderValue("application/octet-stream");
Headers.ContentDisposition = new ContentDispositionHeaderValue("attachment");
Headers.ContentDisposition.FileName = filename;
}
protected override Task SerializeToStreamAsync(Stream stream, TransportContext context)
{
return _stream.CopyToAsync(stream);
}
protected override bool TryComputeLength(out long length)
{
length = _stream.Length;
return true;
}
}