How to post content to WordPress using Python and Rest API

To get familiar with WordPress REST API, I fired up Python started playing with the requests module, the elegant and simple HTTP library for Python, built for human beings. Python and the WordPress REST API Handbook gave me enough information to get started.

The default cookies authentication mechanism would not work with Python and you need to install a plugin for this sort of application. See this tutorial on how to use the WordPress OAuth 1.0a plugin.

For a quick demo, the Application Passwords plugin for WordPress is the easiest choice. The installation is straightforward, and the instructions to generate a password for the client application are quite simple to follow. I needed to modify the .htaccess file due to the way my DreamPress site is configured. Notice: the password generated by the plugin contains white spaces, and they are part of the password. Once the WordPress authentication is taken care of, it’s all much easier.

On to Python, get json and requests modules ready, set the base URL of your WordPress site, your username and the application password generated by the plugin (including the white spaces):

import requests
import json

user = 'username'
pythonapp = 'G4kN hBNh r35J luXk aXyd n6Lm'
url = ''

The Application Password plugin requires a token made of username and password encoded in base64, so let python create it and add that to the http headers:

token = base64.standard_b64encode(user + ':' + pythonapp)
headers = {'Authorization': 'Basic ' + token}

Next, prepare some demo content for a new post. WordPress API expect a JSON object:

post = {'date': '2017-06-19T20:00:35',
        'title': 'First REST API post',
        'slug': 'rest-api-1',
        'status': 'publish',
        'content': 'this is the content post',
        'author': '1',
        'excerpt': 'Exceptional post!',
        'format': 'standard'

That’s all you need to create a post:

r = + '/posts', headers=headers, json=post)
print('Your post is published on ' + json.loads(r.content)['link'])

You’ll see printed on screen the URL of the new post. That was fun and quick :slight_smile: Now let’s publish an image: first you have to add it to the Media library (as you would when you use WordPress admin panel). To publish images you’ll need to use the media API endpoint. For the example, use the file demo.jpg in the current directory

media = {'file': open('demo.jpg',rb),
'caption': 'My great demo picture'}

And let Python requests do the heavy lifting:

image = + '/media', headers=headers, files=media)
print('Your image is published on ' + json.loads(image.content)['link'])

That should give you the URL for the image you just uploaded. Now to embed that image in a post, we can edit its content. To update a post we need to find its ID and push to the API endpoint the new value using JSON.

imgsrc = json.loads(up.content)['source_url']
postid = json.loads(r.content)['id']
updatedpost = {'content': 'Changed things.<img src=' 
        + imgsrc
        + '>'}

Update the post with the new content:

update = + '/posts/' + postid, headers=headers, json=updatedpost)
print('The updated post is published on ' + json.loads(updatedpost.content)['link'])

And that’s all: you created a new post, added an image to WordPress media library and modified a post using only Python and the REST API.


@smaffulli Hello,
I have a doubt tho…
What if I want to upload a media from URL?
Like for example “
So… Instead of

 media = {'file': open('demo.jpg',rb)}

can i do…

media = {'file': <img src=\"\" />"}


media = {'file': urllib.request.urlopen("")}

And then use this media… as the Featured Image Only?
I am not sure whether this will work… Thank you for every and any kind of Help :blush:

1 Like

I think that as long as the media contains an image for Python, it should work. Try and see if/how that fails.


@smaffulli Ok… I will try that out and … How do I use that same image in the same program to set as Featured Image?
Thank you :slight_smile:


@sdk If you use python3.5 or later then you have to encode slightly differently.

token = base64.standard_b64encode(b’user + “:” + pythonapp’)
headers = {‘Authorization’: 'Basic ’ + str(token)}

I changed these lines to this and it now works.

Thanks for sharing @smaffulli.

I tried this with Python 3.5 and had to make some changes to your code. I thought I’d share my final working code for creating a new post – in case other folks using Python 3.5+ find it helpful:

import requests
import json
import base64

user = 'username'
pythonapp = 'G4kN hBNh r35J luXk aXyd n6Lm'
url = ''

data_string = user + ':' + pythonapp

token = base64.b64encode(data_string.encode())

headers = {'Authorization': 'Basic ' + token.decode('utf-8')}

post = {'date': '2017-06-19T20:00:35',
		'title': 'First REST API post',
		'slug': 'rest-api-1',
		'status': 'publish',
		'content': 'this is the content post',
		'author': '1',
		'excerpt': 'Exceptional post!',
		'format': 'standard'

r = + '/posts', headers=headers, json=post)

print('Your post is published on ' + json.loads(r.content.decode('utf-8'))['link']) 


Hey I did the exact same you did… I also had an issue with the bytes to string and string to bytes conversion…
However, even after doing this, i get the error:
Traceback (most recent call last):
File “C:\Users\Jarvis\Desktop\”, line 33, in
print('Your post is published on ’ + json.loads(r.content.decode(‘utf-8’))[‘link’])
KeyError: ‘link’

Also, i copy pasted your code and just swapped out the username, pwd, url… and got the exact same error…

Please can you help ? I tried a lot but it doesn’t seem to work… I edited the HTACCESS file and all the other things… But is still get the same error

Can you print your JSON response and share it here?


I’m having the same problem as Dr_Shah

My server is giving error [Response 400]

I’ve updated htaccess, installed the plugin and don’t know where the problem is.

Try using a tool like Postman to debug this.

Hello there,

I’m trying to automate updating a link on a WP page using the REST api, and came across this plugin for the authentication.

I’ve got most of my script worked out, and everything seems to be working - I’m getting a status code of 200 returned… but the actual link on the page isn’t getting updated.

Any suggestions?

Thanks for this update… I was following the code in the original post, and not able to get authenticated. This helped clear that up!

Might be worth putting a blurb in the original post (if possible) pointing folks to the appropriate comment below…

Hi!Could you tell me how should I change the categories?Please!

How to set featured image?

I am getting error while posting to my wordpress… i have modded the .htaccess file and created an application password, which i am using in the code…

can someone help me understand [‘link’] ???

print('Your post is published on ' + json.loads(r.content)['link'])

File “/usr/lib/python3.8/json/”, line 357, in loads
return _default_decoder.decode(s)
File “/usr/lib/python3.8/json/”, line 337, in decode
obj, end = self.raw_decode(s, idx=_w(s, 0).end())
File “/usr/lib/python3.8/json/”, line 355, in raw_decode
raise JSONDecodeError(“Expecting value”, s, err.value) from None
json.decoder.JSONDecodeError: Expecting value: line 1 column 1 (char 0)

i tried codes by smaffulli and omerkhan… but i am getting the same json error… what am i missing…

how can we add meta tags or any tags that will help us rank in search pages through rest api?