11

I am trying to create a REST APIs for my wordpress website which is used for facility listing using wordpress job manager plugin.

I have registered my custom post , taxonomies in \plugins\rest-api\plugin.php.

below API gives me all the listings with default response.

http://localhost/sports/wp-json/wp/v2/joblisting/

I wanted to add post meta in the JSON response using the below code.

function slug_register_phone_number() {
            register_rest_field( 'job_listing',
                'phone',
            array(
                'get_callback' => 'slug_get_phone_number',
                'update_callback' => null,
                'schema' => null,
            )
        );
    }

    function slug_get_phone_number($post, $field_name, $request) {
        return get_post_meta($post->id, '_phone' );
    }
}

Using above code i am able to add "phone" as a REST response but i am always getting phone = false in response. It is not showing the correct data from wp_postmeta table.

I have followed below mentioned links for reference.

http://v2.wp-api.org/extending/modifying/

Plug in details. 1. WP Job manager 2. rest-api

Any help will be really helpful.

6
  • where do you see the "false"? Have you checked what is actually going on the "wire" with the browser's network tools? Commented May 23, 2016 at 3:32
  • Hi i am getting in JSON as a response.
    – Hari Soni
    Commented May 23, 2016 at 3:33
  • I am using chrome plugin postman to hit the service. I am not using any kind of authentication. Its a simple API request without any data in request body.
    – Hari Soni
    Commented May 23, 2016 at 3:52
  • then how do you know that you actually trigger the right post? do you even get to that callback?. Commented May 23, 2016 at 3:56
  • I am new to PHP and wordpress. I am working with JAVA for long time. Could you please let me know how i can check if my function is called or not? I tried to print the post object but not able to see the value..
    – Hari Soni
    Commented May 23, 2016 at 4:38

5 Answers 5

7

$post in the callback function is an array, not an object. So you cannot use $post->id. Change it to $post['id'] and it should work:

function slug_get_phone_number($post, $field_name, $request)
{
    return get_post_meta($post['id'], '_phone', true);
}

I recommend to change _phone to phone_number or something else without underscore prefix. Because _ is often used with private meta keys. Try to add a custom field which has meta key with _ prefix directly to your post, you will see what I meant.

20

WP API has a rest_prepare_post filter (or rest_prepare_CPT if you are working with custom posts) which you can use to modify the JSON response. In your case it will be rest_prepare_joblisting.

function filter_joblisting_json( $data, $post, $context ) {
$phone = get_post_meta( $post->ID, '_phone', true );

if( $phone ) {
    $data->data['phone'] = $phone;
}

return $data;
}
add_filter( 'rest_prepare_joblisting', 'filter_joblisting_json', 10, 3 );

Using the same filter you can also remove fields/data from the response and do any manipulation of the data.

2
  • +1 as it is probably a better way than trying to get each info in different requests as the OP seems to do. Commented May 23, 2016 at 16:50
  • This solution worked perfectly for me
    – Asif
    Commented Sep 23, 2017 at 18:40
3

Just Add this methods to function.php

add_action( 'rest_api_init', 'create_api_posts_meta_field' );

function create_api_posts_meta_field() {

 // register_rest_field ( 'name-of-post-type', 'name-of-field-to-return', array-of-callbacks-and-schema() )
 register_rest_field( 'tour', 'metaval', array(
 'get_callback' => 'get_post_meta_for_api',
 'schema' => null,
 )
 );
}

function get_post_meta_for_api( $object ) {
 //get the id of the post object array
 $post_id = $object['id'];

 //return the post meta
 return get_post_meta( $post_id );
}
0

Here is an OOP example:

class MetaDataFetcher{

    public function enableAPIroute(){
        add_action ('rest_api_init', array($this, 'doRegisterRoutes'));
    }

    public function doRegisterRoutes(){
        register_rest_route(
            'yournamespace/vXX',
            'fetch-post-meta',
            array(
                'methods'               => array('GET','POST'),
                'callback'              => array($this, 'returnMetaData'),

                //You should have a better auth, or this endpoint will be exposed
                permission_callback'   => function(){return TRUE;}
        );
    }

    public function returnMetaData(){
        if (!(isset($_REQUEST['post-id']))){
            return "ERROR: No post ID";
        }
        $postID = $_REQUEST['post-id'];
        $meta = get_post_meta($postID);
        $meta = json_encode($meta);
        return $meta;
    }
}

$MetaDetaFetcher = New MetaDataFetcher;
$MetaDetaFetcher->enableAPIroute();
0

I tested and used what seems to be an easier way to me, after you register the custom post type you can also register the custom meta and make it available in the rest API.

See register_meta()

register_post_type( 'job_listing', $args ); // in $args you can make the post type available in rest api
register_meta(
    'post', '_phone', [
    'object_subtype' => 'job_listing',
        'show_in_rest' => true
    ]
   );

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.