Chrome nettleser, Nyheter

Breaking change: sync methods for AccessHandles

The
origin private file system
provides access to a special kind of file that is highly optimized for performance, for example, by
offering in-place and exclusive write access to a file’s content. Developers can get access to such
files by calling
createSyncAccessHandle(),
which is a method exposed on
FileSystemFileHandle objects. This call
results in a FileSystemSyncAccessHandle.

The createSyncAccessHandle() method and therefore FileSystemSyncAccessHandle is only
exposed in Workers. It is not available in the main thread.

FileSystemSyncAccessHandle is a file primitive that provides performant access to local files. One
of its main use cases is applications porting C/C++ code to Wasm; however, asynchronous calls are
not fully supported on Wasm yet, and using the
Asyncify library as an alternative has
substantially degraded performance. Making all the methods of the FileSystemSyncAccessHandle synchronous matches the synchronous, POSIX-like file API Wasm-based application expect; making the API more ergonomic while bringing substantial performance gains.

What’s new?

FileSystemSyncAccessHandle exposes the following methods that used to be asynchronous, but that
are synchronous as of Chromium 108.

  • truncate(newSize): Resizes the file associated with the access handle to be newSize bytes
    long. If newSize is larger than the current file size, it pads the file with null bytes;
    otherwise it truncates the file.
  • getSize(): Returns the size of the file associated with the access handle in bytes.
  • flush(): Ensures that the contents of the file associated with the access handle contain all the
    modifications done through write().
  • close(): Flushes the access handle and then closes it. Closing an access handle disables any
    further operations on it and releases the lock on the entry associated with the access handle.
// In a `Worker`:
const root = await navigator.storage.getDirectory();
const fileHandle = await root.getFileHandle('test', { create: true });
// `createSyncAccessHandle()` is still async.
const accessHandle = await fileHandle.createSyncAccessHandle();
// Both `read()` and `write()` were sync before.
accessHandle.read(/* ... */);
accessHandle.write(/* ... */);

// New: synchronous as of Chromium 108.
console.log(accessHandle.getSize());
accessHandle.truncate(123);
accessHandle.flush();
accessHandle.close();

What do I need to do?

Note that changing methods from asynchronous to synchronous is a web-exposed change with potential
breakage. While using await in synchronous methods is a no-op, any use of Promise.then() will break.
If you chain a then() call on the result of any of the previously asynchronous and now
synchronous methods, you need to change your code.

// (✅) This won't break, but you better remove the superfluous `await`:
await accessHandle.flush();
// ✅ Correct:
accessHandle.flush();
// ⛔️ This will break, and you need to restructure your code:
accessHandle.flush().then(/* Follow-up code */);
// ✅ Correct:
accessHandle.flush();
/* Follow-up code */

This post is also available in: English

author-avatar

About Aksel Lian

En selvstendig full stack webutvikler med en bred variasjon av kunnskaper herunder SEO, CMS, Webfotografi, Webutvikling inkl. kodespråk..