Ian*_*ton 8 javascript c# angularjs typescript
所以我花了几周时间研究如何通过ajax从服务器获取pdf,然后将其显示给客户端.我需要这样做的原因是用户不能直接在服务器上转到pdf,因为他们不会提供令牌来传递安全性,但我可以使用javascript.使用以下代码,我能够得到我所期望的:
var xhr = new XMLHttpRequest();
xhr.open('GET', url, true);
xhr.responseType = 'arraybuffer';
xhr.setRequestHeader("token", token.value);
xhr.onload = function (e) {
if (this.status == 200) {
var file = new Blob([this.response], { type: 'application/pdf' });
var fileURL = URL.createObjectURL(file);
window.open(fileURL, '_blank');
}
};
xhr.send();
Run Code Online (Sandbox Code Playgroud)
然而,当我尝试以这样的角度做这个确切的事情时(我正在做这个东西的一半,所以两者中的标题匹配):
var config = {
url: url,
method: 'GET',
responseType: 'arraybuffer',
headers: {
'Accept':'*/*',
"token": token.value
}
}
$http(config)
.success(function (response) {
var file = new Blob([response], { type: 'application/pdf' });
var fileURL = URL.createObjectURL(file);
window.open(fileURL, '_blank')
});
Run Code Online (Sandbox Code Playgroud)
以下是两个标题的样子:
GET http://example.com HTTP/1.1
Host: example.com
Connection: keep-alive
Accept: */*
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/50.0.2661.94 Safari/537.36
token: test
Referer: http://example.com
Accept-Encoding: gzip, deflate, sdch
Accept-Language: en-US,en;q=0.8
Run Code Online (Sandbox Code Playgroud)
唯一的区别是xmlhttprequest版本具有Authorization:Negotiate标头,但我可以从服务器的响应中在fiddler中呈现它们.这告诉我来自$ http的'response'与xmlhttprequest中的this.response不同.有人可以告诉我有什么不同以及如何解决它?
我想了很长一段时间,这是一个charset问题,我甚至在通过线路发送它之前使用了base64字节,然后使用atob()将其切换回来,但这似乎没有让它变得更好.似乎$ http版本接受响应并将字节转换为utf8,即使它们不是......我认为我的字节是windows-1252/latin1/ios-8895-1
我说这个的原因是因为我在十六进制编辑器中看到了这个:
btye 85(在服务器上)切换到C2 85的两个字节(在$ http代码之后) http://www.fileformat.info/info/unicode/char/85/charset_support.htm
btye c5(在服务器上)切换到c3 85的两个字节(在$ http代码之后) http://www.fileformat.info/info/unicode/char/c5/charset_support.htm
我甚至尝试编码/解码,如果各种组合无济于事.我真的认为pdf在通过棱角分析时会被破坏,但我不知道如何.
更新1
在服务器端,代码如下所示:
public class LabelController : Controller
{
//using Microsoft.AspNet.Mvc
[HttpGet, Route("api/labels/box")]
public IActionResult BoxLabels(Guid requestId)
{
var data = this.getPDF("http://foobar.com/example.pdf");
Response.Headers.Add("Content-Length", data.Length.ToString());
Response.Headers.Add("Content-Disposition", "inline; filename=example.pdf");
return new FileContentResult(data, "application/pdf");
}
//using restsharp
private bytes[] getPDF(url)
{
var client = new RestClient
{
BaseUrl = new Uri(url),
Authenticator = new NtlmAuthenticator()
};
var request = new RestRequest
{
Method = Method.POST,
Credentials = CredentialCache.DefaultNetworkCredentials,
RequestFormat = DataFormat.Xml
};
var response = client.Execute(request);
return response.RawBytes;
}
}
Run Code Online (Sandbox Code Playgroud)
以下是它的样子:http://plnkr.co/edit/R3FiesPk7Os22SMsTTfE没有"No'Access-Control-Allow-Origin'"错误
更新2
以下是使用$ http时pdf的样子:
所以我认为你的问题是浏览器正在执行 CORS 预检,因为你正在执行跨浏览器请求。它将 GET 请求转变为 OPTIONS。
您需要将 OPTIONS 请求添加到您接受的 CORS 选项中。您可能还需要将您的 IP 地址添加到 CORS 选项中接受的来源。
以下是一些有用的链接: http://barnabas.tumblr.com/post/87914971548/the-curse-of-the-cors-preflight-and-how-to-defeat 对如何处理 CORS OPTIONS 预检请求感到困惑
归档时间: |
|
查看次数: |
875 次 |
最近记录: |