From a758173dfabf60392de4e7c7cbfa317f2c02bb9a Mon Sep 17 00:00:00 2001 From: Gauthier BERTHOMIEU Date: Wed, 21 Oct 2026 18:06:29 +0200 Subject: [PATCH 1/4] add failing test for serialize path with symlink --- tests/test_serialization.py | 24 +++++++++++++++++------- 1 file changed, 17 insertions(+), 7 deletions(-) diff --git a/tests/test_serialization.py b/tests/test_serialization.py index 9bded198..da8d86aa 100644 --- a/tests/test_serialization.py +++ b/tests/test_serialization.py @@ -1052,14 +1052,24 @@ def test_spectro_dataset_serialization( """ -def can_symlink(tmp_path: Path) -> bool: +def test_serialize_path_with_symlink(tmp_path: Path) -> None: + real_root = tmp_path / "cocteau" + real_root.mkdir(parents=True, exist_ok=True) + + alias_root = tmp_path / "twins" + try: - test_link = tmp_path / "link_test" - test_link.symlink_to(tmp_path) - test_link.unlink() - except OSError: - return False - return True + alias_root.symlink_to(real_root) + except (OSError, NotImplementedError) as e: + pytest.skip(f"Symlink not permitted on this system:\n{e}") + + target = "serpentskirt" + + target_path = alias_root / target + + result = _serialize_path(value=target_path, root_path=real_root) + + assert result == target def test_path_anchor() -> None: From 315683011269f50036f6fed2bc18e898336fe563 Mon Sep 17 00:00:00 2001 From: Gauthier BERTHOMIEU Date: Wed, 21 Oct 2026 18:07:57 +0200 Subject: [PATCH 2/4] fix serialize_path() with relative paths that include symlinks --- src/osekit/core/json_serializer.py | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/osekit/core/json_serializer.py b/src/osekit/core/json_serializer.py index fdbfc8b9..9770a799 100644 --- a/src/osekit/core/json_serializer.py +++ b/src/osekit/core/json_serializer.py @@ -64,7 +64,10 @@ def _serialize_path(value: Path, root_path: Path) -> str: # Path is outside the project: we store it as an absolute path. return value.as_posix() try: - return Path(os.path.relpath(path=value, start=root_path)).as_posix() + # Return value relative to the root_path + return Path( + os.path.relpath(path=value.resolve(), start=root_path.resolve()) + ).as_posix() except ValueError: # Value is not expressible as relative to root return value.as_posix() From dacf3b3260bcf25b1e6ea7257a0db00b9faeae3d Mon Sep 17 00:00:00 2001 From: Gauthier BERTHOMIEU Date: Wed, 21 Oct 2026 18:15:22 +0200 Subject: [PATCH 3/4] add failing test for _serialize_path with symlinked anchor --- tests/test_serialization.py | 27 ++++++++++++++++++++++++++- 1 file changed, 26 insertions(+), 1 deletion(-) diff --git a/tests/test_serialization.py b/tests/test_serialization.py index da8d86aa..385ba7ff 100644 --- a/tests/test_serialization.py +++ b/tests/test_serialization.py @@ -1052,7 +1052,8 @@ def test_spectro_dataset_serialization( """ -def test_serialize_path_with_symlink(tmp_path: Path) -> None: +@pytest.fixture +def create_symlink(tmp_path: Path) -> tuple[Path, Path]: real_root = tmp_path / "cocteau" real_root.mkdir(parents=True, exist_ok=True) @@ -1063,6 +1064,15 @@ def test_serialize_path_with_symlink(tmp_path: Path) -> None: except (OSError, NotImplementedError) as e: pytest.skip(f"Symlink not permitted on this system:\n{e}") + return real_root, alias_root + + +def test_serialize_path_with_symlink( + tmp_path: Path, + create_symlink: tuple[Path, Path], +) -> None: + real_root, alias_root = create_symlink + target = "serpentskirt" target_path = alias_root / target @@ -1146,6 +1156,21 @@ def test_serialize_path_within_anchor(tmp_path: Path) -> None: assert _serialize_path(value=value, root_path=root_path) == expected +def test_serialize_path_within_anchor_with_symlink( + tmp_path: Path, create_symlink: tuple[Path, Path] +) -> None: + real_root, alias_root = create_symlink + + target = "fun" + + value = alias_root / target + + with path_anchor(anchor=real_root): + # Anchor is real_root, which should also be alias_root + # So the path should be serialized as relative + assert _serialize_path(value=value, root_path=alias_root) == target + + def test_serialize_path_outside_anchor(tmp_path: Path) -> None: value = tmp_path / "fun" / "top.wav" anchor = tmp_path / "cool" From 19ef02aa1437f051d3deacefa10bef72a863170f Mon Sep 17 00:00:00 2001 From: Gauthier BERTHOMIEU Date: Wed, 21 Oct 2026 18:15:40 +0200 Subject: [PATCH 4/4] fix _serialize_path with symlinked anchor --- src/osekit/core/json_serializer.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/osekit/core/json_serializer.py b/src/osekit/core/json_serializer.py index 9770a799..52b50dac 100644 --- a/src/osekit/core/json_serializer.py +++ b/src/osekit/core/json_serializer.py @@ -60,7 +60,7 @@ def _serialize_path(value: Path, root_path: Path) -> str: return str(value) anchor = _anchor.get() - if anchor is not None and not value.is_relative_to(anchor): + if anchor is not None and not value.resolve().is_relative_to(anchor.resolve()): # Path is outside the project: we store it as an absolute path. return value.as_posix() try: