An HTTP 415 error means the server refused your request because it cannot handle the format of the data you sent. In WordPress it shows up on REST API calls, form posts and image uploads. In our tests the fix was always the Content-Type header or a rule that checks it.
We reproduced the error on a WordPress 7.1.3 and WooCommerce 11.2 test site in October 2026. We used curl, a block editor upload and two different senders of the 415. Every fix below comes from a request that failed and then worked.
You will get the exact meaning of the status code, a way to find which layer sent it, and three causes with tested fixes. We also cover why a blocked file type is a different error.
What Does the 415 Unsupported Media Type Status Code Mean?
An HTTP 415 error means the server refused the request because the format of its content is not supported. RFC 9110 says the cause might be “the request’s indicated Content-Type or Content-Encoding”, or what the server finds when it inspects the data. MDN adds that some servers are strict about the Content-Type they expect.
The 415 status code, also called 415 unsupported media type, is about the request body you send. A good server can also reply with an Accept-Post header that names the type it wants, and MDN shows an example of that.
Browsers and API tools report the same status in different words. You might see “Unsupported Media Type”, “HTTP error 415” or a console line that says the server responded with a status of 415.
| Status | What to check | What it means |
|---|---|---|
| 400 | The JSON syntax | The server could not read the body |
| 406 | The Accept header | No response format fits the request |
| 415 | The Content-Type header | The server refuses the request body format |
| 422 | The field values | The format is fine but the content cannot be used |

The 406 row comes from MDN’s 406 page, which ties it to the Accept header. Our guides on the 400 Bad Request error and the 406 Not Acceptable error cover the neighbors.
Does WordPress Itself Send an HTTP 415 Error?
WordPress core and WooCommerce do not send an HTTP 415 error on their own. We searched the WordPress 7.1.3 and WooCommerce 11.2.0 code and found 415 only in lists of status names and an HTTP client class. A 415 on your site comes from the server, a firewall, a plugin, a theme or the client.
We then sent six requests to a stock WordPress REST API to see what core does with a wrong Content-Type. None of them returned a 415:
| Request | Result |
|---|---|
| JSON body with a JSON header | 201 created |
| Form data with a form header | 201 created |
| JSON body with a text/plain header | 400 empty_content because the body was ignored |
| Form body with a JSON header | 400 rest_invalid_json |
| XML body with an XML header | 400 empty_content |
| No Content-Type header | 400 empty_content |
Warning: The same text/plain request to the WooCommerce products endpoint returned 201 and created a product named “Product” with no data. A wrong header can fail silently. Check the response and not only the status.
How to Find What Sent the 415
To find what sent the HTTP status 415, repeat the failing request with curl and read the full response. The response body and headers show which layer answered. Run it from your own computer instead of the failing browser tab.
Use this order:
- Repeat the request: Run it with
curl -iso curl prints the status line and the headers. Add the same method, URL and body that failed. - Read the body: An HTML error page, such as Apache’s, means the web server answered. JSON with a
codefield means WordPress code answered, usually a plugin or theme. - Change only the header: Send the same body with
Content-Type: application/jsonand see if the status changes. If it works, the client was at fault.
curl -i -X POST https://example.com/wp-json/demo/v1/submit -d 'name=Ada'
Here is what the plugin-style 415 looked like on our test site:
HTTP/1.1 415 Unsupported Media Type
Content-Type: application/json; charset=UTF-8
{"code":"demo_unsupported_media_type","message":"Send this request as application\/json.","data":{"status":415}}

Cause 1: A Server Rule Rejects the Content-Type
A server rule that allows only JSON on the REST API returns a 415 for every form post and every file upload. Such a rule looks harmless because most API calls send JSON. The block editor sends uploads as multipart form data instead.
This rule is Apache syntax. Nginx and CDN dashboards use their own rule syntax for the same idea.
This .htaccess rule sends a 415 for any POST to the REST API that is not JSON:
RewriteEngine On
RewriteCond %{REQUEST_METHOD} POST
RewriteCond %{REQUEST_URI} ^/wp-json/
RewriteCond %{HTTP:Content-Type} !^application/json [NC]
RewriteRule ^ - [R=415,L]
With the rule in place, a JSON post worked and a form post returned the plain Apache page. It says the supplied request data is not in a format acceptable for processing by this resource.

The rule also broke image uploads. The block editor sends files as multipart form data. The upload failed and the editor showed a message that never mentions a 415.

To fix it, allow every type your site really sends. This version allows JSON, form data and multipart uploads, and the same upload then returned 201:
RewriteCond %{HTTP:Content-Type} !^(application/json|application/x-www-form-urlencoded|multipart/form-data) [NC]
A raw image upload that sends image/jpeg as its Content-Type was still blocked in our test. Add the types your tools send. For wider hardening ideas, see our WordPress security checklist.
Cause 2: Plugin or Theme Code Rejects the Request
Plugin or theme code can send a 415 on purpose, and its JSON reply names the sender. Look at the code value in the response, because it usually starts with the plugin’s prefix. Then check that plugin’s documentation for the Content-Type it expects.
We built a small test endpoint that accepts JSON only, the way many plugin APIs do. It is the source of the plugin-style reply shown earlier:
add_action(
'rest_api_init',
function () {
register_rest_route(
'demo/v1',
'/submit',
array(
'methods' => 'POST',
'permission_callback' => '__return_true',
'callback' => function ( WP_REST_Request $request ) {
if ( ! $request->is_json_content_type() ) {
return new WP_Error( 'demo_unsupported_media_type', 'Send this request as application/json.', array( 'status' => 415 ) );
}
return array( 'received' => $request->get_json_params() );
},
)
);
}
);
In our tests a form post, a plain text post and a request with no header all returned 415. A request with application/json; charset=UTF-8 returned 200.
To find the plugin on your own site, deactivate plugins one at a time and repeat the request after each one. Reactivate each plugin before you move to the next. If the 415 stops, read that plugin’s settings and API notes.
Tip: If you write the endpoint yourself, add a helpful hint. MDN’s example replies with an Accept-Post header that names the type the endpoint wants. Clients then know the fix at once.
Cause 3: Your Client Sends the Wrong Content-Type
A common source of 415 errors is the client, because many tools default to a Content-Type that a JSON endpoint refuses. The curl command sends form data whenever you use the -d option to attach a body. A JavaScript fetch call with a string body and no headers sends plain text.
Here are the three clients we tested against the JSON-only endpoint, each with the failing and working version:
- curl:
-d 'name=Ada'returned 415. Adding-H "Content-Type: application/json"with a JSON body returned 200 and so did the--jsonoption in curl 8.7.1. - JavaScript fetch: A call with
body: JSON.stringify(...)and no headers returned 415. Addingheaders: { 'Content-Type': 'application/json' }returned 200. - PHP wp_remote_post: A body array returned 415, and a JSON string with no header returned 415. The
headerskey set to JSON pluswp_json_encode()returned 200.
Here is the working PHP call:
$response = wp_remote_post( 'https://example.com/wp-json/demo/v1/submit', array( 'headers' => array( 'Content-Type' => 'application/json' ), 'body' => wp_json_encode( array( 'name' => 'Ada' ) ), ) );
If a tool lets you pick the body type, choose raw JSON and set the header yourself. Do not rely on a default. In our tests a JSON body sent with a text/plain header failed the same way as a missing header.
Is a File Type Error the Same as a 415?
No, a blocked file type is a different error with a different status. WordPress refuses unsafe uploads with its own message and its own status. We uploaded a small file named test.exe through the REST media endpoint, and it came back with a 500 status.
The reply said “Sorry, you are not allowed to upload this file type.” That message comes from WordPress’s own upload checks and has nothing to do with the Content-Type of the request.
To tell the two apart, read the status and the message together. A 415 names the media type, and the upload check names the file type. Keep unsafe types blocked, and do not add an .exe file type to your uploads to make it go away.
That is why old advice to add file types to .htaccess does not fix a real 415. If you would rather hand a stubborn server rule to a developer, see our WordPress maintenance services.
How to Confirm the Fix
To confirm the fix, repeat the exact request that failed and check the status line. A 200 or 201 means the format was accepted. Also test the neighbors, such as an image upload in the editor, because a fix to one rule can change another.
After we widened the Apache rule, the same image upload that failed before returned 201.

After a fix, check these three things:
- The original request: It should return 2xx and the same body you expect.
- Editor uploads: Upload one image in the block editor and confirm it appears.
- Other forms: Submit one contact or checkout form, because they may send a different Content-Type.
Our guide on the HTTP 302 status code covers another status you can read the same way.
Conclusion
The HTTP 415 error is a format refusal, and WordPress core never sends it. Read the response with curl first and then check server rules, plugins and your client in that order.
Most fixes are small. Send the Content-Type the endpoint asks for, or widen a server rule so it allows the types your site really uses. Then repeat the original request and test an image upload before you call it done.
Frequently Asked Questions (FAQs)
Q1. Is the 415 error my fault or the server’s?
It is a mismatch between the two. The client sent a format the server refuses. You fix it either in the client or by loosening the server rule. Start with the client, because that fix needs no server change.
Q2. Can a plugin cause a 415 error on my WordPress site?
Yes. A plugin can register an endpoint that accepts only JSON and answer anything else with a 415, as our test endpoint did. Its JSON reply carries a code value that usually names the plugin.
Q3. Why does curl return 415 when I use -d?
The -d option sends the body as form data, which a JSON-only endpoint refuses. Add -H "Content-Type: application/json" with a JSON body, or use the --json option in a newer curl version.
Q4. Can the Content-Encoding header cause a 415?
Yes. RFC 9110 says an origin server may answer 415 when a request body has a content coding it does not accept. A compressed request body that the server cannot unpack is one example.
Q5. How do I see a 415 error in my browser?
Open the browser developer tools and go to the Network tab. Repeat the action and look for the request with status 415. The Console tab may also show a line that says the server responded with a status of 415.
Q6. What should my own API return instead of a bare 415?
Return a clear message and, when you can, an Accept-Post header that names the type you accept. MDN shows that header in its examples. A hint saves clients a round of guessing.
