admin管理员组

文章数量:1193817

I need to sync a Rails database with a WordPress db, using API calls. Each Rails record creates one wp_post, and up to 15 wp_postmeta records. I can loop over the data that becomes the postmetas, but that takes a long time. I assume most of that time comes from making so many API calls, so I'm trying to cut that number down to one.

For a single record, I've cobbled this URL together, which works:

/?post_id=202559&meta_key=activity_id&meta_value=2387511

I tried putting the following into my functions.php file to create a custom route:

function bulk_import_postmeta($request) {
    $metas = $request->get_param("meta");
  if (is_array($metas)) {
    foreach($metas as $meta){
      update_post_meta($meta[0], $meta[1], $meta[2]);
    }
  }
}

add_action( 'rest_api_init', function() {
    register_rest_route('/imports/v1', '/postmeta_bulk/',
        array(
            'methods' => 'POST',
            'callback' => 'bulk_import_postmeta',
            'args' => array('meta' => array('required' => true))));
});

—but I don't know how I need to encode the URL when I call it, and I don't know if it would work if I did.

My question is, then: given a post_id, what API call can I make to bulk create these wp_postmeta records?

I need to sync a Rails database with a WordPress db, using API calls. Each Rails record creates one wp_post, and up to 15 wp_postmeta records. I can loop over the data that becomes the postmetas, but that takes a long time. I assume most of that time comes from making so many API calls, so I'm trying to cut that number down to one.

For a single record, I've cobbled this URL together, which works:

https://mysite.wpengine.com/wp-json/imports/v1/new_postmeta/?post_id=202559&meta_key=activity_id&meta_value=2387511

I tried putting the following into my functions.php file to create a custom route:

function bulk_import_postmeta($request) {
    $metas = $request->get_param("meta");
  if (is_array($metas)) {
    foreach($metas as $meta){
      update_post_meta($meta[0], $meta[1], $meta[2]);
    }
  }
}

add_action( 'rest_api_init', function() {
    register_rest_route('/imports/v1', '/postmeta_bulk/',
        array(
            'methods' => 'POST',
            'callback' => 'bulk_import_postmeta',
            'args' => array('meta' => array('required' => true))));
});

—but I don't know how I need to encode the URL when I call it, and I don't know if it would work if I did.

My question is, then: given a post_id, what API call can I make to bulk create these wp_postmeta records?

Share Improve this question asked Jul 28, 2022 at 0:11 amp108amp108 1112 bronze badges 2
  • Can you dump to csv and use eg wp-cli? – birgire Commented Jul 28, 2022 at 15:12
  • @birgire, the process needs to be automatic and cron-tabbable. – amp108 Commented Jul 28, 2022 at 16:04
Add a comment  | 

1 Answer 1

Reset to default 2

We can use the existing meta property (see docs) to add multiple meta fields (in a JSON format) when we create a post via POST method:

POST: example.com/wp-json/wp/v2/posts/

Body payload:

{
    "title": "My title",
    "content": "My content",
    "meta": {"myfield1":"myvalue1", "myfield2":"myvalue2"}
}

or when we want to update a post with ID 123:

POST: example.com/wp-json/wp/v2/posts/123

Body payload:

{
    "title": "My title 2",
    "content": "My content 2",
    "meta": {"myfield1":"myvalue11", "myfield2":"myvalue22"}
}

Note that we will have to register the meta fields with corresponding schema properties (see docs and docs), for example registering meta field myfield1 as a string with:

add_action( 'rest_api_init', function() {
    register_post_meta(
         'post', // post type
         'myfield1', // meta key
         array(
             'single'       => true,
             'type'         => 'string',
             'show_in_rest' => array(
                 'schema' => array(
                     'type'    => 'string',
                     'default' => '',
                 ),
             ),
         )
     );
} );

We can see how the meta scheme property is checked in the rest posts controller:

if ( ! empty( $schema['properties']['meta'] ) && isset( $request['meta'] ) ) {
    $meta_update = $this->meta->update_value( $request['meta'], $post_id );

    if ( is_wp_error( $meta_update ) ) {
        return $meta_update;
    }
}

https://developer.wordpress.org/reference/classes/wp_rest_posts_controller/create_item/

本文标签: rest apiHow To Bulk Import wppostmeta records in an API call