Python bindings for FUSE (Filesystem in USErspace) enabling custom userspace filesystems
—
Essential filesystem operations that form the foundation of any FUSE filesystem implementation. These methods handle basic file system functionality including attribute retrieval, directory operations, and file content access.
Retrieve and modify file and directory attributes including permissions, ownership, timestamps, and size information.
def getattr(self, path):
"""
Get file/directory attributes.
Args:
path (str): Path to file or directory
Returns:
Stat: File attributes object
int: Negative errno on error
"""
def chmod(self, path, mode):
"""
Change file permissions.
Args:
path (str): Path to file or directory
mode (int): New permission mode
Returns:
int: 0 on success, negative errno on error
"""
def chown(self, path, uid, gid):
"""
Change file ownership.
Args:
path (str): Path to file or directory
uid (int): New user ID
gid (int): New group ID
Returns:
int: 0 on success, negative errno on error
"""
def truncate(self, path, size):
"""
Truncate file to specified size.
Args:
path (str): Path to file
size (int): New file size in bytes
Returns:
int: 0 on success, negative errno on error
"""
def utime(self, path, times):
"""
Change file access and modification times.
Args:
path (str): Path to file or directory
times (tuple): (atime, mtime) tuple or None for current time
Returns:
int: 0 on success, negative errno on error
"""
def utimens(self, path, ts_acc, ts_mod):
"""
Change file timestamps with nanosecond precision.
Args:
path (str): Path to file or directory
ts_acc (Timespec): Access time specification
ts_mod (Timespec): Modification time specification
Returns:
int: 0 on success, negative errno on error
"""Usage Example:
def getattr(self, path):
st = fuse.Stat()
if path == '/':
st.st_mode = stat.S_IFDIR | 0o755
st.st_nlink = 2
st.st_size = 4096
elif path in self.files:
st.st_mode = stat.S_IFREG | 0o644
st.st_nlink = 1
st.st_size = len(self.files[path])
else:
return -errno.ENOENT
# Set timestamps
st.st_atime = st.st_mtime = st.st_ctime = time.time()
return stHandle directory listing, creation, and navigation operations.
def readdir(self, path, offset):
"""
Read directory contents.
Args:
path (str): Path to directory
offset (int): Starting offset for reading (typically 0)
Yields:
Direntry: Directory entry objects for each item
"""
def opendir(self, path):
"""
Open directory for reading.
Args:
path (str): Path to directory
Returns:
int: 0 on success, negative errno on error
"""
def releasedir(self, path):
"""
Release (close) directory.
Args:
path (str): Path to directory
Returns:
int: 0 on success, negative errno on error
"""
def fsyncdir(self, path, datasync):
"""
Synchronize directory contents.
Args:
path (str): Path to directory
datasync (bool): If True, sync only data, not metadata
Returns:
int: 0 on success, negative errno on error
"""Usage Example:
def readdir(self, path, offset):
# Always include . and .. entries
yield fuse.Direntry('.')
yield fuse.Direntry('..')
# Add directory contents
if path == '/':
for filename in self.files:
yield fuse.Direntry(filename.lstrip('/'))Read and write file content, with support for arbitrary offsets and partial operations.
def open(self, path, flags):
"""
Open file for reading/writing.
Args:
path (str): Path to file
flags (int): Open flags (O_RDONLY, O_WRONLY, O_RDWR, etc.)
Returns:
int: 0 on success, negative errno on error
"""
def read(self, path, size, offset):
"""
Read file content.
Args:
path (str): Path to file
size (int): Number of bytes to read
offset (int): Byte offset to start reading from
Returns:
bytes: File content
int: Negative errno on error
"""
def write(self, path, buf, offset):
"""
Write file content.
Args:
path (str): Path to file
buf (bytes): Data to write
offset (int): Byte offset to start writing at
Returns:
int: Number of bytes written on success, negative errno on error
"""
def flush(self, path):
"""
Flush cached data for file (called on each close() of a file descriptor).
Args:
path (str): Path to file
Returns:
int: 0 on success, negative errno on error
Note:
This is called for every close() of a file descriptor, not just
when the file is finally released. Can be used to write back
dirty data before the file is closed.
"""
def release(self, path, flags):
"""
Release (close) file.
Args:
path (str): Path to file
flags (int): Open flags used when file was opened
Returns:
int: 0 on success, negative errno on error
"""
def fsync(self, path, datasync):
"""
Synchronize file contents.
Args:
path (str): Path to file
datasync (bool): If True, sync only data, not metadata
Returns:
int: 0 on success, negative errno on error
"""Usage Example:
def read(self, path, size, offset):
if path not in self.files:
return -errno.ENOENT
content = self.files[path]
return content[offset:offset + size]
def write(self, path, buf, offset):
if path not in self.files:
self.files[path] = b''
# Extend file if necessary
if offset + len(buf) > len(self.files[path]):
self.files[path] += b'\0' * (offset + len(buf) - len(self.files[path]))
# Write data
content = bytearray(self.files[path])
content[offset:offset + len(buf)] = buf
self.files[path] = bytes(content)
return len(buf)Retrieve overall filesystem statistics and information.
def statfs(self, path):
"""
Get filesystem statistics.
Args:
path (str): Path within filesystem
Returns:
StatVfs: Filesystem statistics object
int: Negative errno on error
"""Usage Example:
def statfs(self, path):
stv = fuse.StatVfs()
stv.f_bsize = 4096 # Block size
stv.f_frsize = 4096 # Fragment size
stv.f_blocks = 1000000 # Total blocks
stv.f_bfree = 500000 # Free blocks
stv.f_bavail = 500000 # Available blocks
stv.f_files = 100000 # Total inodes
stv.f_ffree = 50000 # Free inodes
stv.f_favail = 50000 # Available inodes
stv.f_namemax = 255 # Maximum filename length
return stvCore operations should handle errors consistently:
-errno.ENOENT, -errno.EACCES)ENOENT: File or directory not foundEACCES: Permission deniedEISDIR: Is a directory (when file expected)ENOTDIR: Not a directory (when directory expected)EEXIST: File or directory already existsfgetattr and ftruncate variants when file handles are availableInstall with Tessl CLI
npx tessl i tessl/pypi-fuse-python