【问题标题】:Open blob objectURL in Chrome在 Chrome 中打开 blob objectURL
【发布时间】:2017-09-03 03:40:23
【问题描述】:

我想在 chrome 浏览器(Chrome 56.0.2924.87,Ubuntu 14.04)的新标签页中使用 javascript 中的 window.open(fileObjectURL) 打开 PDF。我正在从 base64 编码数据创建 blob,并创建一个像这样的 objectURL:

const fileObjectURL = URL.createObjectURL(fileBlob); 

它在最新的 Firefox 浏览器中运行良好。但在 Chrome 中,我可以看到新标签页被打开但随后立即关闭。所以我在控制台等中没有任何错误。 它现在在 Chrome 中工作的唯一方法是将 base64 数据直接提供给 window.open(fileBase64Data) 函数。但我不喜欢在 url 中设置完整的数据。

也许这是 Chrome 阻止打开 blob 的安全问题?

【问题讨论】:

  • 您知道是否有办法在新选项卡中打开 PDF 并在 URL 中设置文件名?谢谢!

标签: javascript google-chrome base64 blob


【解决方案1】:

原因可能是 adblock 扩展(我遇到了完全相同的问题)。

【讨论】:

  • 确实,uBlockOrigin 列表称为 easylist(默认值之一)具有 |blob:$popup 规则,它使用 blob 方案阻止此类新链接,因为(如列表中上述评论所述) :! Used with many websites to generate multiple popups(如果你知道哪些网站使用了这个技巧,请告诉我!)
【解决方案2】:

在将 blob url 放入窗口之前,您必须打开新窗口:

let newWindow = window.open('/')

您也可以使用其他页面,例如 /loading,带有加载指示器。

然后你需要等待newWindow加载,你可以在这个窗口中推送你的blob文件的url:

newWindow.onload = () => {
    newWindow.location = URL.createObjectURL(blob);
};

Adblock 扩展程序不会阻止它。

我将它与这样的 AJAX 和 ES 生成器一起使用:

let openPDF = openFile();
openPDF.next();
axios.get('/pdf', params).then(file => {
  openPDF.next(file);
});

function* openFile() {
  let newWindow = window.open('/pages/loading');
  // get file after .next(file)
  let file = yield;
  // AJAX query can finish before window loaded,
  // So we need to check document.readyState, else listen event
  if (newWindow.document.readyState === 'complete') {
    openFileHelper(newWindow, file);
  } else {
    newWindow.onload = () => {
      openFileHelper(newWindow, file);
    };
  }
}

function openFileHelper(newWindow, file) {
  let blob = new Blob([file._data], {type: `${file._data.type}`});
  newWindow.location = URL.createObjectURL(blob);
}

【讨论】:

  • 我用 let newWindow = window.open('/'); newWindow.onload = () => { newWindow.location.assign(blobURL); };其中 blobURL 是字符串类型。谢谢
【解决方案3】:

绕过广告拦截器。

coffeescript & jquery

$object = $("<object>")
$object.css
  position: 'fixed'
  top: 0
  left: 0
  bottom: 0
  right: 0
  width: '100%'
  height: '100%'
$object.attr 'type', 'application/pdf'
$object.attr 'data', fileObjectURL
new_window = window.open()
new_window.onload = ->
  $(new_window.document.body).append $object

【讨论】:

  • 此解决方案适用于我在 Chrome 和 Firefox 中使用 uBlock Origin。
【解决方案4】:

在普通的 javascript 中(因为我没有 jquery)

let newWindow = window.open('/file.html');
newWindow.onload = () => {
    var blobHtmlElement;
    blobHtmlElement = document.createElement('object');
    blobHtmlElement.style.position = 'fixed';
    blobHtmlElement.style.top = '0';
    blobHtmlElement.style.left = '0';
    blobHtmlElement.style.bottom = '0';
    blobHtmlElement.style.right = '0';
    blobHtmlElement.style.width = '100%';
    blobHtmlElement.style.height = '100%';
    blobHtmlElement.setAttribute('type', 'application/pdf'); 
    blobHtmlElement.setAttribute('data', fileObjectURL);
    newWindow.document.title = 'my custom document title';
    newWindow.document.body.appendChild(blobHtmlElement);
};

/file.html是一个几乎是空的html文件,来源:

<!DOCTYPE html>
<html lang="en">
<head>
</head>
<body>

</body>
</html>

在 chrome 和 firefox 中测试(2019 年 11 月 20 日)

【讨论】:

  • 不适用于 Firefox 75。在调用 open() 后,会向用户显示警告“弹出窗口被阻止”,newWindownull
  • 为我工作,稍作改动:var fileURL = URL.createObjectURL(blob); let newWindow = window.open(fileURL);
【解决方案5】:

我没有广告拦截器。看起来将 blob 类型显式设置为 application/pdf 将解决此问题。

const newBlob = new Blob([blobData], {type: "application/pdf"});

【讨论】:

    【解决方案6】:

    很遗憾,上述解决方案均无效。新窗口在生产中仍然被阻塞,在开发中它可以工作。只有 Chrome 块,在 Edge 中一切正常。

    【讨论】:

    • 如果您有新问题,请点击 按钮提出问题。如果有助于提供上下文,请包含指向此问题的链接。 - From Review
    【解决方案7】:

    萨拉姆

    blob:http://***.***.***.**/392d72e4-4481-4843-b0d4-a753421c0433
    

    Blob 不会被 Chrome 屏蔽,但会被 AdBlock 扩展程序屏蔽 要么:

    • 在此网站上暂停
    • 不要在本网站的页面上运行
    • 或者禁用或删除 AdBlock 扩展

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2014-08-20
      • 2019-05-25
      • 2017-08-06
      • 1970-01-01
      • 2020-11-10
      • 1970-01-01
      • 2017-06-12
      • 2017-12-26
      相关资源
      最近更新 更多