diff --git a/src/BigCommerce/Catalog/CategoriesApi.php b/src/BigCommerce/Catalog/CategoriesApi.php index 95845e40..c1a6804f 100644 --- a/src/BigCommerce/Catalog/CategoriesApi.php +++ b/src/BigCommerce/Catalog/CategoriesApi.php @@ -8,12 +8,15 @@ use BigCommerce\ApiV3\ResourceModels\Catalog\Category\Category; use BigCommerce\ApiV3\ResponseModels\Category\CategoriesResponse; use BigCommerce\ApiV3\ResponseModels\Category\CategoryResponse; +use BigCommerce\ApiV3\ResponseModels\Category\CategoryTreeResponse; +use GuzzleHttp\RequestOptions; class CategoriesApi extends ResourceApi { private const RESOURCE_NAME = 'categories'; private const CATEGORIES_ENDPOINT = 'catalog/categories'; private const CATEGORY_ENDPOINT = 'catalog/categories/%d'; + private const CATEGORY_TREE_ENDPOINT = 'catalog/categories/tree'; public function image(): CategoryImageApi { @@ -30,6 +33,15 @@ public function getAll(array $filters = [], int $page = 1, int $limit = 250): Ca return new CategoriesResponse($this->getAllResources($filters, $page, $limit)); } + public function getCategoryTree(): CategoryTreeResponse + { + $response = $this->getClient()->getRestClient()->get( + self::CATEGORY_TREE_ENDPOINT + ); + + return new CategoryTreeResponse($response); + } + public function getAllPages(array $filter = []): CategoriesResponse { return CategoriesResponse::buildFromAllPages(function ($page) use ($filter) { diff --git a/src/BigCommerce/ResourceModels/Catalog/Category/CategoryTreeBranch.php b/src/BigCommerce/ResourceModels/Catalog/Category/CategoryTreeBranch.php new file mode 100644 index 00000000..7f18b734 --- /dev/null +++ b/src/BigCommerce/ResourceModels/Catalog/Category/CategoryTreeBranch.php @@ -0,0 +1,32 @@ +children as $categoryData) { + $this->children[] = $categoryData instanceof CategoryTreeBranch ? $categoryData : new CategoryTreeBranch($categoryData); + } + + unset($optionObject->children); + parent::__construct($optionObject); + } +} diff --git a/src/BigCommerce/ResponseModels/Category/CategoryTreeResponse.php b/src/BigCommerce/ResponseModels/Category/CategoryTreeResponse.php new file mode 100644 index 00000000..7ee4676a --- /dev/null +++ b/src/BigCommerce/ResponseModels/Category/CategoryTreeResponse.php @@ -0,0 +1,37 @@ +getBody(); + $rawData = json_decode($body); + $this->decodeResponseData($rawData); + } + + private function decodeResponseData($rawData): void + { + $this->categoryTree = array_map(function (\stdClass $c) { + return new CategoryTreeBranch($c); + }, $rawData->data); + } + + /** + * @return CategoryTreeBranch[] + */ + public function getTree(): array + { + return $this->categoryTree; + } +} \ No newline at end of file diff --git a/tests/BigCommerce/Catalog/CategoriesApiTest.php b/tests/BigCommerce/Catalog/CategoriesApiTest.php index b8437f09..c102ef36 100644 --- a/tests/BigCommerce/Catalog/CategoriesApiTest.php +++ b/tests/BigCommerce/Catalog/CategoriesApiTest.php @@ -3,6 +3,7 @@ namespace BigCommerce\Tests\Catalog; use BigCommerce\ApiV3\Catalog\Categories\CategoryImageApi; +use BigCommerce\ApiV3\ResourceModels\Catalog\Category\CategoryTreeBranch; use BigCommerce\Tests\BigCommerceApiTest; class CategoriesApiTest extends BigCommerceApiTest @@ -43,4 +44,82 @@ public function testCanGetAllCategoryPages(): void $this->assertEquals(6, $categoriesResponse->getPagination()->total); $this->assertCount(6, $categoriesResponse->getCategories()); } + + public function testCanGetCategoryTree(): void + { + $this->setReturnData('catalog__categories__get_tree.json'); + + $expectedTree = [ + new CategoryTreeBranch((object)[ + "id" => 23, + "parent_id" => 0, + "name" => "Shop All", + "is_visible" => true, + "url" => "/shop-all/", + "children" => [], + ]), + new CategoryTreeBranch((object)[ + "id" => 18, + "parent_id" => 0, + "name" => "Bath", + "is_visible" => true, + "url" => "/bath/", + "children" => [ + new CategoryTreeBranch((object)[ + "id" => 24, + "parent_id" => 18, + "name" => "Small Baths", + "is_visible" => true, + "url" => "/bath/small-baths/", + "children" => [ + new CategoryTreeBranch((object)[ + "id" => 25, + "parent_id" => 24, + "name" => "Small Red Baths", + "is_visible" => true, + "url" => "/bath/small-baths/small-red-baths/", + "children" => [] + ]) + ] + ]) + ] + ]), + new CategoryTreeBranch((object)[ + "id" => 19, + "parent_id" => 0, + "name" => "Garden", + "is_visible" => true, + "url" => "/garden/", + "children" => [] + ]), + new CategoryTreeBranch((object)[ + "id" => 21, + "parent_id" => 0, + "name" => "Kitchen", + "is_visible" => true, + "url" => "/kitchen/", + "children" => [] + ]), + new CategoryTreeBranch((object)[ + "id" => 20, + "parent_id" => 0, + "name" => "Publications", + "is_visible" => true, + "url" => "/publications/", + "children" => [] + ]), + new CategoryTreeBranch((object)[ + "id" => 22, + "parent_id" => 0, + "name" => "Utility", + "is_visible" => true, + "url" => "/utility/", + "children" => [] + ]) + ]; + + $response = $this->getApi()->catalog()->categories()->getCategoryTree()->getTree(); + + $this->assertEquals($expectedTree, $response); + } } diff --git a/tests/BigCommerce/responses/catalog__categories__get_tree.json b/tests/BigCommerce/responses/catalog__categories__get_tree.json new file mode 100644 index 00000000..615c8e71 --- /dev/null +++ b/tests/BigCommerce/responses/catalog__categories__get_tree.json @@ -0,0 +1 @@ +{"data":[{"id":23,"parent_id":0,"name":"Shop All","is_visible":true,"url":"\/shop-all\/","children":[]},{"id":18,"parent_id":0,"name":"Bath","is_visible":true,"url":"\/bath\/","children":[{"id":24,"parent_id":18,"name":"Small Baths","is_visible":true,"url":"\/bath\/small-baths\/","children":[{"id":25,"parent_id":24,"name":"Small Red Baths","is_visible":true,"url":"\/bath\/small-baths\/small-red-baths\/","children":[]}]}]},{"id":19,"parent_id":0,"name":"Garden","is_visible":true,"url":"\/garden\/","children":[]},{"id":21,"parent_id":0,"name":"Kitchen","is_visible":true,"url":"\/kitchen\/","children":[]},{"id":20,"parent_id":0,"name":"Publications","is_visible":true,"url":"\/publications\/","children":[]},{"id":22,"parent_id":0,"name":"Utility","is_visible":true,"url":"\/utility\/","children":[]}],"meta":{}} \ No newline at end of file