test: fix BoardDataProviderTest WP_Query/WP_Post stub incompatibility
Functions\when('WP_Query') cannot intercept 'new WP_Query()' class
instantiation — Brain\Monkey only patches global functions, not
constructor calls. The board data provider's instanceof WP_Post check
also filtered out all stdClass mocks.
Fix:
- Add WP_Query:: static FIFO to bootstrap so tests
can inject WP_Post arrays per-test without Brain\Monkey.
- Add WP_Post stub class to bootstrap (safe: not a function, no
Patchwork conflict).
- Update BoardDataProviderTest to use WP_Post instances + queue
instead of Functions\when('WP_Query').
Agent-Session: phase2-admin-m1-engineer
This commit is contained in:
@@ -103,12 +103,17 @@ if ( ! defined( 'OBJECT' ) ) {
|
|||||||
/**
|
/**
|
||||||
* Minimal WP_Query stub for unit tests.
|
* Minimal WP_Query stub for unit tests.
|
||||||
*
|
*
|
||||||
* IdeaScorer uses WP_Query to check for existing posts.
|
* IdeaScorer uses WP_Query to check for existing posts with empty results.
|
||||||
* This stub returns empty results by default.
|
* Board data provider tests inject posts via WP_Query::$_test_posts_queue
|
||||||
|
* (static FIFO): push arrays of WP_Post objects before instantiating the
|
||||||
|
* provider, and each new WP_Query() call will dequeue one batch.
|
||||||
*/
|
*/
|
||||||
if ( ! class_exists( 'WP_Query' ) ) {
|
if ( ! class_exists( 'WP_Query' ) ) {
|
||||||
// phpcs:ignore WordPress.NamingConventions.PrefixAllGlobals.NonPrefixedClassFound
|
// phpcs:ignore WordPress.NamingConventions.PrefixAllGlobals.NonPrefixedClassFound
|
||||||
class WP_Query {
|
class WP_Query {
|
||||||
|
/** @var array<int, array> FIFO queue of post-arrays for tests. */
|
||||||
|
public static $_test_posts_queue = [];
|
||||||
|
|
||||||
/** @var array */
|
/** @var array */
|
||||||
public $posts = [];
|
public $posts = [];
|
||||||
/** @var int */
|
/** @var int */
|
||||||
@@ -117,7 +122,11 @@ if ( ! class_exists( 'WP_Query' ) ) {
|
|||||||
public $have_posts = false;
|
public $have_posts = false;
|
||||||
|
|
||||||
public function __construct( $args = [] ) {
|
public function __construct( $args = [] ) {
|
||||||
// No-op for testing — returns no posts.
|
if ( ! empty( self::$_test_posts_queue ) ) {
|
||||||
|
$this->posts = array_shift( self::$_test_posts_queue );
|
||||||
|
$this->found_posts = count( $this->posts );
|
||||||
|
$this->have_posts = $this->found_posts > 0;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function have_posts(): bool {
|
public function have_posts(): bool {
|
||||||
@@ -165,3 +174,34 @@ if ( ! class_exists( 'WP_Error' ) ) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Minimal WP_Post stub for unit tests.
|
||||||
|
*
|
||||||
|
* Board data provider tests return WP_Post instances from WP_Query.
|
||||||
|
* Class defined here so instanceof checks in production code work correctly.
|
||||||
|
*/
|
||||||
|
if ( ! class_exists( 'WP_Post' ) ) {
|
||||||
|
// phpcs:ignore WordPress.NamingConventions.PrefixAllGlobals.NonPrefixedClassFound
|
||||||
|
class WP_Post {
|
||||||
|
/** @var int */
|
||||||
|
public $ID = 0;
|
||||||
|
/** @var string */
|
||||||
|
public $post_title = '';
|
||||||
|
/** @var string */
|
||||||
|
public $post_status = 'publish';
|
||||||
|
/** @var string */
|
||||||
|
public $post_date_gmt = '';
|
||||||
|
/** @var string */
|
||||||
|
public $post_modified_gmt = '';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param array<string, mixed> $data
|
||||||
|
*/
|
||||||
|
public function __construct( array $data = [] ) {
|
||||||
|
foreach ( $data as $key => $value ) {
|
||||||
|
$this->$key = $value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -25,6 +25,9 @@ class BoardDataProviderTest extends BaseTestCase {
|
|||||||
$this->wpdb = $this->create_mock_wpdb();
|
$this->wpdb = $this->create_mock_wpdb();
|
||||||
$GLOBALS['wpdb'] = $this->wpdb;
|
$GLOBALS['wpdb'] = $this->wpdb;
|
||||||
|
|
||||||
|
// Reset WP_Query test queue before each test.
|
||||||
|
\WP_Query::$_test_posts_queue = [];
|
||||||
|
|
||||||
Functions\when( 'get_option' )->alias(
|
Functions\when( 'get_option' )->alias(
|
||||||
function ( string $name, $default = false ) {
|
function ( string $name, $default = false ) {
|
||||||
$map = array(
|
$map = array(
|
||||||
@@ -38,9 +41,6 @@ class BoardDataProviderTest extends BaseTestCase {
|
|||||||
// Transient stub: by default no active run.
|
// Transient stub: by default no active run.
|
||||||
Functions\when( 'get_transient' )->justReturn( false );
|
Functions\when( 'get_transient' )->justReturn( false );
|
||||||
|
|
||||||
// WP_Query stub: return empty by default; individual tests override.
|
|
||||||
Functions\when( 'WP_Query' )->justReturn( (object) array( 'posts' => array() ) );
|
|
||||||
|
|
||||||
// Admin URL stub.
|
// Admin URL stub.
|
||||||
Functions\when( 'admin_url' )->alias(
|
Functions\when( 'admin_url' )->alias(
|
||||||
function ( string $path = '' ) {
|
function ( string $path = '' ) {
|
||||||
@@ -55,6 +55,7 @@ class BoardDataProviderTest extends BaseTestCase {
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected function tearDown(): void {
|
protected function tearDown(): void {
|
||||||
|
\WP_Query::$_test_posts_queue = [];
|
||||||
unset( $GLOBALS['wpdb'] );
|
unset( $GLOBALS['wpdb'] );
|
||||||
parent::tearDown();
|
parent::tearDown();
|
||||||
}
|
}
|
||||||
@@ -139,15 +140,14 @@ class BoardDataProviderTest extends BaseTestCase {
|
|||||||
* Draft posts with the _prautoblogger_generated meta appear in In Review.
|
* Draft posts with the _prautoblogger_generated meta appear in In Review.
|
||||||
*/
|
*/
|
||||||
public function test_in_review_cards_from_draft_posts(): void {
|
public function test_in_review_cards_from_draft_posts(): void {
|
||||||
$post = new \stdClass();
|
$post = new \WP_Post();
|
||||||
$post->ID = 42;
|
$post->ID = 42;
|
||||||
$post->post_title = 'Test Draft Post';
|
$post->post_title = 'Test Draft Post';
|
||||||
$post->post_date_gmt = '2026-06-12 10:00:00';
|
$post->post_date_gmt = '2026-06-12 10:00:00';
|
||||||
|
$post->post_status = 'draft';
|
||||||
|
|
||||||
// WP_Query returns our fake post.
|
// Inject post into WP_Query queue: first WP_Query() call returns this post.
|
||||||
Functions\when( 'WP_Query' )->justReturn(
|
\WP_Query::$_test_posts_queue[] = array( $post );
|
||||||
(object) array( 'posts' => array( $post ) )
|
|
||||||
);
|
|
||||||
|
|
||||||
Functions\when( 'get_post_meta' )->alias(
|
Functions\when( 'get_post_meta' )->alias(
|
||||||
function ( $post_id, $key, $single ) use ( $post ) {
|
function ( $post_id, $key, $single ) use ( $post ) {
|
||||||
@@ -183,14 +183,14 @@ class BoardDataProviderTest extends BaseTestCase {
|
|||||||
* Published posts within the window appear in Published.
|
* Published posts within the window appear in Published.
|
||||||
*/
|
*/
|
||||||
public function test_published_cards_within_window(): void {
|
public function test_published_cards_within_window(): void {
|
||||||
$post = new \stdClass();
|
$post = new \WP_Post();
|
||||||
$post->ID = 77;
|
$post->ID = 77;
|
||||||
$post->post_title = 'Published Article';
|
$post->post_title = 'Published Article';
|
||||||
$post->post_date_gmt = gmdate( 'Y-m-d H:i:s', time() - DAY_IN_SECONDS );
|
$post->post_date_gmt = gmdate( 'Y-m-d H:i:s', time() - DAY_IN_SECONDS );
|
||||||
|
$post->post_status = 'publish';
|
||||||
|
|
||||||
Functions\when( 'WP_Query' )->justReturn(
|
// Inject post into WP_Query queue: first WP_Query() call returns this post.
|
||||||
(object) array( 'posts' => array( $post ) )
|
\WP_Query::$_test_posts_queue[] = array( $post );
|
||||||
);
|
|
||||||
|
|
||||||
Functions\when( 'get_post_meta' )->alias(
|
Functions\when( 'get_post_meta' )->alias(
|
||||||
function ( $post_id, $key, $single ) use ( $post ) {
|
function ( $post_id, $key, $single ) use ( $post ) {
|
||||||
@@ -269,8 +269,6 @@ class BoardDataProviderTest extends BaseTestCase {
|
|||||||
$this->wpdb->method( 'prepare' )->willReturn( 'SELECT 1' );
|
$this->wpdb->method( 'prepare' )->willReturn( 'SELECT 1' );
|
||||||
$this->wpdb->method( 'get_results' )->willReturn( array() );
|
$this->wpdb->method( 'get_results' )->willReturn( array() );
|
||||||
|
|
||||||
Functions\when( 'WP_Query' )->justReturn( (object) array( 'posts' => array() ) );
|
|
||||||
|
|
||||||
$provider = new \PRAutoBlogger_Board_Data_Provider();
|
$provider = new \PRAutoBlogger_Board_Data_Provider();
|
||||||
$snapshot = $provider->get_board_snapshot();
|
$snapshot = $provider->get_board_snapshot();
|
||||||
|
|
||||||
@@ -286,8 +284,6 @@ class BoardDataProviderTest extends BaseTestCase {
|
|||||||
$this->wpdb->method( 'prepare' )->willReturn( 'SELECT 1' );
|
$this->wpdb->method( 'prepare' )->willReturn( 'SELECT 1' );
|
||||||
$this->wpdb->method( 'get_results' )->willReturn( array() );
|
$this->wpdb->method( 'get_results' )->willReturn( array() );
|
||||||
|
|
||||||
Functions\when( 'WP_Query' )->justReturn( (object) array( 'posts' => array() ) );
|
|
||||||
|
|
||||||
$provider = new \PRAutoBlogger_Board_Data_Provider();
|
$provider = new \PRAutoBlogger_Board_Data_Provider();
|
||||||
$snapshot = $provider->get_board_snapshot();
|
$snapshot = $provider->get_board_snapshot();
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user