-
-
Notifications
You must be signed in to change notification settings - Fork 37
Description
Discussed in https://github.com/orgs/zen-fs/discussions/280
Originally posted by lvcabral December 19, 2025
I have an implementation of sync configuration that I need for my project, would you consider this feature?
I just submitted the PR, but if you don't like that, I will have to create a forked NPM package for my project.
Below the summary of the changes:
ZenFS Sync Configuration Enhancements
Overview
The proposed changes adds full support for configuring ZenFS backends in purely synchronous JavaScript runtimes. Historically, mounting or reconfiguring a backend required awaiting configure() or configureSingle(). We now expose synchronous equivalents, enforce deterministic readiness across file systems, and document/test the new flow end-to-end.
Key Additions
-
Synchronous configuration APIs
configureSync()mirrorsconfigure()and accepts the same shape. It validates that every backend involved is synchronously constructible and mounted.configureSingleSync()mirrorsconfigureSingle()for the common single-mount use case.resolveMountConfigSync()performs backend resolution without promises and rejects configurations that would require async work (e.g., asyncisAvailable()checks orcreate()implementations that return promises).
-
FileSystem readiness contract
- New helper
ensureReadySync()lives insrc/internal/filesystem.ts. It invokes an optionalreadySync()hook on file systems and throws when the instance can only be prepared asynchronously. StoreFS,CopyOnWriteFS, and theMutexedmixin now implementreadySync(), unlocking synchronous initialization for every backend layered on top of them (e.g.,InMemory,SingleBuffer, and CoW compositions).
- New helper
-
Synchronous mounting utilities
mountWithMkdirSync()mirrors the async helper, ensuring mount points exist (creating directories synchronously when missing) beforemount()is invoked.- Device injection honors synchronous semantics. When
addDevicesis enabled, the DeviceFS instance is initialized viaensureReadySync().
Updated Backends & Mixins
- InMemory / SingleBuffer: both still wrap
StoreFS, so onceStoreFS.readySync()became available the backends worked automatically with the new APIs. - CopyOnWrite: now ensures both readable and writable layers are synchronously ready.
- Mutexed: delegates
readySync()to the wrapped file system, keeping mutex-wrapped instances compatible with synchronous configuration paths.
Developer Guidance
- Prefer
configureSync()/configureSingleSync()only when your environment cannot await promises (e.g., kernel bootstrap or embedders that expect immediate mounting). - Backends that perform network IO, rely on async
isAvailable()checks, or defer initialization will throwENOTSUPwhen used with the sync APIs. Stick with the async configuration path in those scenarios. - When authoring new backends:
- Keep
create()synchronous if you want compatibility withconfigureSync(). - If extra initialization time is needed, implement both
ready()andreadySync()(the latter should throw when truly impossible). - Ensure any nested mount configuration that might be synchronous also calls
ensureReadySync()once constructed.
- Keep
Testing & Documentation
- Added
tests/common/config.test.tscoveringconfigureSync,configureSingleSync, and backend compatibility (including rejection of async backends). - Extended
documentation/configuration.mdwith examples forconfigureSync()/configureSingleSync()and guidance on usingresolveMountConfigSync().
These improvements collectively let synchronous runtimes opt into ZenFS without rewriting application initialization, while keeping asynchronous setups unchanged.