category; } public function getSubCategory(): string { return $this->subCategory; } public function getValue(): string { return $this->value; } public function getName(): string { return $this->name; } } class TestResourceWithEnum { public function __construct( private TestEnum $category, private string $name = 'default' ) { } public function getCategory(): TestEnum { return $this->category; } public function getName(): string { return $this->name; } } enum TestEnum: string { case CATEGORY_A = 'category-a'; case CATEGORY_B = 'category-b'; } // Classe testable pour accéder aux méthodes protected class TestableResourceTreeBuilder extends ResourceTreeBuilder { public static function callGetterPublic($object, $propName): string { return parent::callGetter($object, $propName); } } class ResourceTreeBuilderTest extends TestCase { private function getResourceTreeBuilderMockFor(string $methodName): TestableResourceTreeBuilder|MockObject { return $this->getMockBuilder(TestableResourceTreeBuilder::class) ->setMethodsExcept([$methodName]) ->getMock(); } /** * @see ResourceTreeBuilder::makeTree() */ public function testMakeTree(): void { $data = [ new TestResource('category1', 'sub1', 'item1'), new TestResource('category1', 'sub1', 'item2'), new TestResource('category1', 'sub2', 'item3'), new TestResource('category2', 'sub3', 'item4'), ]; $result = ResourceTreeBuilder::makeTree($data, 'category', 'subCategory', 'value'); $expected = [ 'category1' => [ 'sub1' => ['item1', 'item2'], 'sub2' => ['item3'], ], 'category2' => [ 'sub3' => ['item4'], ], ]; self::assertEquals($expected, $result); } /** * @see ResourceTreeBuilder::makeTree() */ public function testMakeTreeWithOneLevel(): void { $data = [ new TestResource('category1', 'sub1', 'item1', 'name1'), new TestResource('category2', 'sub2', 'item2', 'name2'), new TestResource('category1', 'sub3', 'item3', 'name3'), ]; $result = ResourceTreeBuilder::makeTree($data); $expected = ['name1', 'name2', 'name3']; self::assertEquals($expected, $result); } /** * @see ResourceTreeBuilder::makeTree() */ public function testMakeTreeWithTwoLevels(): void { $data = [ new TestResource('category1', 'sub1', 'item1'), new TestResource('category1', 'sub2', 'item2'), new TestResource('category2', 'sub1', 'item3'), ]; $result = ResourceTreeBuilder::makeTree($data, 'category', 'subCategory'); $expected = [ 'category1' => ['sub1', 'sub2'], 'category2' => ['sub1'], ]; self::assertEquals($expected, $result); } /** * @see ResourceTreeBuilder::makeTree() */ public function testMakeTreeWithEmptyData(): void { $result = ResourceTreeBuilder::makeTree([]); self::assertEquals([], $result); } /** * @see ResourceTreeBuilder::callGetter() */ public function testCallGetter(): void { $resource = new TestResource('cat1', 'sub1', 'val1'); $result = TestableResourceTreeBuilder::callGetterPublic($resource, 'category'); self::assertEquals('cat1', $result); } /** * @see ResourceTreeBuilder::callGetter() */ public function testCallGetterWithEnum(): void { $resource = new TestResourceWithEnum(TestEnum::CATEGORY_A); $result = TestableResourceTreeBuilder::callGetterPublic($resource, 'category'); self::assertEquals('category-a', $result); } /** * @see ResourceTreeBuilder::callGetter() */ public function testCallGetterWithInvalidProperty(): void { $resource = new TestResource('cat1', 'sub1', 'val1'); $this->expectException(\InvalidArgumentException::class); $this->expectExceptionMessage('Invalid property name'); TestableResourceTreeBuilder::callGetterPublic($resource, 'invalidProperty'); } /** * @see ResourceTreeBuilder::makeTree() */ public function testMakeTreeWithDuplicateEntries(): void { $data = [ new TestResource('category1', 'sub1', 'item1'), new TestResource('category1', 'sub1', 'item1'), // Duplicate new TestResource('category1', 'sub1', 'item2'), ]; $result = ResourceTreeBuilder::makeTree($data, 'category', 'subCategory', 'value'); $expected = [ 'category1' => [ 'sub1' => ['item1', 'item2'], ], ]; self::assertEquals($expected, $result); } }