Advent of code 2022/7
Ajax Direct

Answer

Part 1 :
Part 2 :
// Keep only usefull lines : cd and sizes
$input = $input->pregReplace("/\n(?!(?:\\$ cd)|(?:[0-9]+))[^\n]+/", "");

// Remove "$ cd" and use "~" instead of "/" for root because of reasons
$input = $input->replace(["$ cd /", "$ cd "], ["~", ""]);

// Create an index of all the directories
$cwd = "";
$index = $input->lines->reduce(function ($index, $line) use (&$cwd) {

    // If not a number, change directory
    if (!$line->int) {
        $cwd .= $line . "/";
        $cwd = preg_replace("/\/[^\/]+\/\.\./", "", $cwd); // Go back for each ../
        return $index;
    }

    // Else, add the size to the current directory and to all its parents
    $adding_to = "";
    foreach (explode("/", trim($cwd, "/")) as $dir) {
        $adding_to .= $dir . "/";
        $index[$adding_to] = empty($index[$adding_to]) ? $line->int : $index[$adding_to] + $line->int;
    }

    return $index;
}, set([]));

// ==================================================
// > SOLUTIONS
// ==================================================
$solution_1 = $index->filter(fn ($size) => $size < 100000)->sum();
$solution_2 = $index->filter(fn ($size) => 70000000 - ($index["~/"] - $size) >= 30000000)->sort()->first();