Skip to content

Commit

Permalink
Properly handle getting/updating fields for different object types.
Browse files Browse the repository at this point in the history
Squashed commit of the following:

commit 7e9ee84159c9b45781f86423c9ddb66d6f8eaf05
Author: Justin Sternberg <justin@dsgnwrks.pro>
Date:   Thu Oct 20 17:35:08 2016 -0400

    Fix bleeding global scope by resetting object params at teardown, and uncomment tests

commit 41c542277b6c9a2c730793f0b8507e178d522fb1
Author: Justin Sternberg <justin@dsgnwrks.pro>
Date:   Thu Oct 20 17:31:09 2016 -0400

    Make CMB2_REST::$boxes and CMB2_REST::$type_boxes properties protected

    Also add a get_all method for $boxes

commit 4e6044d6bd9a3a400286a4c7cf58b10dc93f39df
Merge: 82a6679 4a91731
Author: Justin Sternberg <justin@dsgnwrks.pro>
Date:   Wed Oct 19 11:46:16 2016 -0400

    Merge branch 'trunk' into cmb2-rest-api-update

commit 82a6679ddcc1b3084c49ee125ed23333793478a6
Author: Justin Sternberg <justin@dsgnwrks.pro>
Date:   Wed Oct 19 09:53:36 2016 -0400

    Need to figure out what the deal is with the tests initiations since they run in isolation, but not with all tests
  • Loading branch information
jtsternberg committed Oct 20, 2016
1 parent f19a751 commit 35e1e72
Show file tree
Hide file tree
Showing 6 changed files with 142 additions and 84 deletions.
129 changes: 74 additions & 55 deletions includes/CMB2_REST.php
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,18 @@ class CMB2_REST extends CMB2_Hookup_Base {
* @var CMB2_REST[] objects
* @since 2.2.4
*/
public static $boxes;
protected static $boxes = array();

/**
* @var array Array of cmb ids for each type.
* @since 2.2.4
*/
protected static $type_boxes = array(
'post' => array(),
'user' => array(),
'comment' => array(),
'term' => array(),
);

/**
* Array of readable field objects.
Expand Down Expand Up @@ -128,19 +139,18 @@ public function init_routes() {
*/
public static function register_cmb2_fields() {
$alltypes = $taxonomies = array();
$has_user = $has_comment = $has_taxonomies = false;

foreach ( self::$boxes as $cmb_id => $rest_box ) {
$types = array_flip( $rest_box->cmb->box_types() );

if ( isset( $types['user'] ) ) {
unset( $types['user'] );
$has_user = true;
self::$type_boxes['user'][ $cmb_id ] = $cmb_id;
}

if ( isset( $types['comment'] ) ) {
unset( $types['comment'] );
$has_comment = true;
self::$type_boxes['comment'][ $cmb_id ] = $cmb_id;
}

if ( isset( $types['term'] ) ) {
Expand All @@ -151,11 +161,12 @@ public static function register_cmb2_fields() {
CMB2_Utils::ensure_array( $rest_box->cmb->prop( 'taxonomies' ) )
);

$has_taxonomies = true;
self::$type_boxes['term'][ $cmb_id ] = $cmb_id;
}

if ( ! empty( $types ) ) {
$alltypes = array_merge( $alltypes, array_flip( $types ) );
self::$type_boxes['post'][ $cmb_id ] = $cmb_id;
}
}

Expand All @@ -165,15 +176,15 @@ public static function register_cmb2_fields() {
self::register_rest_field( $alltypes, 'post' );
}

if ( $has_user ) {
if ( ! empty( self::$type_boxes['user'] ) ) {
self::register_rest_field( 'user', 'user' );
}

if ( $has_comment ) {
if ( ! empty( self::$type_boxes['comment'] ) ) {
self::register_rest_field( 'comment', 'comment' );
}

if ( $has_taxonomies ) {
if ( ! empty( self::$type_boxes['term'] ) ) {
self::register_rest_field( $taxonomies, 'term' );
}
}
Expand Down Expand Up @@ -354,24 +365,21 @@ protected static function get_rest_values( $object, $request, $object_type, $mai

$values = array();

foreach ( self::$boxes as $cmb_id => $rest_box ) {
$check = 'term' === $main_object_type ? 'term' : $object_type;

// This is not the box you're looking for...
if ( ! in_array( $check, $rest_box->cmb->box_types() ) ) {
continue;
}
if ( ! empty( self::$type_boxes[ $main_object_type ] ) ) {
foreach ( self::$type_boxes[ $main_object_type ] as $cmb_id ) {
$rest_box = self::$boxes[ $cmb_id ];

foreach ( $rest_box->read_fields as $field_id ) {
$rest_box->cmb->object_id( $object['id'] );
$rest_box->cmb->object_type( $main_object_type );
foreach ( $rest_box->read_fields as $field_id ) {
$rest_box->cmb->object_id( $object['id'] );
$rest_box->cmb->object_type( $main_object_type );

$field = $rest_box->cmb->get_field( $field_id );
$field = $rest_box->cmb->get_field( $field_id );

$field->object_id( $object['id'] );
$field->object_type( $main_object_type );
$field->object_id( $object['id'] );
$field->object_type( $main_object_type );

$values[ $cmb_id ][ $field->id( true ) ] = $field->get_data();
$values[ $cmb_id ][ $field->id( true ) ] = $field->get_data();
}
}
}

Expand Down Expand Up @@ -472,25 +480,27 @@ protected static function update_rest_values( $values, $object, $request, $objec
return;
}

// @todo verify that $object_type matches this output.
$data = self::get_object_data( $object );
if ( ! $data ) {
$object_id = self::get_object_id( $object, $main_object_type );

if ( ! $object_id ) {
return;
}

$updated = array();

// @todo Security hardening... check for object type, check for show_in_rest values.
foreach ( self::$boxes as $cmb_id => $rest_box ) {
if ( ! array_key_exists( $cmb_id, $values ) ) {
continue;
}
if ( ! empty( self::$type_boxes[ $main_object_type ] ) ) {
foreach ( self::$type_boxes[ $main_object_type ] as $cmb_id ) {
$rest_box = self::$boxes[ $cmb_id ];

$rest_box->cmb->object_id( $data['object_id'] );
$rest_box->cmb->object_type( $data['object_type'] );
if ( ! array_key_exists( $cmb_id, $values ) ) {
continue;
}

// TODO: Test since refactor.
$updated[ $cmb_id ] = $rest_box->sanitize_box_values( $values );
$rest_box->cmb->object_id( $object_id );
$rest_box->cmb->object_type( $main_object_type );

$updated[ $cmb_id ] = $rest_box->sanitize_box_values( $values );
}
}

return $updated;
Expand Down Expand Up @@ -587,27 +597,26 @@ public function is_protected_meta( $protected, $meta_key, $meta_type ) {
return $protected;
}

protected static function get_object_data( $object ) {
$object_id = 0;
if ( isset( $object->ID ) ) {
$object_id = intval( $object->ID );
$object_type = isset( $object->user_login ) ? 'user' : 'post';
} elseif ( isset( $object->comment_ID ) ) {
$object_id = intval( $object->comment_ID );
$object_type = 'comment';
} elseif ( is_array( $object ) && isset( $object['term_id'] ) ) {
$object_id = intval( $object['term_id'] );
$object_type = 'term';
} elseif ( isset( $object->term_id ) ) {
$object_id = intval( $object->term_id );
$object_type = 'term';
}

if ( empty( $object_id ) ) {
return false;
}

return compact( 'object_id', 'object_type' );
protected static function get_object_id( $object, $object_type = 'post' ) {
switch ( $object_type ) {
case 'user':
case 'post':
if ( isset( $object->ID ) ) {
return intval( $object->ID );
}
case 'comment':
if ( isset( $object->comment_ID ) ) {
return intval( $object->comment_ID );
}
case 'term':
if ( is_array( $object ) && isset( $object['term_id'] ) ) {
return intval( $object['term_id'] );
} elseif ( isset( $object->term_id ) ) {
return intval( $object->term_id );
}
}

return 0;
}

public function field_can_read( $field_id, $return_object = false ) {
Expand Down Expand Up @@ -652,6 +661,16 @@ public static function remove( $cmb_id ) {
}
}

/**
* Retrieve all CMB2_REST instances from the registry.
*
* @since 2.2.4
* @return CMB2[] Array of all registered CMB2_REST instances.
*/
public static function get_all() {
return self::$boxes;
}

/**
* Checks if given value is readable.
*
Expand Down
5 changes: 3 additions & 2 deletions includes/CMB2_REST_Controller_Boxes.php
Original file line number Diff line number Diff line change
Expand Up @@ -78,13 +78,14 @@ public function register_routes() {
public function get_items( $request ) {
$this->initiate_request( $request, 'boxes_read' );

if ( empty( CMB2_REST::$boxes ) ) {
$boxes = CMB2_REST::get_all();
if ( empty( $boxes ) ) {
return new WP_Error( 'cmb2_rest_no_boxes', __( 'No boxes found.', 'cmb2' ), array( 'status' => 403 ) );
}

$boxes_data = array();
// Loop boxes and get specific field.
foreach ( CMB2_REST::$boxes as $this->rest_box ) {
foreach ( $boxes as $this->rest_box ) {
if ( $this->rest_box->rest_read ) {
$rest_box = $this->get_rest_box();
$boxes_data[ $this->rest_box->cmb->cmb_id ] = $this->server->response_to_data( $rest_box, isset( $this->request['_embed'] ) );
Expand Down
40 changes: 32 additions & 8 deletions tests/cmb-rest-tests-base.php
Original file line number Diff line number Diff line change
Expand Up @@ -43,19 +43,32 @@ public function set_up_and_init( $metabox_array ) {
foreach ( $this->metabox_array['fields'] as $field ) {
update_post_meta( $this->post_id, $field['id'], md5( $field['id'] ) );
}

CMB2_REST::register_cmb2_fields();
}

public function tearDown() {
parent::tearDown();
foreach ( $this->metabox_array['fields'] as $field ) {
delete_post_meta( $this->post_id, $field['id'] );
if ( ! empty( $this->metabox_array['fields'] ) ) {
foreach ( $this->metabox_array['fields'] as $field ) {
delete_post_meta( $this->post_id, $field['id'] );
}
}
CMB2_Boxes::remove( $this->cmb_id );
CMB2_REST::remove( $this->cmb_id );

Test_CMB2_REST_Object::reset_boxes();
Test_CMB2_REST_Object::reset_type_boxes();

foreach ( CMB2_Boxes::get_all() as $box ) {
CMB2_Boxes::remove( $box->cmb_id );
}

global $wp_actions, $wp_rest_server;
unset( $wp_rest_server );
unset( $wp_actions['rest_api_init'] );
}

protected function reset_instances() {
foreach ( CMB2_REST::$boxes as $cmb_id => $rest ) {
foreach ( CMB2_REST::get_all() as $cmb_id => $rest ) {
$rest = new CMB2_REST( $rest->cmb );
$rest->universal_hooks();
}
Expand Down Expand Up @@ -116,7 +129,7 @@ protected function assertResponseData( $data, $response ) {

if ( ! class_exists( 'Test_CMB2_REST_Object' ) ) {
/**
* Simply allows access to the mb_defaults protected property (for testing)
* Make some things accessible in the CMB2_REST class.
*/
class Test_CMB2_REST_Object extends CMB2_REST {
public function declare_read_edit_fields() {
Expand All @@ -128,8 +141,19 @@ public function can_read( $show_in_rest ) {
public function can_edit( $show_in_rest ) {
return parent::can_edit( $show_in_rest );
}
public static function get_object_data( $object ) {
return parent::get_object_data( $object );
public static function get_object_id( $object, $object_type = 'post' ) {
return parent::get_object_id( $object, $object_type );
}
public static function reset_boxes() {
parent::$boxes = array();
}
public static function reset_type_boxes() {
parent::$type_boxes = array(
'post' => array(),
'user' => array(),
'comment' => array(),
'term' => array(),
);
}
}
}
4 changes: 4 additions & 0 deletions tests/test-cmb-rest-controllers.php
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,10 @@ public function setUp() {
) );
}

public function tearDown() {
parent::tearDown();
}

public function test_get_schema() {
$this->assertResponseStatuses( '/' . CMB2_REST::NAME_SPACE, array(
'GET' => 200,
Expand Down

0 comments on commit 35e1e72

Please sign in to comment.