Skip to content

IsChildOf/IsParentOf return false for every path directly under a filesystem root ("/home" vs "/", "C:\foo" vs "C:\") #282

Description

@matt-edmondson

What's wrong

The span-based IsChildOf in Semantics.Paths/Implementations/AbsoluteDirectoryPath.cs (~lines 218-228) checks for a prefix match. It then requires a directory separator at thisPath[parent.Length]. IsParentOf delegates to the same logic, and AbsoluteFilePath.IsChildOf has an equivalent check.

A filesystem root already ends in a separator (/, C:\). For a path directly under a root, the character at parent.Length is therefore the first letter of the child's name, not a separator, so the check fails.

Reproduction

(Linux; the same happens on Windows with C:\foo and C:\.)

var root = AbsoluteDirectoryPath.Create<AbsoluteDirectoryPath>("/");
var home = AbsoluteDirectoryPath.Create<AbsoluteDirectoryPath>("/home");
home.IsChildOf(root);   // False, expected True
root.IsParentOf(home);  // False, expected True
AbsoluteFilePath.Create<AbsoluteFilePath>("/etc.txt").IsChildOf(root); // False, expected True

The type contradicts itself: home.Parent returns /, and GetAncestors() yields /. Deeper paths such as /home/user under /home work correctly.

Why it matters

Containment checks are a typical guard, for example "is this file inside the chosen directory?". They give the wrong answer whenever the user picks a drive or filesystem root, which is a common choice.

Suggested fix / acceptance criteria

  • After the prefix match, return true when the parent ends in a separator (Path.EndsInDirectorySeparator(parentPathSpan)) and the child is longer. Otherwise keep the existing next-character check.
  • Apply the change to both AbsoluteDirectoryPath and AbsoluteFilePath.
  • Add tests for /home vs /, /etc.txt vs /, and (Windows-conditional) C:\foo vs C:\. Add a negative test that /home2 is not a child of /home.

Confirmed by running against main (8c06aba) on Linux.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Labels

bugSomething isn't working

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions