Create a Post with WordPress REST API from Remote Website

In this tutorial, I will guide you through the process of creating a post with the WordPress REST API. First, we’re going to talk about authentication, then we will send an example REST API request, and finally, we talk a little bit about request parameters.

WordPress REST API Authentication

Some time ago we had to use some external plugins in order to create an authentication with WordPress REST API from another website. One of those plugins was Application Passwords.

But the super-good news is that this plugin has been merged into WordPress Core version 5.6, and you do not have to install it anymore.

Now let’s get a pair of Login and Password for the REST API examples below.

Login – is the username. You can get a password if you go to the bottom of the profile settings page.

create application password for WordPress REST API authentication
So, the login is misha, and the password is 1HEu PFKe dnqM lr4j xDJX My63, we will need it in the examples below.

If you’re working on localhost, do not forget to open wp-config.php file and add the following constant there:

define( 'WP_ENVIRONMENT_TYPE', 'local' );

Create a Post with REST API – Example

Below, you will find some PHP code examples written with WordPress HTTP API functions, because I think there is no particular reason to use cURL for that purpose. I hope you don’t come up with the question of where to insert the code because it is more like a developer tutorial and I suppose you already know that anyway.

But now let me remind you that we have two websites:

Let’s create a simple draft right now!

$login = 'misha';
$password = '1HEu PFKe dnqM lr4j xDJX My63';

// create a post with WordPress REST API
wp_remote_post(
		'https://WEBSITE-DOMAIN/wp-json/wp/v2/posts',
		array(
			'headers' => array(
				'Authorization' => 'Basic ' . base64_encode( "$login:$password" )
			),
			'body' => array(
				'title'   => 'My test',
				'status'  => 'draft',
			)
		)
);

Once you run the above code correctly, the post will appear on “Website 1”.

WordPress REST API create post

Handle server response messages

Sometimes posts are not going to be created with the code you’re using. The good idea is to check error messages from the server and display them to users. I learned it the hard way when I only started developing my Simple WP Crossposting plugin. Because, it is much better to display a message to a user why something is not working instead of answering an extra support ticket.

$request = wp_remote_post( ... );

if( 'Created' !== wp_remote_retrieve_response_message( $request ) ) {
	// ok we have some errors here
	$body = json_decode( wp_remote_retrieve_body( $request ) );
	print_r( $body );
}

For example, you can get an error “Unknown username. Check again or try your email address,” which occurs when you’re trying to use an incorrect username in basic authentication of your REST API requests. I got it once when I tried to use the application name instead.

On the other hand, you can display success messages also:

$request = wp_remote_post( ... );

if( 'Created' === wp_remote_retrieve_response_message( $request ) ) {
	$body = json_decode( wp_remote_retrieve_body( $request ) );
	printf( 'The post %s has been created successfully', $body->title->rendered );
}

More parameters for REST API requests

In the above example, we just used title and status to create a post with REST API. But obviously. you will need more parameters for that, at least post content or maybe some metadata.

So, let’s take a look at the table below:

ParameterDescription
dateThe post date in a format, for example, 2024-11-07 05:00:00
slugThe post slug.
statusThe post status, for example draft, or published, or pending.
passwordThe post password (if it is a password-protected post).
titleThe post title.
contentThe post content.
authorThe post author ID; should exist on “Website 2”
excerptThe post excerpt.
featured_mediaThe ID of the post featured image.
comment_statusopen or closed
ping_statusopen or closed
metaThe associative array of post’s custom fields, more about custom fields in REST API requests you can read here.
stickyIs it a sticky post? true or false.
templateThe custom post template name when used.
categoriesThe array of category IDs.
tagsThe array of tag IDs.
Of course, all of them you can find in the official WordPress documentation.

You might be wondering, where is the type parameter, so we can create a custom post type with the REST API requests? The thing is that the type of a post is defined not by a request body parameter but by an endpoint, for example:

The $rest_base variable could be just a post type name or set specifically during a post type registration.

Misha Rudrastyh

Misha Rudrastyh

Hey guys and welcome to my website. For more than 10 years I've been doing my best to share with you some superb WordPress guides and tips for free.

Need some developer help? Contact me

Follow me on X