Skip to content

Commit

Permalink
Merge pull request #714 from epeli/global-post-test
Browse files Browse the repository at this point in the history
Setup postdata on field levels
  • Loading branch information
jasonbahl committed Mar 11, 2019
2 parents 7750d33 + 3569055 commit b1caf66
Show file tree
Hide file tree
Showing 5 changed files with 31 additions and 11 deletions.
8 changes: 0 additions & 8 deletions src/Data/DataSource.php
Expand Up @@ -179,14 +179,6 @@ public static function resolve_post_object( $id, $post_type ) {
remove_filter( 'the_content', 'prepend_attachment' );
}

/**
* Set the resolving post to the global $post. That way any filters that
* might be applied when resolving fields can rely on global post and
* post data being set up.
*/
$GLOBALS['post'] = $post_object;
setup_postdata( $post_object );

return $post_object;

}
Expand Down
5 changes: 5 additions & 0 deletions src/Request.php
Expand Up @@ -139,9 +139,14 @@ private function after_execute( $response ) {
* This allows for a GraphQL query to be used in the middle of post content, such as in a Shortcode
* without disrupting the flow of the post as the global POST before and after GraphQL execution will be
* the same.
*
* We cannot use wp_reset_postdata here because it just resets the post from the global query which can
* be anything the because the resolvers themself can set it to whatever. So we just manually reset the
* post with setup_postdata we cached before this request.
*/
if ( ! empty( $this->global_post ) ) {
$GLOBALS['post'] = $this->global_post;
setup_postdata( $this->global_post );
}

/**
Expand Down
17 changes: 17 additions & 0 deletions src/Utils/InstrumentSchema.php
Expand Up @@ -17,6 +17,12 @@
*/
class InstrumentSchema {

/**
* Cache post for the resolvers so we can call the setup_postdata only when the actual
* source post changes
*/
private static $cached_post = null;

/**
* @param \WPGraphQL\WPSchema $schema
*
Expand Down Expand Up @@ -110,6 +116,17 @@ protected static function wrap_fields( $fields, $type_name ) {
*/
$field->resolveFn = function( $source, array $args, AppContext $context, ResolveInfo $info ) use ( $field_resolver, $type_name, $field_key, $field ) {

/**
* Setup the global post to the current post (if a post)
* This ensures that functions like get_the_content() work correctly
* so graphql queries can be used in the loop without issues.
*/
if ( is_a( $source, 'WP_Post' ) && self::$cached_post !== $source ) {
self::$cached_post = $source;
$GLOBALS['post'] = $source;
setup_postdata( $source );
}

/**
* Fire an action BEFORE the field resolves
*
Expand Down
4 changes: 2 additions & 2 deletions tests/wpunit/PostObjectConnectionQueriesTest.php
Expand Up @@ -732,12 +732,12 @@ public function testPostExcerptsAreDifferent() {

$post_1_args = [
'post_content' => 'Post content 1',
'post_excerpt' => 'Post excerpt 1',
'post_excerpt' => '',
];

$post_2_args = [
'post_content' => 'Post content 2',
'post_excerpt' => 'Post excerpt 2',
'post_excerpt' => '',
];

$post_1_id = $this->createPostObject( $post_1_args );
Expand Down
8 changes: 7 additions & 1 deletion tests/wpunit/PostObjectQueriesTest.php
Expand Up @@ -1355,9 +1355,15 @@ public function testPostQueryPostDataReset() {
do_graphql_request( $graphql_query );

/**
* Asset that the query has been reset to the main query.
* Assert that the query has been reset to the main query.
*/
$this->assertEquals( $main_query_post_id, $post->ID );

// setup_postdata sets the global $id too so assert it is reset back to
// original
// https://github.com/WordPress/WordPress/blob/b5542c6b1b41d69b4e5c26ef8280c6e85de67224/wp-includes/class-wp-query.php#L4158
$this->assertEquals( $main_query_post_id, $GLOBALS['id'] );

}

/**
Expand Down

0 comments on commit b1caf66

Please sign in to comment.