Adds an `rclone://<remote>/<path>` scheme backed by the rclone CLI, giving
yazi native browsing of any of rclone's 100+ remotes (S3, GCS, Azure, SFTP,
WebDAV, local, …) without a FUSE mount.
- New SchemeKind::Rclone threaded through the scheme/URL type system,
mirroring Sftp (remote, virtual, Unix-path, byte-encoded path semantics).
- yazi-vfs rclone provider:
- read_dir via `rclone lsjson`
- metadata via `rclone lsjson --stat` (synthesized POSIX mode)
- seekable read-only File streaming `rclone cat --offset`; seek respawns
the child at the new offset. Detects premature EOF and unknown sizes.
- all write ops return Unsupported (read-only for now)
- `remote:/path` targets preserve the leading slash, so filesystem-like
backends (local, sftp) work alongside object stores.
- Config: [services.<name>] type = "rclone", remote = "..."
- Tests:
- tests/rclone_local.rs: hermetic, points an rclone `local` remote at a
temp fixture dir, so it needs no cloud/credentials and skips if `rclone`
isn't installed. Covers list, read, seek, missing-object, and a >8 MiB
parallel multi-chunk copy with position-varying bytes.
- tests/rclone_read.rs: env-driven live tests against a real remote
(ignored by default; paths supplied via env vars, nothing hard-coded).
4.1 KiB
Proposal: rclone-backed VFS provider (re: #3395)
STATUS: LOCAL DRAFT — not posted anywhere. This is the comment we'd put on issue #3395 once we decide to engage upstream. Nothing has been pushed or shared.
Summary
A read-only rclone:// VFS provider that shells out to the rclone CLI,
giving yazi native browsing of any of rclone's 100+ remotes (S3, GCS, Azure,
Backblaze, WebDAV, …) through a single provider — no FUSE/NFS mount. This is
the "integrate rclone" item on the #3395 roadmap, and reuses the VFS
infrastructure from #3821 / the (closed) S3 PR #3843.
A working proof-of-concept is implemented and verified against live GCS and S3 buckets (directory browsing, metadata, byte-exact streaming reads + seeks).
URL / scheme shape
rclone://<service>//<path>
<service> is a name defined in vfs.toml; it maps to an rclone remote.
One scheme covers every backend — the backend choice lives in rclone's own
config, not in yazi.
# ~/.config/yazi/vfs.toml
[services.gcs]
type = "rclone"
remote = "gcs" # an existing rclone remote (`rclone listremotes`)
[services.s3]
type = "rclone"
remote = "s3"
# binary = "/opt/homebrew/bin/rclone" # optional
# config_file = "/path/to/rclone.conf" # optional
# flags = ["--fast-list"] # optional extra args
Then: rclone://gcs//my-bucket/some/dir.
SchemeKind::Rclone mirrors Sftp — remote, virtual, Unix-path,
byte-encoded filenames — so it threads through the existing scheme/URL enums
with minimal new surface (mostly folded into existing Sftp match arms).
How each operation maps
| Provider op | rclone |
|---|---|
read_dir |
rclone lsjson <remote>:<path> |
metadata |
rclone lsjson --stat <remote>:<path> |
open/read |
rclone cat --offset <pos> <remote>:<path> |
| write/create/… | Unsupported (read-only v1) |
The AsyncSeek-over-a-CLI problem
Provider::File must be AsyncRead + AsyncSeek + AsyncWrite. rclone has no
persistent file handle, so the File type streams rclone cat from the
current offset; a seek kills the child process and the next read respawns
rclone cat --offset <new>. This makes the file seekable enough for yazi's
previewer and copy paths without any random-access protocol. Verified
byte-exact vs rclone cat for both full reads and post-seek tail reads.
Scope decisions (seeking maintainer input)
- Read-only first. Matches PR #3843's scope. Writes (
rcat/copyto) and mutations (deletefile,mkdir,moveto) are a clean follow-up but raise consistency/UX questions worth deciding separately. - CLI vs
rclone rcddaemon. The PoC spawns a subprocess per op (simple, no lifecycle). A long-livedrclone rcd+ HTTP API would cut per-op latency and enable a connection-pool model like the SFTP provider. Happy to go either way — which do you prefer? - Metadata. rclone gives
Size/ModTime/IsDirbut no uid/gid/perm/nlink; the PoC synthesizes0755/0644.Capabilitiesonly modelssymlinktoday, so read-only-ness surfaces as per-opUnsupported. Want awritable/read_onlycapability flag? - Pagination.
lsjsonreturns a whole directory as one JSON array (simple, but memory-heavy for very large dirs). Incremental listing would need--files-only/chunking or the rc daemon. Acceptable for v1? searchon remote schemes is currently disabled (per #3395) — this provider doesn't change that.
Rough edit surface
~40 files, but the vast majority are one-line enum/match additions folded
into existing Sftp arms. The real code is the ~6-file provider module in
yazi-vfs/src/provider/rclone/ plus config/rclone.rs. Diffstat of the
PoC: 44 files, ~790 insertions.
Open question for the maintainer
Before we polish this into a PR: does this scheme shape and the CLI-first (vs rcd-daemon) approach match what you discussed on Telegram? If the daemon model is preferred, we'll refactor the transport before submitting.