Getting Post Meta for the WP REST API

Getting Post Meta for the WP REST API

My friend and I are working on a little side project. It’s a job posting site for an industry we’re familiar with: ESL jobs around the world. While this project could be seen as “just another job board”, we’re hoping to add some features that will make it fun to use and valuable for schools and recruiters. I of course want to build it on WordPress, but to get a some of the functionality I want, I need to expose some post meta to the WP REST API.

In researching how to do this, I quickly found out that the WP REST API doesn’t naturally expose post or user meta. As with most things WP REST API, you don’t have to go too far down the rabbit hole before you find a practical article written by the Josh Pollock. While the register_api_field function isn’t in use anymore, the register_rest_field function is, so this article and that function were all I needed to get going.

Here’s the code for getting all post meta for the WP REST API:

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( 'post', 'post-meta-fields', 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 );

The comments in there are self explanatory, but this also allows me to get the custom fields for any custom post type as well (Josh’s example is a jedi custom post type, which is way cooler than my practical job-postings custom post type 🙂 ). That way, I can save whatever information in the custom fields of my job-postings custom post type I need, like:

  • application deadline
  • salary
  • location
  • type of teaching job
  • whatever else I need!

While it currently exposes all post meta, I can definitely filter it as I need to to remove anything extra. However, here’s the basic post meta dump in a post endpoint:

Hopefully, if you’re struggling on how to get this done, this snippet will help and you can extend it how you like.




UPDATE Feb. 2, 2018

Josh Pollock recently wrote a new article reviewing the register_meta() function. This function has gotten some updates and love, and now allows for you add an array of arguments, one of which is 'show_in_rest' => true. This allows the meta to be shown as children of the meta node (empty in the above screenshot). That’s pretty nice! The original version of this will still work, and there are some cases where you should still use it.

Josh outlines different use cases and how to use the new array of arguments here. There’s also a link in that article to an article by Pippin Williamson about using custom table meta data in the REST API. Enjoy!

0 responses to “Getting Post Meta for the WP REST API”

  1. Marco Avatar

    I know this may sound stupid, but I have to share this. Part of the whole ordeals you get whilst developing where you just laugh at something so bad. I accidentally placed the REST-API code on the WP install that requests the info… [face_i_suck] and spent a day trying to figure out why it didn’t work… hahaaha.

    1. Nate Avatar

      Hahaha, I’ve been there, Marco. I’m glad you got it figured out!

  2. chris Avatar

    Excellent and very useful. However, I do hope that in a future release the post meta fields, user meta fields and importantly, the advanced custom fields, are all exposed, so they can all be read and updated in one api.

    1. Nate Avatar

      Hey Chris! Yeah, I hear that a lot from folks. I think I think the main thing about meta is that it can be used to store anything, and some folks might just start using the custom fields stuff as a dump for “all the extra stuff”… I think the folks who put the API together kinda said “We don’t know what could be in there, so we don’t want to expose it by default.” That’s purely my speculation :-). And by “using the custom fields”, I mean the default fields that ship with wp-core, plus anything that gets associated with the post that’s not in the wp_posts table by default… Again, my speculation. Have a good one!

  3. Emilio Dominguez Avatar

    Amazing, you are such a great dev thanks for your tutorials

    1. Nate Avatar

      Happy to help! 🙂

  4. Mark Haynes Avatar

    This is great. Do you know how we can use the REST Api to update custom fields though?

    1. Nate Avatar

      Hey Mark! I’m actually not sure, never had to do that, but I bet it’s possible:-)

  5. Ricardo Avatar

    Man, you’re my WP Hero!
    Help me a lot! Thank you!

    1. Nate Avatar

      Hey Ricardo, hahahaha, happy to help!

  6. wgo Avatar

    what to say as an json array to add/modify content of post meta ?!
    lets say :

    post = {'date': '2018-02-19T22:44:35',
    'title': 'whatever',
    'slug': 'rest-api-1',
    'status': 'publish',
    'content': 'whatever',
    'author': '1',
    'excerpt': 'whatever',
    'format': 'standard',
    'post-meta-fields': [
    'views': [{
    '0': '333'

    which perfectly works for posts but not for metaposts

    1. Nate Avatar

      Hey WGO, I’m not really sure what you’re asking here.

      1. wgo Avatar

        why am i only allowed to display meta,categories,tags without being able to modify, add new content to it,
        found lot of out-dated plugins neither of them worked etc

        1. Nate Avatar

          Hey WGO, that is a great question for the RESTAPI team. Have you checked with them on Slack?:

  7. Jonathan Avatar

    Hi Nate,

    This is a very basic question, but — where do I put this code? I’m a React Native developer making an app based on a WP site. I have FTP access to the WP site so I can get to the PHP files. I don’t know what files you’re putting these functions in. Can you help?

    1. Nate Avatar

      Hey Jonathan! No worries, you might have figured this out by now but you can put this in your child theme’s functions.php file, or create a quick plugin and add it there (I’d probably opt for the second approach).