在 Service Worker 中缓存 Amazon S3 文件以供离线使用

Cache Amazon S3 files in Service Worker for Offline usage

我正在使用服务工作者来允许离线访问我的页面。我正在使用工作箱,但我认为这个问题适用于一般的服务人员。

用户的工作流程是他点击一个按钮下载数据供离线使用。这包括许多文件,它们可能存储在也可能不存储在 Amazon S3 上。

例如,可以想象当用户点击按钮时的代码是:

function cacheFilesForOfflineUse(files) {
    files.forEach(file => fetch(file));
}

然后,在 serviceWorker.js 中,类似于:

workbox.routing.registerRoute(
    ({event}) => /* ... omitted ... */,
    new workbox.strategies.CacheFirst({cacheName: 'myFilesCache'})
);

负责拦截fetch并将其存入缓存。这当然是简化了。

这大部分都有效,但对于一种特定情况:如果文件位于 302 重定向 之后(当文件存储在 S3 上时就是这种情况),我会尝试下载 文件(通过设置 document.location),我在控制台中收到此错误:

... a redirected response was used for a request whose redirect mode is not "follow"

并显示错误页面。

中建议在收到重定向响应时存储响应的副本,因此我尝试将此技术用作工作箱插件(cleanResponse 与链接 post 中的一样) ):

{
    cacheWillUpdate: async ({request, response, event}) => {
        if (response.redirected && response.ok) {
            // Sanitize redirects
            for (const key of response.headers.keys()) {
                console.log(key, response.headers.get(key));
            }
            return cleanResponse(response);
        }
        return response;
    },
}

这几乎可以工作,但有一个重要警告:它不会克隆所有响应 header。唯一记录/复制的 header 是:

content-type image/png last-modified Tue, 18 Jun 2019 12:57:10 GMT

其中严重遗漏了 Content-Disposition:附件 header,浏览器将其视为下载是必需的。

有什么办法解决这个问题,还是我 运行 遇到了一些安全限制?

我找到了解决方法。也许以后会对其他人有所帮助。

解决方法是避免使用导航下载文件。所以我替换了:

function downloadFile(fileUrl) {
    document.location.assign(fileUrl);
}

function downloadFile(fileUrl, filename) {
    fetch(url).then(function (response) {
        response.blob().then(function (blob) {
            downloadFile(blob, filename, response.headers.get('content-type'));
        });
    });
}

downloadFile 这个包在哪里:https://www.npmjs.com/package/downloadjs.

它似乎工作正常。但是,如果有更清晰的答案,我会很乐意放弃对它的复选标记。