如何用ServiceStack和Angular下载动态生成的XML文件?



下面的代码理论上可以工作,但是它缺少错误处理。我遇到的问题是,当一个带有服务堆栈创建的url的新窗口打开时,它开始下载XML文件。但是现在,当服务器端发生错误时,您在这个只有堆栈跟踪的新页面上。

用服务栈和Angular下载动态二进制文件(不存储在磁盘上)的正确方法是什么?Angular with ServiceStack:

downloadExportXML(){
const request = new GetRatingsExportRequest(this.request);
const url = this.jsonServiceClient.createUrlFromDto("GET", request)
window.open(url);
}

WebAPI (c#)收集XML文件。

public HttpResult Get(GetRatingsExportRequest request)
{
MemoryStream ms = new MemoryStream(Encoding.UTF8.GetBytes(xmlContent));
var result = new HttpResult(ms.ToArray());
var disposition = $"attachment;filename=myfilename;";
result.Headers.Add(HttpHeaders.ContentDisposition, disposition);
return result;
}

如果你返回Content-Disposition: attachmentHTTP报头的内容,浏览器将把它作为一个单独的文件下载。

如果你不希望返回它作为一个普通的XML响应。但是你返回它的方式是相当低效的,即调用ToArray()违背了使用流的目的,因为你已经在内存中强制加载了流的整个内容,相反,你应该返回流,这样它就可以作为流异步写入HTTP响应,例如:

return new HttpResult(ms, MimeTypes.Xml);

但是如果你已经得到了XML作为一个字符串,你不需要MemoryStream包装器的开销,也可以只是返回XML字符串原样,例如:

return new HttpResult(xmlContent, MimeTypes.Xml);

我不能让它工作。所以我创建了这个解决方案:使用ServiceStack方法jsonServiceClient.createUrlFromDto()生成下载XML的URL,然后通过Angular HTTPClient下载文件。

downloadExportXML(){
const request = new GetRatingsExportRequest(this.request);
const url = this.jsonServiceClient.createUrlFromDto("GET", request)
this.httpClient.get(url, {observe: 'response', responseType: 'arraybuffer'})
.subscribe((response) => {
var contentDisposition = response.headers.get('content-disposition');
this.downloadFile(response.body)
},
error => this.handleError()
);
}
private downloadFile(blobData: ArrayBuffer)
{
let file = new Blob([blobData], { type: 'application/binary' });
let fileURL = URL.createObjectURL(file);
let fileLink = document.createElement('a');
fileLink.href = fileURL;
fileLink.download = "MYFILENAME.pdf";
fileLink.click();
}

最新更新