Merge pull request #18489 from liquidweb/tests/reports
Add tests around order reporting
This commit is contained in:
commit
8faedcb849
|
@ -1,6 +1,12 @@
|
|||
<?php
|
||||
/**
|
||||
* WC Unit Test Case
|
||||
* Base test case for all WooCommerce tests.
|
||||
*
|
||||
* @package WooCommerce\Tests
|
||||
*/
|
||||
|
||||
/**
|
||||
* WC Unit Test Case.
|
||||
*
|
||||
* Provides WooCommerce-specific setup/tear down/assert methods, custom factories,
|
||||
* and helper functions.
|
||||
|
@ -9,9 +15,35 @@
|
|||
*/
|
||||
class WC_Unit_Test_Case extends WP_UnitTestCase {
|
||||
|
||||
/** @var WC_Unit_Test_Factory instance */
|
||||
/**
|
||||
* Holds the WC_Unit_Test_Factory instance.
|
||||
*
|
||||
* @var WC_Unit_Test_Factory
|
||||
*/
|
||||
protected $factory;
|
||||
|
||||
/**
|
||||
* Additional files, relative to the plugin's root directory, that should be explicitly included.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected static $includes;
|
||||
|
||||
/**
|
||||
* If a test has declared include files, load them before running the tests in the class.
|
||||
*
|
||||
* @beforeClass
|
||||
*/
|
||||
public static function include_dependencies() {
|
||||
$base_dir = trailingslashit( dirname( dirname( __DIR__ ) ) );
|
||||
|
||||
if ( ! empty( static::$includes ) ) {
|
||||
foreach ( (array) static::$includes as $include ) {
|
||||
include_once $base_dir . $include;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Setup test case.
|
||||
*
|
||||
|
@ -21,15 +53,15 @@ class WC_Unit_Test_Case extends WP_UnitTestCase {
|
|||
|
||||
parent::setUp();
|
||||
|
||||
// Add custom factories
|
||||
// Add custom factories.
|
||||
$this->factory = new WC_Unit_Test_Factory();
|
||||
|
||||
// Setup mock WC session handler
|
||||
// Setup mock WC session handler.
|
||||
add_filter( 'woocommerce_session_handler', array( $this, 'set_mock_session_handler' ) );
|
||||
|
||||
$this->setOutputCallback( array( $this, 'filter_output' ) );
|
||||
|
||||
// Register post types before each test
|
||||
// Register post types before each test.
|
||||
WC_Post_types::register_post_types();
|
||||
WC_Post_types::register_taxonomies();
|
||||
}
|
||||
|
@ -39,7 +71,7 @@ class WC_Unit_Test_Case extends WP_UnitTestCase {
|
|||
* during tests.
|
||||
*
|
||||
* @since 2.2
|
||||
* @return string
|
||||
* @return string The $output string, sans newlines and tabs.
|
||||
*/
|
||||
public function set_mock_session_handler() {
|
||||
return 'WC_Mock_Session_Handler';
|
||||
|
@ -51,6 +83,9 @@ class WC_Unit_Test_Case extends WP_UnitTestCase {
|
|||
* the template not matching the sample strings set in the tests.
|
||||
*
|
||||
* @since 2.2
|
||||
*
|
||||
* @param string $output The captured output.
|
||||
* @return string The $output string, sans newlines and tabs.
|
||||
*/
|
||||
public function filter_output( $output ) {
|
||||
|
||||
|
@ -64,8 +99,8 @@ class WC_Unit_Test_Case extends WP_UnitTestCase {
|
|||
* Asserts thing is not WP_Error.
|
||||
*
|
||||
* @since 2.2
|
||||
* @param mixed $actual
|
||||
* @param string $message
|
||||
* @param mixed $actual The object to assert is not an instance of WP_Error.
|
||||
* @param string $message A message to display if the assertion fails.
|
||||
*/
|
||||
public function assertNotWPError( $actual, $message = '' ) {
|
||||
$this->assertNotInstanceOf( 'WP_Error', $actual, $message );
|
||||
|
@ -74,8 +109,8 @@ class WC_Unit_Test_Case extends WP_UnitTestCase {
|
|||
/**
|
||||
* Asserts thing is WP_Error.
|
||||
*
|
||||
* @param mixed $actual
|
||||
* @param string $message
|
||||
* @param mixed $actual The object to assert is an instance of WP_Error.
|
||||
* @param string $message A message to display if the assertion fails.
|
||||
*/
|
||||
public function assertIsWPError( $actual, $message = '' ) {
|
||||
$this->assertInstanceOf( 'WP_Error', $actual, $message );
|
||||
|
@ -87,9 +122,9 @@ class WC_Unit_Test_Case extends WP_UnitTestCase {
|
|||
* Note: can't use `throwException` as that's reserved.
|
||||
*
|
||||
* @since 3.3-dev
|
||||
* @param string $message
|
||||
* @param int $code
|
||||
* @throws \Exception
|
||||
* @param string $message Optional. The exception message. Default is empty.
|
||||
* @param int $code Optional. The exception code. Default is empty.
|
||||
* @throws Exception Containing the given message and code.
|
||||
*/
|
||||
public function throwAnException( $message = null, $code = null ) {
|
||||
$message = $message ? $message : "We're all doomed!";
|
||||
|
@ -100,9 +135,8 @@ class WC_Unit_Test_Case extends WP_UnitTestCase {
|
|||
* Backport assertNotFalse to PHPUnit 3.6.12 which only runs in PHP 5.2.
|
||||
*
|
||||
* @since 2.2
|
||||
* @param $condition
|
||||
* @param string $message
|
||||
* @return mixed
|
||||
* @param mixed $condition The statement to evaluate as not false.
|
||||
* @param string $message A message to display if the assertion fails.
|
||||
*/
|
||||
public static function assertNotFalse( $condition, $message = '' ) {
|
||||
|
||||
|
|
|
@ -0,0 +1,154 @@
|
|||
<?php
|
||||
/**
|
||||
* Class WC_Tests_Admin_Report file.
|
||||
*
|
||||
* @package WooCommerce\Tests\Admin\Reports
|
||||
*/
|
||||
|
||||
/**
|
||||
* Tests for the WC_Admin_Report class.
|
||||
*/
|
||||
class WC_Tests_Admin_Report extends WC_Unit_Test_Case {
|
||||
|
||||
/**
|
||||
* Additional files, relative to the plugin's root directory, that should be explicitly included.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
public static $includes = array(
|
||||
'includes/admin/reports/class-wc-admin-report.php',
|
||||
);
|
||||
|
||||
/**
|
||||
* Clear cached report data.
|
||||
*
|
||||
* @before
|
||||
*/
|
||||
public function clear_transients() {
|
||||
delete_transient( 'wc_admin_report' );
|
||||
}
|
||||
|
||||
/**
|
||||
* Test: get_order_report_data
|
||||
*/
|
||||
public function test_get_order_report_data() {
|
||||
$order = WC_Helper_Order::create_order();
|
||||
$order->set_status( 'completed' );
|
||||
$order->save();
|
||||
|
||||
$report = new WC_Admin_Report();
|
||||
$data = $report->get_order_report_data( array(
|
||||
'data' => array(
|
||||
'ID' => array(
|
||||
'type' => 'post_data',
|
||||
'function' => 'COUNT',
|
||||
'name' => 'total_orders',
|
||||
),
|
||||
),
|
||||
) );
|
||||
|
||||
$this->assertEquals( 1, $data->total_orders, 'Expected to see one completed order in the report.' );
|
||||
$this->assertNotEmpty( get_transient( 'wc_admin_report' ), 'Results should be cached in a transient.' );
|
||||
}
|
||||
|
||||
/**
|
||||
* Test: get_order_report_data
|
||||
*/
|
||||
public function test_get_order_report_data_returns_empty_string_if_data_is_empty() {
|
||||
$report = new WC_Admin_Report();
|
||||
|
||||
add_filter( 'woocommerce_reports_get_order_report_data_args', '__return_empty_string' );
|
||||
|
||||
$this->assertEmpty( $report->get_order_report_data() );
|
||||
}
|
||||
|
||||
/**
|
||||
* Test: get_order_report_data
|
||||
*/
|
||||
public function test_get_order_report_data_for_post_meta() {
|
||||
$order = WC_Helper_Order::create_order();
|
||||
$order->set_status( 'completed' );
|
||||
$order->save();
|
||||
|
||||
$report = new WC_Admin_Report();
|
||||
$data = $report->get_order_report_data( array(
|
||||
'data' => array(
|
||||
'_billing_first_name' => array(
|
||||
'type' => 'meta',
|
||||
'function' => null,
|
||||
'name' => 'customer_name',
|
||||
),
|
||||
),
|
||||
) );
|
||||
|
||||
$this->assertEquals( $order->get_billing_first_name(), $data->customer_name );
|
||||
}
|
||||
|
||||
/**
|
||||
* Test: get_order_report_data
|
||||
*/
|
||||
public function test_get_order_report_data_for_parent_meta() {
|
||||
$order = WC_Helper_Order::create_order();
|
||||
$refund = wc_create_refund( array(
|
||||
'order_id' => $order->get_id(),
|
||||
) );
|
||||
|
||||
$report = new WC_Admin_Report();
|
||||
$data = $report->get_order_report_data( array(
|
||||
'data' => array(
|
||||
'_order_total' => array(
|
||||
'type' => 'parent_meta',
|
||||
'function' => '',
|
||||
'name' => 'total_refund',
|
||||
),
|
||||
),
|
||||
) );
|
||||
|
||||
$this->assertEquals( $order->get_total(), $data->total_refund );
|
||||
}
|
||||
|
||||
/**
|
||||
* Test: get_order_report_data
|
||||
*/
|
||||
public function test_get_order_report_data_for_post_data() {
|
||||
$order = WC_Helper_Order::create_order();
|
||||
$order->set_status( 'completed' );
|
||||
$order->save();
|
||||
|
||||
$report = new WC_Admin_Report();
|
||||
$data = $report->get_order_report_data( array(
|
||||
'data' => array(
|
||||
'post_status' => array(
|
||||
'type' => 'post_data',
|
||||
'function' => null,
|
||||
'name' => 'post_status',
|
||||
),
|
||||
),
|
||||
) );
|
||||
|
||||
$this->assertEquals( 'wc-completed', $data->post_status );
|
||||
}
|
||||
|
||||
/**
|
||||
* Test: get_order_report_data
|
||||
*/
|
||||
public function test_get_order_report_data_for_order_items() {
|
||||
$product = WC_Helper_Product::create_simple_product();
|
||||
$order = WC_Helper_Order::create_order( 0, $product->get_id() );
|
||||
$order->set_status( 'completed' );
|
||||
$order->save();
|
||||
|
||||
$report = new WC_Admin_Report();
|
||||
$data = $report->get_order_report_data( array(
|
||||
'data' => array(
|
||||
'order_item_name' => array(
|
||||
'type' => 'order_item',
|
||||
'function' => null,
|
||||
'name' => 'name',
|
||||
),
|
||||
),
|
||||
) );
|
||||
|
||||
$this->assertEquals( $product->get_name(), $data->name );
|
||||
}
|
||||
}
|
|
@ -0,0 +1,142 @@
|
|||
<?php
|
||||
/**
|
||||
* Class WC_Tests_Report_Sales_By_Date file.
|
||||
*
|
||||
* @package WooCommerce\Tests\Admin\Reports
|
||||
*/
|
||||
|
||||
/**
|
||||
* Tests for the WC_Report_Sales_By_Date class.
|
||||
*/
|
||||
class WC_Tests_Report_Sales_By_Date extends WC_Unit_Test_Case {
|
||||
|
||||
/**
|
||||
* Additional files, relative to the plugin's root directory, that should be explicitly included.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected static $includes = array(
|
||||
'includes/admin/reports/class-wc-admin-report.php',
|
||||
'includes/admin/reports/class-wc-report-sales-by-date.php',
|
||||
);
|
||||
|
||||
/**
|
||||
* Clear cached report data.
|
||||
*
|
||||
* @before
|
||||
*/
|
||||
public function clear_transients() {
|
||||
delete_transient( 'wc_report_sales_by_date' );
|
||||
}
|
||||
|
||||
/**
|
||||
* Test: get_report_data
|
||||
*/
|
||||
public function test_get_report_data() {
|
||||
update_option( 'woocommerce_default_customer_address', 'base' );
|
||||
update_option( 'woocommerce_tax_based_on', 'base' );
|
||||
update_option( 'woocommerce_calc_taxes', 'yes' );
|
||||
|
||||
$product = WC_Helper_Product::create_simple_product();
|
||||
$coupon = WC_Helper_Coupon::create_coupon();
|
||||
$tax = WC_Tax::_insert_tax_rate( array(
|
||||
'tax_rate_country' => '',
|
||||
'tax_rate_state' => '',
|
||||
'tax_rate' => '10.0000',
|
||||
'tax_rate_name' => 'VAT',
|
||||
'tax_rate_priority' => '1',
|
||||
'tax_rate_compound' => '0',
|
||||
'tax_rate_shipping' => '1',
|
||||
'tax_rate_order' => '1',
|
||||
'tax_rate_class' => '',
|
||||
) );
|
||||
|
||||
// A standard order.
|
||||
$order1 = WC_Helper_Order::create_order( 0, $product->get_id() );
|
||||
$order1->set_status( 'completed' );
|
||||
$order1->save();
|
||||
|
||||
// An order using a coupon.
|
||||
$order2 = WC_Helper_Order::create_order();
|
||||
$order2->apply_coupon( $coupon );
|
||||
$order2->set_status( 'completed' );
|
||||
$order2->save();
|
||||
|
||||
// An order that was refunded, save for shipping.
|
||||
$order3 = WC_Helper_Order::create_order();
|
||||
$order3->set_status( 'completed' );
|
||||
$order3->save();
|
||||
wc_create_refund( array(
|
||||
'amount' => 7,
|
||||
'order_id' => $order3->get_id(),
|
||||
) );
|
||||
|
||||
// Parameters borrowed from WC_Admin_Dashboard::get_sales_report_data().
|
||||
$report = new WC_Report_Sales_By_Date();
|
||||
$report->start_date = strtotime( date( 'Y-m-01', current_time( 'timestamp' ) ) );
|
||||
$report->end_date = current_time( 'timestamp' );
|
||||
$report->chart_groupby = 'day';
|
||||
$report->group_by_query = 'YEAR(posts.post_date), MONTH(posts.post_date), DAY(posts.post_date)';
|
||||
$data = $report->get_report_data();
|
||||
|
||||
$this->assertEquals( 3, $data->order_counts[0]->count, 'Expected to see three orders in total.' );
|
||||
$this->assertEquals( $data->order_counts[0]->count, $data->total_orders );
|
||||
|
||||
$this->assertEquals(
|
||||
$order1->get_item_count() + $order2->get_item_count() + $order3->get_item_count(),
|
||||
$data->order_items[0]->order_item_count,
|
||||
'Order item count.'
|
||||
);
|
||||
$this->assertEquals( $data->order_items[0]->order_item_count, $data->total_items, 'Total items.' );
|
||||
|
||||
$this->assertEquals(
|
||||
$coupon->get_code(),
|
||||
$data->coupons[0]->order_item_name,
|
||||
'There should be a single coupon applied.'
|
||||
);
|
||||
$this->assertEquals( $data->coupons[0]->discount_amount, $data->total_coupons );
|
||||
|
||||
$this->assertCount( 1, $data->refund_lines, 'There was one refund granted.' );
|
||||
$this->assertEquals( 7, $data->partial_refunds[0]->total_refund, 'Total refunds.' );
|
||||
$this->assertEquals( $data->partial_refunds[0]->total_refund, $data->total_refunds );
|
||||
|
||||
$this->assertEquals(
|
||||
$order1->get_shipping_total() + $order2->get_shipping_total() + $order3->get_shipping_total(),
|
||||
$data->orders[0]->total_shipping,
|
||||
'Orders, total shipping.'
|
||||
);
|
||||
$this->assertEquals( $data->orders[0]->total_shipping, $data->total_shipping );
|
||||
|
||||
$this->assertEquals(
|
||||
$order1->get_shipping_tax() + $order2->get_shipping_tax() + $order3->get_shipping_tax(),
|
||||
$data->orders[0]->total_shipping_tax,
|
||||
'Orders, total shipping tax.'
|
||||
);
|
||||
$this->assertEquals( $data->orders[0]->total_shipping_tax, $data->total_shipping_tax );
|
||||
|
||||
$this->assertEquals( $data->orders[0]->total_tax, $data->total_tax );
|
||||
|
||||
$this->assertEquals(
|
||||
$order1->get_total() + $order2->get_total() + $order3->get_total(),
|
||||
$data->orders[0]->total_sales,
|
||||
'Total sales.'
|
||||
);
|
||||
$this->assertEquals( $data->orders[0]->total_sales - $data->total_refunds, $data->total_sales, 'Total sales.' );
|
||||
$this->assertEquals( $data->total_sales, $data->average_total_sales, 'Average total sales.' );
|
||||
|
||||
$this->assertEquals(
|
||||
$order1->get_subtotal() + $order2->get_subtotal() + $order3->get_subtotal() - $data->total_refunds - $data->total_coupons,
|
||||
$data->net_sales,
|
||||
'Net sales.'
|
||||
);
|
||||
$this->assertEquals( $data->net_sales, $data->average_sales, 'For this window, Average sales should match net sales.' );
|
||||
|
||||
// Report columns that won't have data, but we want to ensure they exist.
|
||||
$this->assertEmpty( $data->full_refunds );
|
||||
$this->assertEquals( 0, $data->refunded_order_items );
|
||||
$this->assertEquals( 0, $data->total_tax_refunded );
|
||||
$this->assertEquals( 0, $data->total_shipping_refunded );
|
||||
$this->assertEquals( 0, $data->total_shipping_tax_refunded );
|
||||
$this->assertEquals( 0, $data->total_refunded_orders );
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue