($node->key->value ?? null) === $key ); } /** * @param Expr\ArrayItem[] $arrayItems * @param string $key * * @return bool */ protected function hasItem(array $arrayItems, string $key): bool { return boolval($this->getItem($arrayItems, $key)); } protected function expressionNodeIsArray(Expr $expressionNode): bool { return $expressionNode instanceof Expr\Array_; } /** * @param Expr\ArrayItem[] $arrayItems * * @return bool */ protected function arrayIsList(array $arrayItems): bool { // List arrays, like ['a', 'b', 'c'] have all `key`s as null when parsed return isset($arrayItems[0]) && $arrayItems[0]->key === null; } /** * Get values in $list that are not in $otherList. * Replaces array_diff($list, $otherList) * * @template T of Node * @param T[] $list * @param T[] $otherList * * @return array */ protected function subtractOtherListFromList(array $list, array $otherList): array { $diff = []; // There's no easy way to compare two AST nodes for equality // So we'll just convert them to strings and check if they're equal $otherListWithItemsAsText = array_map( fn($item) => $this->convertAstNodesToText($item), $otherList ); foreach ($list as $item) { $itemAsText = $this->convertAstNodesToText($item); if (!in_array($itemAsText, $otherListWithItemsAsText)) { $diff[] = ['ast' => $item, 'text' => $itemAsText]; } } return $diff; } /** * @param Node[]|Node $nodes * * @return string */ protected function convertAstNodesToText($nodes): string { return (new NodeDumper())->dump($nodes); } }