仅通过一个对话框提示实现从浏览器到设备的自动保存

Implement autosave from browser to device with only one dialog prompt

在我正在实施的网站中,用户将文件保存在他们的本地设备上。我想实现自动保存,但是像 this one 这样的问题让我相信,如果没有每次写入文件系统的“文件保存”对话框是不可能的(除非用户修改他们的默认浏览器设置)。

然而,我看到app.diagrams.net does it! Once I specify a file path via an initial dialog my edits are autosaved without additional dialogs. That project is open-source,但我努力寻找相关代码至今没有成功。

有人知道这是怎么做到的吗?

以下是证明这是可能的步骤:

  1. 浏览至 app.diagrams.net
  2. 在“将图表保存到”对话框中,选择“设备”
  3. “创建新图表”
  4. “创建”
  5. 在“另存为”对话框中,输入文件名
  6. 进行一些编辑
  7. 重新加载页面
  8. “打开现有图表”
  9. 在“打开”对话框中,选择您的文件 - 它会打开您自动保存的编辑。

快速浏览一下源代码,apps.diagram.net 正在使用 File System Access API 写入文件系统。如果你保留文件句柄,它会让你继续创建一个可写的文件。它要求事物 运行 来自安全上下文 (https) 才能工作。

这是一个简化的例子:

var fHnd = null;
var counter = 0;
var autoSaveOn = true;

window.onload = function() {

  var autoSave = async function() {
    if (autoSaveOn) {
      counter++;
      document.getElementById('status').innerHTML = 'Saving...'
      const writable = await fHnd.createWritable();
      await writable.write(counter);
      await writable.close();
      document.getElementById('status').innerHTML = '';
      window.setTimeout(autoSave, 3000);
    }
  }

  document.getElementById('btnAutoSave').addEventListener('click', async() => {
    if (autoSaveOn) {
      autoSaveOn = false;
      document.getElementById('btnAutoSave').innerHTML = 'Turn autosave on';
    } else {
      autoSaveOn = true;
      document.getElementById('btnAutoSave').innerHTML = 'Turn autosave off';
      await autoSave();
    }
  });

  document.getElementById('btnCreateFile').addEventListener('click', async() => {
    fHnd = await window.showSaveFilePicker({
      types: [{
        description: 'Text Files',
        accept: {
          'text/plain': ['.txt']
        }
      }]
    });
    document.getElementById('btnCreateFile').style.display = 'none';
    document.getElementById('btnAutoSave').style.display = 'block';

    await autoSave();
  });

}
<!doctype html>
<html>

<head>
  <script language="javascript" src="./sample.js"></script>
</head>

<body>
  <button id="btnCreateFile">Save to file</button>
  <p id="status"></p>
  <button id="btnAutoSave" style="display: none">Turn autosave off</button>
</body>

</html>