FileTreeUtil { public static boolean isSameOrUnder(@Nullable FilePath parent, @NotNull FilePath child) { return getPathDepth(child, parent) >= 0; }  @NotNull static List<FilePath> getTree(@NotNull FilePath path); @Nullable static List<FilePath> getTreeTo(@NotNull FilePath path, @Nullable FilePath parent); @Nullable static List<VirtualFile> getTreeTo(@NotNull VirtualFile path, @Nullable VirtualFile parent); static int getPathDepth(@NotNull FilePath path, @Nullable FilePath parent); static int getPathDepth(@NotNull VirtualFile path, @Nullable VirtualFile parent); static int getPathDepth(@NotNull FilePath path, @Nullable VirtualFile parent); static boolean isSameOrUnder(@Nullable FilePath parent, @NotNull FilePath child); static boolean isSameOrUnder(@Nullable VirtualFile parent, @NotNull FilePath child); @Nullable static FilePath getCommonRoot(@NotNull Collection<FilePath> files);  }
@Test void isSameOrUnder() { Map<String, MockVirtualFile> vfs = MockVirtualFileSystem.createTree( "one/two/three/four/five.txt", "contents", "root.txt", "contents", "one/root.txt", "contents", "two/root.txt", "contents", "other/file.txt", "contents" ); FilePath five = vfs.get("one/two/three/four/five.txt").asFilePath(); FilePath other = vfs.get("other/file.txt").asFilePath(); assertFalse(FileTreeUtil.isSameOrUnder(five, other)); assertFalse(FileTreeUtil.isSameOrUnder(other, five)); assertFalse(FileTreeUtil.isSameOrUnder((FilePath) null, five)); assertFalse(FileTreeUtil.isSameOrUnder((VirtualFile) null, five)); assertTrue(FileTreeUtil.isSameOrUnder(five.getParentPath(), five)); assertTrue(FileTreeUtil.isSameOrUnder(five.getParentPath().getParentPath(), five)); assertTrue(FileTreeUtil.isSameOrUnder(five.getParentPath().getParentPath().getParentPath(), five)); assertTrue(FileTreeUtil.isSameOrUnder(five.getParentPath().getParentPath().getParentPath().getParentPath(), five)); }