From 512f2570aa2267040b8678e74a9e13e52f45be4a Mon Sep 17 00:00:00 2001 From: Dimitri Papadopoulos <3234522+DimitriPapadopoulos@users.noreply.github.com> Date: Sat, 24 May 2025 15:13:02 +0200 Subject: [PATCH 1/6] Enforce ruff rule RUF012 RUF012 Mutable class attributes should be annotated with `typing.ClassVar` --- fsspec/gui.py | 17 +++++++++++++---- fsspec/implementations/memory.py | 4 ++-- fsspec/implementations/tests/conftest.py | 2 +- fsspec/implementations/tests/test_archive.py | 4 ++-- fsspec/tests/conftest.py | 5 +++-- pyproject.toml | 1 + 6 files changed, 22 insertions(+), 11 deletions(-) diff --git a/fsspec/gui.py b/fsspec/gui.py index 321379eb8..9ec465b63 100644 --- a/fsspec/gui.py +++ b/fsspec/gui.py @@ -169,8 +169,17 @@ def show(self, threads=False): class SingleSelect(SigSlot): """A multiselect which only allows you to select one item for an event""" - signals = ["_selected", "selected"] # the first is internal - slots = ["set_options", "set_selection", "add", "clear", "select"] + signals: ClassVar[Sequence[str]] = [ + "_selected", + "selected", + ] # the first is internal + slots: ClassVar[Sequence[str]] = [ + "set_options", + "set_selection", + "add", + "clear", + "select", + ] def __init__(self, **kwargs): self.kwargs = kwargs @@ -212,7 +221,7 @@ class FileSelector(SigSlot): them as the output of a cell, or in a separate browser tab using ``.show()``. """ - signals = [ + signals: ClassVar[Sequence[str]] = [ "protocol_changed", "selection_changed", "directory_entered", @@ -221,7 +230,7 @@ class FileSelector(SigSlot): "go_clicked", "filters_changed", ] - slots = ["set_filters", "go_home"] + slots: ClassVar[Sequence[str]] = ["set_filters", "go_home"] def __init__(self, url=None, filters=None, ignore=None, kwargs=None): """ diff --git a/fsspec/implementations/memory.py b/fsspec/implementations/memory.py index c1c526b56..37fbc24c4 100644 --- a/fsspec/implementations/memory.py +++ b/fsspec/implementations/memory.py @@ -5,7 +5,7 @@ from errno import ENOTEMPTY from io import BytesIO from pathlib import PurePath, PureWindowsPath -from typing import Any, ClassVar +from typing import Any, ClassVar, Sequence from fsspec import AbstractFileSystem from fsspec.implementations.local import LocalFileSystem @@ -22,7 +22,7 @@ class MemoryFileSystem(AbstractFileSystem): """ store: ClassVar[dict[str, Any]] = {} # global, do not overwrite! - pseudo_dirs = [""] # global, do not overwrite! + pseudo_dirs: ClassVar[Sequence[str]] = [""] # global, do not overwrite! protocol = "memory" root_marker = "/" diff --git a/fsspec/implementations/tests/conftest.py b/fsspec/implementations/tests/conftest.py index 7dce3ee4e..d71c31032 100644 --- a/fsspec/implementations/tests/conftest.py +++ b/fsspec/implementations/tests/conftest.py @@ -10,7 +10,7 @@ class MultiProtocolFileSystem(LocalFileSystem): - protocol = ["file", "other"] + protocol = ("file", "other") FILESYSTEMS = { diff --git a/fsspec/implementations/tests/test_archive.py b/fsspec/implementations/tests/test_archive.py index 457714b39..dce41a4f2 100644 --- a/fsspec/implementations/tests/test_archive.py +++ b/fsspec/implementations/tests/test_archive.py @@ -214,14 +214,14 @@ class TestAnyArchive: will adhere to the same specification. """ - scenarios = [ + scenarios = ( scenario_zip, scenario_tar, scenario_targz, scenario_tarbz2, scenario_tarxz, scenario_libarchive, - ] + ) def test_repr(self, scenario: ArchiveTestScenario): with scenario.provider() as archive: diff --git a/fsspec/tests/conftest.py b/fsspec/tests/conftest.py index ccf7bdccf..7daaed062 100644 --- a/fsspec/tests/conftest.py +++ b/fsspec/tests/conftest.py @@ -6,6 +6,7 @@ from collections import ChainMap from http.server import BaseHTTPRequestHandler, HTTPServer from types import SimpleNamespace +from typing import ClassVar import pytest @@ -45,7 +46,7 @@ def reset_files(): class HTTPTestHandler(BaseHTTPRequestHandler): - static_files = { + static_files: ClassVar[dict[str, bytes]] = { "/index/realfile": data, "/index/otherfile": data, "/index": _make_index_listing, @@ -55,7 +56,7 @@ class HTTPTestHandler(BaseHTTPRequestHandler): "/simple/dir/": _make_listing("/simple/dir/file"), "/simple/dir/file": data, } - dynamic_files = {} + dynamic_files: ClassVar[dict[str, bytes]] = {} files = ChainMap(dynamic_files, static_files) diff --git a/pyproject.toml b/pyproject.toml index c00e3069b..c78aeba0e 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -178,6 +178,7 @@ select = [ # "PT", enable in later PR "PYI", "RUF006", + "RUF012", "RUF015", "RUF024", "SIM", From 21eab419e20c6127a5a4bff5c7410ce7b8e9f01b Mon Sep 17 00:00:00 2001 From: Dimitri Papadopoulos <3234522+DimitriPapadopoulos@users.noreply.github.com> Date: Sat, 24 May 2025 14:54:40 +0200 Subject: [PATCH 2/6] Enforce ruff rule RUF019 RUF019 Unnecessary key check before dictionary access --- fsspec/implementations/gist.py | 8 ++++---- pyproject.toml | 1 + 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/fsspec/implementations/gist.py b/fsspec/implementations/gist.py index 74117b544..8f302768f 100644 --- a/fsspec/implementations/gist.py +++ b/fsspec/implementations/gist.py @@ -141,16 +141,16 @@ def _get_kwargs_from_urls(path): """ so = infer_storage_options(path) out = {} - if "username" in so and so["username"]: + if so.get("username"): out["username"] = so["username"] - if "password" in so and so["password"]: + if so.get("password"): out["token"] = so["password"] - if "host" in so and so["host"]: + if so.get("host"): # We interpret 'host' as the gist ID out["gist_id"] = so["host"] # Extract SHA and filename from path - if "path" in so and so["path"]: + if so.get("path"): path_parts = so["path"].rsplit("/", 2)[-2:] if len(path_parts) == 2: if path_parts[0]: # SHA present diff --git a/pyproject.toml b/pyproject.toml index c78aeba0e..a22199c06 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -180,6 +180,7 @@ select = [ "RUF006", "RUF012", "RUF015", + "RUF019", "RUF024", "SIM", "SLOT", From d4515b181bbed8ad47f789ba84f1dbd3ca0d21df Mon Sep 17 00:00:00 2001 From: Dimitri Papadopoulos <3234522+DimitriPapadopoulos@users.noreply.github.com> Date: Sat, 12 Oct 2024 20:54:28 +0200 Subject: [PATCH 3/6] Enforce ruff rule RUF022 RUF022 `__all__` is not sorted --- fsspec/__init__.py | 12 ++++++------ fsspec/registry.py | 2 +- pyproject.toml | 1 + 3 files changed, 8 insertions(+), 7 deletions(-) diff --git a/fsspec/__init__.py b/fsspec/__init__.py index 452c78a05..183564af0 100644 --- a/fsspec/__init__.py +++ b/fsspec/__init__.py @@ -16,21 +16,21 @@ __all__ = [ "AbstractFileSystem", - "FSTimeoutError", + "Callback", "FSMap", + "FSTimeoutError", + "available_compressions", + "available_protocols", + "caching", "filesystem", - "register_implementation", "get_filesystem_class", "get_fs_token_paths", "get_mapper", "open", "open_files", "open_local", + "register_implementation", "registry", - "caching", - "Callback", - "available_protocols", - "available_compressions", "url_to_fs", ] diff --git a/fsspec/registry.py b/fsspec/registry.py index e26291117..86d554688 100644 --- a/fsspec/registry.py +++ b/fsspec/registry.py @@ -4,7 +4,7 @@ import types import warnings -__all__ = ["registry", "get_filesystem_class", "default"] +__all__ = ["default", "get_filesystem_class", "registry"] # internal, mutable _registry: dict[str, type] = {} diff --git a/pyproject.toml b/pyproject.toml index a22199c06..6acb80db5 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -181,6 +181,7 @@ select = [ "RUF012", "RUF015", "RUF019", + "RUF022", "RUF024", "SIM", "SLOT", From 16f8c8a3b6022db7f88ee36da0c2d13fc8e62931 Mon Sep 17 00:00:00 2001 From: Dimitri Papadopoulos <3234522+DimitriPapadopoulos@users.noreply.github.com> Date: Sat, 24 May 2025 14:49:38 +0200 Subject: [PATCH 4/6] Enforce ruff rule RUF046 RUF046 Value being cast to `int` is already an integer --- fsspec/utils.py | 2 +- pyproject.toml | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/fsspec/utils.py b/fsspec/utils.py index 917af8d19..1aa30e4c2 100644 --- a/fsspec/utils.py +++ b/fsspec/utils.py @@ -174,7 +174,7 @@ def build_name_function(max_int: float) -> Callable[[int], str]: # handle corner cases max_int is 0 or exact power of 10 max_int += 1e-8 - pad_length = int(math.ceil(math.log10(max_int))) + pad_length = math.ceil(math.log10(max_int)) def name_function(i: int) -> str: return str(i).zfill(pad_length) diff --git a/pyproject.toml b/pyproject.toml index 6acb80db5..e76c73712 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -183,6 +183,7 @@ select = [ "RUF019", "RUF022", "RUF024", + "RUF046", "SIM", "SLOT", "SIM101", From acc3f6fecf0d41725694eb3cb51b2411bc42bb3b Mon Sep 17 00:00:00 2001 From: Dimitri Papadopoulos <3234522+DimitriPapadopoulos@users.noreply.github.com> Date: Tue, 11 Mar 2025 22:51:46 +0100 Subject: [PATCH 5/6] Enforce ruff rule RUF100 RUF100 Unused `noqa` directive --- fsspec/implementations/http.py | 6 +++--- pyproject.toml | 3 +-- 2 files changed, 4 insertions(+), 5 deletions(-) diff --git a/fsspec/implementations/http.py b/fsspec/implementations/http.py index 7386d4b80..a724ac64a 100644 --- a/fsspec/implementations/http.py +++ b/fsspec/implementations/http.py @@ -254,7 +254,7 @@ async def _get_file( if isfilelike(lpath): outfile = lpath else: - outfile = open(lpath, "wb") # noqa: ASYNC101, ASYNC230 + outfile = open(lpath, "wb") # noqa: ASYNC230 try: chunk = True @@ -286,7 +286,7 @@ async def gen_chunks(): context = nullcontext(lpath) use_seek = False # might not support seeking else: - context = open(lpath, "rb") # noqa: ASYNC101, ASYNC230 + context = open(lpath, "rb") # noqa: ASYNC230 use_seek = True with context as f: @@ -812,7 +812,7 @@ async def get_range(session, url, start, end, file=None, **kwargs): async with r: out = await r.read() if file: - with open(file, "r+b") as f: # noqa: ASYNC101, ASYNC230 + with open(file, "r+b") as f: # noqa: ASYNC230 f.seek(start) f.write(out) else: diff --git a/pyproject.toml b/pyproject.toml index e76c73712..4f9878e26 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -180,10 +180,9 @@ select = [ "RUF006", "RUF012", "RUF015", - "RUF019", - "RUF022", "RUF024", "RUF046", + "RUF100", "SIM", "SLOT", "SIM101", From 91fb841c5ca8b4b873a3c5112c4aed53772acb44 Mon Sep 17 00:00:00 2001 From: Dimitri Papadopoulos <3234522+DimitriPapadopoulos@users.noreply.github.com> Date: Sat, 24 May 2025 15:18:16 +0200 Subject: [PATCH 6/6] Enforce ruff rules (RUF) --- pyproject.toml | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/pyproject.toml b/pyproject.toml index 4f9878e26..0aa789a6b 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -177,12 +177,7 @@ select = [ "PIE810", # "PT", enable in later PR "PYI", - "RUF006", - "RUF012", - "RUF015", - "RUF024", - "RUF046", - "RUF100", + "RUF", "SIM", "SLOT", "SIM101", @@ -216,6 +211,8 @@ ignore = [ "UP011", "UP015", "UP018", + "RUF001", + "RUF005", "SIM102", "SIM105", "SIM108",