我试图从我的web api生成一个CSV文件,并通过angularjs接收该文件.我有一个如下所示的API控制器:
[HttpPost] public HttpResponseMessage GenerateCSV(FieldParameters fieldParams) { var output = new byte[] { }; if (fieldParams!= null) { using (var stream = new MemoryStream()) { this.Serialize(fieldParams, stream); stream.Flush(); output = stream.ToArray(); } } var result = new HttpResponseMessage(HttpStatusCode.OK) { Content = new ByteArrayContent(output) }; result.Content.Headers.ContentType = new MediaTypeHeaderValue("application/octet-stream"); result.Content.Headers.ContentDisposition = new ContentDispositionHeaderValue("attachment") { FileName = "Fields.csv" }; return result; }
在我的angularjs中,我有这个:
$scope.save = function () { var csvInput= extractDetails(); // File is an angular resource. We call its save method here which // accesses the api above which should return the content of csv File.save(csvInput, function (content) { console.log(content); // only creates a csv file with "[object Object]" written in it var hiddenElement = document.createElement('a'); hiddenElement.href = 'data:text/csv;charset=utf-8,\uFEFF' + encodeURI(content.Parameters); hiddenElement.target = '_blank'; hiddenElement.download = 'myFile.csv'; hiddenElement.click(); }); };
让我们举例来说,在我的API控制器中,响应的内容是
产量
{字节[152]}
[0]:83
[1]:101
[2]:44
[3]:67
[4]:10
当我在angularjs中收到这个并且我将值content
放在控制台日志(chrome)中时,这就是我得到的:
{Parameters:Array [1],$ promise:Object,$ resolved:true,$ get:function,$ save:function ...}
0: "S"
1:"e"
2:","
3:"C"
4:"↵"
$ promise:对象
$ resolved:true`
为什么content
angularjs中的接收包含字符而不是数组的字节?
我如何控制content
以这样的方式,我将只使用CSV相关的数据,并删除$promise
和$resolved
?它们为什么首先包括在内?如何删除它们?
如果我正在做的事情是错误的,那么生成csv的正确方法是什么?:|
raberana.. 5
忘了更新这个,但我现在找到了解决这个问题的方法:
将有两个API,一个(POST)将记住要在处理中使用的数据,另一个(GET)将分配文件.
POST:
[HttpPost] public async TaskBuildFile(FileParameters fileParams) { var guid = Guid.NewGuid().ToString(); if (fileParams!= null) { await Task.Run(() => FileContents.Add(guid, fileParams)); return this.Request.CreateResponse(HttpStatusCode.OK, new { Value = guid }); } return this.Request.CreateErrorResponse(HttpStatusCode.BadRequest, "Invalid data"); }
在AngularJs中,记住guid返回并将其传递给另一个api:
location.href = '/api/file/generatefile' + '?guid=' + generatedGuidFromAPI + '&reportName=' + $scope.reportName;
这是generatefile
MVC中的API控制器:
得到:
[HttpGet] public async TaskGenerateFile(string guid, string reportName) { byte[] output = null; if (FileContents.ContainsKey(guid)) { await Task.Run(() => { using (var stream = new MemoryStream()) { this.CreateFile(FileContents[guid], stream); stream.Flush(); output = stream.ToArray(); } }); } FileContents.Remove(guid); if (output != null) { var result = new HttpResponseMessage(HttpStatusCode.OK) { Content = new ByteArrayContent(output) }; result.Content.Headers.ContentType = new MediaTypeHeaderValue("application/octet-stream"); result.Content.Headers.ContentDisposition = new ContentDispositionHeaderValue("attachment") { FileName = reportName + ".csv" }; return result; } return this.Request.CreateErrorResponse(HttpStatusCode.NoContent, "No record found"); }
使用location.href
会导致浏览器自动下载文件,询问是否保存.
忘了更新这个,但我现在找到了解决这个问题的方法:
将有两个API,一个(POST)将记住要在处理中使用的数据,另一个(GET)将分配文件.
POST:
[HttpPost] public async Task<HttpResponseMessage> BuildFile(FileParameters fileParams) { var guid = Guid.NewGuid().ToString(); if (fileParams!= null) { await Task.Run(() => FileContents.Add(guid, fileParams)); return this.Request.CreateResponse(HttpStatusCode.OK, new { Value = guid }); } return this.Request.CreateErrorResponse(HttpStatusCode.BadRequest, "Invalid data"); }
在AngularJs中,记住guid返回并将其传递给另一个api:
location.href = '/api/file/generatefile' + '?guid=' + generatedGuidFromAPI + '&reportName=' + $scope.reportName;
这是generatefile
MVC中的API控制器:
得到:
[HttpGet] public async Task<HttpResponseMessage> GenerateFile(string guid, string reportName) { byte[] output = null; if (FileContents.ContainsKey(guid)) { await Task.Run(() => { using (var stream = new MemoryStream()) { this.CreateFile(FileContents[guid], stream); stream.Flush(); output = stream.ToArray(); } }); } FileContents.Remove(guid); if (output != null) { var result = new HttpResponseMessage(HttpStatusCode.OK) { Content = new ByteArrayContent(output) }; result.Content.Headers.ContentType = new MediaTypeHeaderValue("application/octet-stream"); result.Content.Headers.ContentDisposition = new ContentDispositionHeaderValue("attachment") { FileName = reportName + ".csv" }; return result; } return this.Request.CreateErrorResponse(HttpStatusCode.NoContent, "No record found"); }
使用location.href
会导致浏览器自动下载文件,询问是否保存.