【问题标题】:Safari 12 Won't Download a PDF blobSafari 12 不会下载 PDF blob
【发布时间】:2019-04-02 13:49:11
【问题描述】:

此代码用于通过 blob 下载 pdf。除了适用于 macOS 和 iOS 的 Safari 12 之外,它在所有浏览器上都能正常工作。甚至 Safari 11 也能正常工作。当我第一次运行代码时,它工作正常,但之后每次它都会给我“WebKitBlobResource error 1”

function downloadFileFromBlob(fileBlob, fileName) {
    if (/\bMSIE\b|\bTrident\b/.test($window.navigator.userAgent)) {
        $window.navigator.msSaveOrOpenBlob(fileBlob, fileName);
    } else {
        var fileURL = $window.URL.createObjectURL(fileBlob);
        createDownloadElementAndClick(fileURL, fileName);
    }
}

function createDownloadElementAndClick(fileURL, fileName) {
    var anchorElement = $window.document.createElement('a');
    anchorElement.href = fileURL;
    anchorElement.target = '_blank';
    anchorElement.download = fileName;
    var event = $window.document.createEvent("MouseEvents");
    event.initEvent("click", true, false);
    anchorElement.dispatchEvent(event);
}

【问题讨论】:

标签: javascript macos pdf safari blob


【解决方案1】:

似乎是target = "_blank" 不起作用。我已将其替换为_self,这显然解决了问题。当我遇到同样的问题时,我发现了这个。

如果有人知道我们为什么不能使用_blank,我很想听听。

【讨论】:

  • 鉴于只有 blobURI 受此 _blank 限制(dataURI 似乎工作正常),我想说这是更大限制的一部分,甚至 window.open(blobURI) 也会被阻止。
  • 也在尝试解决这个问题,我遇到的问题是当我使用a.target = '_self' 时,Chrome 不再使用download="" 属性中定义的文件名命名 blob 下载...
【解决方案2】:

显然这是Safari 12 bug,有时会发生。它不是由target = "_self" 修复的,它属于different regression bug。

在修复错误之前,丑陋的解决方法是:

  1. 将 blob 发送到远程保存文件的服务器。
  2. 下载远程文件。

Javascript 代码

   async createDownloadElementAndClick(blob, fileName) {
            let options = {
                method:"POST",
                body:blob
            };

            await fetch(`https://example.com/upload.php`, options);

            window.open(`https://example.com/download.php?${fileName}`, "_self");
    }

PHP 代码

在upload.php中:

<?php    
// add any authentication code as necessary here


    // gets entire POST body
    $data = file_get_contents('php://input');

    $filename = "temp/download.pdf";
    // write the data out to the file
    $fp = fopen($filename, 'wb');

    fwrite($fp, $data);
    fclose($fp);
?>

在download.php中:

<?php
    ob_start();
    $file = $_SERVER["QUERY_STRING"];

    // This is the line that tells Safari to download the file instead of opening it
    header("Content-disposition: attachment; filename=$file");
    header("Content-type: application/pdf", false);
    readfile("temp/download.pdf");

    ob_flush();
    // This deletes the pdf so there is little chance of contaminating the next call
    unlink("temp/download.pdf");
?>

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-12-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-01-22
    • 1970-01-01
    • 1970-01-01
    • 2016-05-14
    相关资源
    最近更新 更多