This commit is contained in:
Tung Du 2022-12-08 08:48:42 +07:00 committed by GitHub
parent c2f640352f
commit e878431068
2 changed files with 479 additions and 0 deletions

View File

@ -0,0 +1,429 @@
<?php
namespace Automattic\WooCommerce\Blocks\Tests\BlockTypes;
use Automattic\WooCommerce\Blocks\Tests\Mocks\ProductQueryMock;
/**
* Tests for the ProductQuery block type
*/
class ProductQuery extends \WP_UnitTestCase {
/**
* This variable holds our cart object.
*
* @var ProductQueryMock
*/
private $block_instance;
/**
* Return starting point for parsed block test data.
* Using a method instead of property to avoid sharing data between tests.
*/
private function get_base_parsed_block() {
return array(
'blockName' => 'core/query',
'attrs' => array(
'namespace' => 'woocommerce/product-query',
'query' => array(
'perPage' => 9,
'pages' => 0,
'offset' => 0,
'postType' => 'product',
'order' => 'desc',
'orderBy' => 'date',
'author' => '',
'search' => '',
'exclude' => array(),
'sticky' => '',
'inherit' => false,
'__woocommerceAttributes' => array(),
'__woocommerceStockStatus' => array(
'instock',
'outofstock',
'onbackorder',
),
),
),
);
}
/**
* Initiate the mock object.
*/
protected function setUp(): void {
$this->block_instance = new ProductQueryMock();
}
/**
* Build the merged_query for testing
*
* @param array $parsed_block Parsed block data.
*/
private function initialize_merged_query( $parsed_block = array() ) {
if ( empty( $parsed_block ) ) {
$parsed_block = $this->get_base_parsed_block();
}
$this->block_instance->set_parsed_block( $parsed_block );
$block = new \stdClass();
$block->context = $parsed_block['attrs'];
$query = build_query_vars_from_query_block( $block, 1 );
return $this->block_instance->build_query( $query );
}
/**
* Test merging on sale queries.
*/
public function test_merging_on_sale_queries() {
// Mock the on sale product ids.
$on_sale_product_ids = array( 1, 2, 3, 4 );
set_transient( 'wc_products_onsale', $on_sale_product_ids, DAY_IN_SECONDS * 30 );
$parsed_block = $this->get_base_parsed_block();
$parsed_block['attrs']['query']['__woocommerceOnSale'] = true;
$merged_query = $this->initialize_merged_query( $parsed_block );
foreach ( $on_sale_product_ids as $id ) {
$this->assertContainsEquals( $id, $merged_query['post__in'] );
}
$this->assertCount( 4, $merged_query['post__in'] );
}
/**
* Test merging stock status queries.
*/
public function test_merging_stock_status_queries() {
$parsed_block = $this->get_base_parsed_block();
$parsed_block['attrs']['query']['__woocommerceStockStatus'] = array(
'outofstock',
'onbackorder',
);
$merged_query = $this->initialize_merged_query( $parsed_block );
$this->assertContainsEquals(
array(
'value' => array( 'outofstock', 'onbackorder' ),
'compare' => 'IN',
'key' => '_stock_status',
),
$merged_query['meta_query']
);
$parsed_block = $this->get_base_parsed_block();
$parsed_block['attrs']['query']['__woocommerceStockStatus'] = array(
'instock',
'onbackorder',
);
$this->block_instance->set_parsed_block( $parsed_block );
$merged_query = $this->block_instance->build_query( $parsed_block['attrs']['query'] );
$this->assertContainsEquals(
array(
'compare' => 'IN',
'key' => '_stock_status',
'value' => array( 'instock', 'onbackorder' ),
),
$merged_query['meta_query']
);
}
/**
* Test merging attribute queries.
*/
public function test_merging_attribute_queries() {
$parsed_block = $this->get_base_parsed_block();
$parsed_block['attrs']['query']['__woocommerceAttributes'] = array(
array(
'taxonomy' => 'pa_test',
'termId' => 1,
),
array(
'taxonomy' => 'pa_test',
'termId' => 2,
),
array(
'taxonomy' => 'pa_another_test',
'termId' => 3,
),
);
$merged_query = $this->initialize_merged_query( $parsed_block );
$this->assertContainsEquals(
array(
'field' => 'term_id',
'terms' => array( 3 ),
'operator' => 'IN',
'taxonomy' => 'pa_another_test',
),
$merged_query['tax_query']
);
$this->assertContainsEquals(
array(
'taxonomy' => 'pa_test',
'field' => 'term_id',
'terms' => array( 1, 2 ),
'operator' => 'IN',
),
$merged_query['tax_query']
);
}
/**
* Test merging order by rating queries.
*/
public function test_merging_order_by_rating_queries() {
$parsed_block = $this->get_base_parsed_block();
$parsed_block['attrs']['query']['orderBy'] = 'rating';
$merged_query = $this->initialize_merged_query( $parsed_block );
$this->assertEquals( 'meta_value_num', $merged_query['orderby'] );
$this->assertEquals( '_wc_average_rating', $merged_query['meta_key'] );
}
/**
* Test merging order by popularity queries.
*/
public function test_merging_order_by_popularity_queries() {
$parsed_block = $this->get_base_parsed_block();
$parsed_block['attrs']['query']['orderBy'] = 'popularity';
$merged_query = $this->initialize_merged_query( $parsed_block );
$this->assertEquals( 'meta_value_num', $merged_query['orderby'] );
$this->assertEquals( 'total_sales', $merged_query['meta_key'] );
}
/**
* Test merging multiple queries.
*/
public function test_merging_multiple_queries() {
$parsed_block = $this->get_base_parsed_block();
$parsed_block['attrs']['query']['orderBy'] = 'rating';
$parsed_block['attrs']['query']['__woocommerceStockStatus'] = array(
'instock',
'onbackorder',
);
$parsed_block['attrs']['query']['__woocommerceAttributes'] = array(
array(
'taxonomy' => 'pa_test',
'termId' => 1,
),
array(
'taxonomy' => 'pa_test',
'termId' => 2,
),
);
$merged_query = $this->initialize_merged_query( $parsed_block );
$this->assertEquals( 'meta_value_num', $merged_query['orderby'] );
$this->assertEquals( '_wc_average_rating', $merged_query['meta_key'] );
$this->assertContainsEquals(
array(
'compare' => 'IN',
'key' => '_stock_status',
'value' => array( 'instock', 'onbackorder' ),
),
$merged_query['meta_query']
);
$this->assertContainsEquals(
array(
'taxonomy' => 'pa_test',
'field' => 'term_id',
'terms' => array( 1, 2 ),
'operator' => 'IN',
),
$merged_query['tax_query']
);
}
/**
* Test merging filter by max price queries.
*/
public function test_merging_filter_by_max_price_queries() {
set_query_var( 'max_price', 100 );
$merged_query = $this->initialize_merged_query();
$this->assertContainsEquals(
array(
array(
'key' => '_price',
'value' => 100,
'compare' => '<',
'type' => 'numeric',
),
array(),
'relation' => 'AND',
),
$merged_query['meta_query']
);
}
/**
* Test merging filter by min price queries.
*/
public function test_merging_filter_by_min_price_queries() {
set_query_var( 'min_price', 20 );
$merged_query = $this->initialize_merged_query();
$this->assertContainsEquals(
array(
array(),
array(
'key' => '_price',
'value' => 20,
'compare' => '>=',
'type' => 'numeric',
),
'relation' => 'AND',
),
$merged_query['meta_query']
);
}
/**
* Test merging filter by min and max price queries.
*/
public function test_merging_filter_by_min_and_max_price_queries() {
set_query_var( 'max_price', 100 );
set_query_var( 'min_price', 20 );
$merged_query = $this->initialize_merged_query();
$this->assertContainsEquals(
array(
array(
'key' => '_price',
'value' => 100,
'compare' => '<',
'type' => 'numeric',
),
array(
'key' => '_price',
'value' => 20,
'compare' => '>=',
'type' => 'numeric',
),
'relation' => 'AND',
),
$merged_query['meta_query']
);
}
/**
* Test merging filter by stock status queries.
*/
public function test_merging_filter_by_stock_status_queries() {
set_query_var( 'filter_stock_status', 'instock' );
$merged_query = $this->initialize_merged_query();
$this->assertContainsEquals(
array(
'operator' => 'IN',
'key' => '_stock_status',
'value' => array( 'instock' ),
),
$merged_query['meta_query']
);
}
/**
* Test merging filter by stock status queries.
*/
public function test_merging_filter_by_attribute_queries() {
// Mock the attribute data.
$this->block_instance->set_attributes_filter_query_args(
array(
array(
'filter' => 'filter_color',
'query_type' => 'query_type_color',
),
array(
'filter' => 'filter_size',
'query_type' => 'query_type_size',
),
)
);
set_query_var( 'filter_color', 'blue' );
set_query_var( 'query_type_color', 'or' );
set_query_var( 'filter_size', 'xl,xxl' );
set_query_var( 'query_type_size', 'and' );
$merged_query = $this->initialize_merged_query();
$attribute_tax_query = $merged_query['tax_query'][0];
$attribute_tax_query_queries = $attribute_tax_query[0];
$this->assertEquals( 'AND', $attribute_tax_query['relation'] );
$this->assertContainsEquals(
array(
'taxonomy' => 'pa_color',
'field' => 'slug',
'terms' => array( 'blue' ),
'operator' => 'IN',
),
$attribute_tax_query_queries
);
$this->assertContainsEquals(
array(
'taxonomy' => 'pa_size',
'field' => 'slug',
'terms' => array( 'xl', 'xxl' ),
'operator' => 'AND',
),
$attribute_tax_query_queries
);
}
/**
* Test merging multiple filter queries.
*/
public function test_merging_multiple_filter_queries() {
set_query_var( 'max_price', 100 );
set_query_var( 'min_price', 20 );
set_query_var( 'filter_stock_status', 'instock' );
$merged_query = $this->initialize_merged_query();
$this->assertContainsEquals(
array(
'operator' => 'IN',
'key' => '_stock_status',
'value' => array( 'instock' ),
),
$merged_query['meta_query']
);
$this->assertContainsEquals(
array(
array(
'key' => '_price',
'value' => 100,
'compare' => '<',
'type' => 'numeric',
),
array(
'key' => '_price',
'value' => 20,
'compare' => '>=',
'type' => 'numeric',
),
'relation' => 'AND',
),
$merged_query['meta_query']
);
}
}

View File

@ -0,0 +1,50 @@
<?php
namespace Automattic\WooCommerce\Blocks\Tests\Mocks;
use Automattic\WooCommerce\Blocks\BlockTypes\ProductQuery;
use Automattic\WooCommerce\Blocks\Package;
use Automattic\WooCommerce\Blocks\Assets\Api;
use Automattic\WooCommerce\Blocks\Assets\AssetDataRegistry;
use Automattic\WooCommerce\Blocks\Integrations\IntegrationRegistry;
/**
* ProductQueryMock used to test Product Query block functions.
*/
class ProductQueryMock extends ProductQuery {
/**
* Initialize our mock class.
*/
public function __construct() {
parent::__construct(
Package::container()->get( API::class ),
Package::container()->get( AssetDataRegistry::class ),
new IntegrationRegistry(),
);
}
/**
* For now don't need to initialize anything in tests so let's
* just override the default behaviour.
*/
protected function initialize() {
}
/**
* Allow test to set the parsed block data.
*
* @param array $parsed_block The block data.
*/
public function set_parsed_block( $parsed_block ) {
$this->parsed_block = $parsed_block;
}
/**
* Allow test to set the $attributes_filter_query_args.
*
* @param array $data The attribute data.
*/
public function set_attributes_filter_query_args( $data ) {
$this->attributes_filter_query_args = $data;
}
}