<?php
/**
 * Class TestPostOrder
 *
 * @package DraggablePostOrder
 */

use Draggable_Post_Order\Draggable_Post_Order;

/**
 * Sample test case.
 */
class TestPostOrder extends WP_UnitTestCase {

	/**
	 * The post type for testing.
	 *
	 * @var WP_Post_Type
	 */
	public WP_Post_Type $test_post_type;

	/**
	 * Runs the routine before each test is executed.
	 */
	public function setUp(): void {
		parent::setUp();

		$this->test_post_type = register_post_type(
			'test',
			[
				'supports'    => [ Draggable_Post_Order::$post_type_feature ],
				'has_archive' => true,
			]
		);

		// since tests are loaded after init, run init manually.
		Draggable_Post_Order::init();
	}

	/**
	 * Test query manipulation on meta_query
	 */
	public function test_query_manipulation_meta_query() {
		$this->go_to( '/?post_type=test' );
		$wp_query = $GLOBALS['wp_query'];

		$meta_sub_query = [
			'relation'                           => 'OR',
			'draggable-post-order-clause'        => [
				'key'  => Draggable_Post_Order::$meta_key,
				'type' => 'NUMERIC',
			],
			// get all posts without the meta as well.
			'draggable-post-order-exists-clause' => [
				'key'     => Draggable_Post_Order::$meta_key,
				'compare' => 'NOT EXISTS',
			],
		];
		$this->assertEquals( [ $meta_sub_query ], $wp_query->get( 'meta_query' ) );
	}

	/**
	 * Test query manipulation on orderby with ASC
	 */
	public function test_query_manipulation_orderby_asc() {
		$this->go_to( '/?post_type=test' );
		$wp_query = $GLOBALS['wp_query'];

		$orderby = [
			'draggable-post-order-clause'        => 'ASC',
			'draggable-post-order-exists-clause' => 'ASC',
		];
		$this->assertEquals( $orderby, $wp_query->get( 'orderby' ) );
	}

	/**
	 * Test query manipulation on orderby with DESC
	 */
	public function test_query_manipulation_orderby_desc() {
		tests_add_filter(
			'draggable_post_order_order',
			function ( $order, $post_type, $query ) {
				$this->assertEquals( 'ASC', $order );
				$this->assertEquals( 'test', $post_type );
				$this->assertTrue( $query->is_archive );

				return 'DESC';
			},
			10,
			3
		);
		$this->go_to( '/?post_type=test' );
		$wp_query = $GLOBALS['wp_query'];

		$orderby = [
			'draggable-post-order-clause'        => 'DESC',
			'draggable-post-order-exists-clause' => 'DESC',
		];
		$this->assertEquals( $orderby, $wp_query->get( 'orderby' ) );
	}

	/**
	 * Test that query is not manipulated on unrelated pages
	 */
	public function test_query_manipulation_orderby_none() {
		$this->go_to( '/' );
		$wp_query = $GLOBALS['wp_query'];

		$this->assertEmpty( $wp_query->get( 'orderby' ) );
	}
}