Trying to make a JWT authorized json rest api request from my angular 8 web application, when it gives the above error. All sensible CORS configuration steps have been followed, and then relaxing of the rules to the point where it still doesn't work and I have turned to you guys for help.
So in terms of CORS config, on the php side of things I started with :
header("Access-Control-Allow-Origin: http://localhost:4200");
header("Content-Type: application/json;charset=utf-8");
header("Access-Control-Allow-Methods: OPTIONS, GET, PUT, POST, DELETE");
header("Access-Control-Max-Age: 3600");
header("Access-Control-Allow-Headers: Content-Type, Access-Control-Allow-Headers, Authorization, X-Requested-With");
I slackened things off a bit to :
header("Access-Control-Allow-Origin: *");
header("Content-Type: *");
header("Access-Control-Allow-Methods: *");
header("Access-Control-Max-Age: 3600");
header("Access-Control-Allow-Headers: *");
But then I read in the CORS docs that Access-Control-Allow-Headers does not allow *, so I reverted that line.
Currently I have :
header("Access-Control-Allow-Origin: *");
header("Content-Type: application/json, text/plain, */*");
header("Access-Control-Allow-Methods: OPTIONS, GET, PUT, POST, DELETE");
header("Access-Control-Max-Age: 3600");
header("Access-Control-Allow-Headers: Content-Type, X-Requested-With, Authorization");
The error I get is :
Access to XMLHttpRequest at
'http://localhost/api/controllers/asset.php/' from origin
'http://localhost:4200' has been blocked by CORS policy: Response to
preflight request doesn't pass access control check: It does not have
HTTP ok status.
This is the header information for the request from the network tab in debug tools (Chrome).
Provisional headers are shown Accept: application/json, text/plain,
/ Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpc3MiOm51bGwsImF1ZCI6IlRIRV9BVURJRU5DRSIsImlhdCI6MTU2NjYyOTIxNywibmJmIjoxNTY2NjI5MjE5LCJleH....redacted
This is running on apache with php 7.2
I would expect the new relaxed CORS settings to work, but still I get this error.
How can I tweak the CORS settings to satisfy the pre-flight request?
I created a framework called Willow. This is the code I use that gets past the CORS insanity.
$requestMethod = $_SERVER['REQUEST_METHOD'];
// Is this a pre-flight request (the request method is OPTIONS)? Then start output buffering.
if ($requestMethod === 'OPTIONS') {
ob_start();
}
// Allow for all origins and credentials. Also allow GET, POST, PATCH, and OPTIONS request verbs
header('Access-Control-Allow-Origin: *');
header('Access-Control-Allow-Credentials: true');
header('Access-Control-Allow-Headers: Access-Control-Allow-Headers, Origin,Accept, X-Requested-With, Content-Type, Access-Control-Request-Method, Access-Control-Request-Headers');
header('Access-Control-Allow-Methods: GET, POST, PATCH, OPTIONS, DELETE');
// If this is a pre-flight request (the request method is OPTIONS)? Then flush the output buffer and exit.
if ($requestMethod === 'OPTIONS') {
ob_end_flush();
exit();
}
HTH
I am getting an error on mobile, when I use Chrome to try out my new responsive web app. I have done everything from add php headers in several different ways, to passing headers in my ajax request. On the web, I used CORS toggle, a Chrome extension that allows you to toggle on and off CORS, which fixes the problem on web. Yet I cannot seem to find a solution like this for mobile. Anyway I can bypass CORS on mobile Chrome??
I have tried ALL of these ways, and nothing seems to work..
php option 1:
<?php
header('Access-Control-Allow-Origin: *');
header('Access-Control-Allow-Headers: Cache-Control, Pragma, Origin, Authorization, Content-Type, X-Requested-With');
header('Access-Control-Allow-Methods: GET, PUT, POST');
?>
php option 2:
<?php
// Allow from any origin
if (isset($_SERVER['HTTP_ORIGIN'])) {
header("Access-Control-Allow-Origin: *");
header("Access-Control-Allow-Credentials: true ");
header("Access-Control-Allow-Methods: OPTIONS, GET, POST");
header("Access-Control-Allow-Headers: Content-Type, Depth, User-Agent, X-File-Size, X-Requested-With, If-Modified-Since, X-File-Name, Cache-Control");
}
// Access-Control headers are received during OPTIONS requests
if ($_SERVER['REQUEST_METHOD'] == 'OPTIONS') {
if (isset($_SERVER['HTTP_ACCESS_CONTROL_REQUEST_METHOD']))
header("Access-Control-Allow-Methods: GET, POST, OPTIONS");
if (isset($_SERVER['HTTP_ACCESS_CONTROL_REQUEST_HEADERS']))
header("Access-Control-Allow-Headers: {$_SERVER['HTTP_ACCESS_CONTROL_REQUEST_HEADERS']}");
exit(0);
}
echo "You have CORS!";
?>
jQuery AJAX:
$.ajax({
url: '<MY API ENDPOINT>',
method: 'POST',
headers: {
'Access-Control-Allow-Origin': '*',
'Access-Control-Allow-Headers': "Cache-Control, Pragma, Origin, Authorization, Content-Type, X-Requested-With",
'Access-Control-Allow-Methods': "GET, PUT, POST",
'Authorization':
'Bearer <MY TOKEN>',
'Cache-Control': 'no-cache'
},
data: formData,
processData: false,
contentType: false
}).done(function(res) {
Remove the access control headers from your ajax request. Access control headers are automatically set by the browser as defined in the W3C CORS spec.
Whatever headers you include in your ajax request, you need to allow in the server response. In your case it's Authorization and Cache-Control. Add them to Access-Control-Allow-Headers.
Use option 2 of your php code. It includes a response for the cors preflight OPTIONS request. Option 1 will not work for that reason.
how can I allow laravel No 'Access-Control-Allow-Origin' header is present on the requested ? Because when I try to $http.get() a certain url using angular.js I always get error about it.
Oh, got it. I just need to add before filter on my application.
filters.php
App::before(function($request)
{
header('Access-Control-Allow-Origin: *');
header('Access-Control-Allow-Methods: GET, POST, OPTIONS');
header('Access-Control-Allow-Headers: Origin, Content-Type, Accept, Authorization, X-Requested-With');
header('Access-Control-Allow-Credentials: true');
});
have a project I'm working on and I'm trying to pull from a Google API. (It does not have a JSONP option).
Right now, I'm getting a "No 'Access-Control-Allow-Origin'" error. I've added the following php:
<?php
header('Access-Control-Allow-Origin: *');
header("Access-Control-Allow-Credentials: true");
header('Access-Control-Allow-Methods: GET, PUT, POST, DELETE, OPTIONS');
header('Access-Control-Allow-Headers: Content-Type, Content-Range, Content-Disposition, Content-Description');
?>
And here is my Ajax call:
$.getJSON(path,function(data) {
console.log(typeof(data));
});
Any thoughts?
I have a simple PHP script that I am attempting a cross-domain CORS request:
<?php
header("Access-Control-Allow-Origin: *");
header("Access-Control-Allow-Headers: *");
...
Yet I still get the error:
Request header field X-Requested-With is not allowed by Access-Control-Allow-Headers
Anything I'm missing?
Handling CORS requests properly is a tad more involved. Here is a function that will respond more fully (and properly).
/**
* An example CORS-compliant method. It will allow any GET, POST, or OPTIONS requests from any
* origin.
*
* In a production environment, you probably want to be more restrictive, but this gives you
* the general idea of what is involved. For the nitty-gritty low-down, read:
*
* - https://developer.mozilla.org/en/HTTP_access_control
* - https://fetch.spec.whatwg.org/#http-cors-protocol
*
*/
function cors() {
// Allow from any origin
if (isset($_SERVER['HTTP_ORIGIN'])) {
// Decide if the origin in $_SERVER['HTTP_ORIGIN'] is one
// you want to allow, and if so:
header("Access-Control-Allow-Origin: {$_SERVER['HTTP_ORIGIN']}");
header('Access-Control-Allow-Credentials: true');
header('Access-Control-Max-Age: 86400'); // cache for 1 day
}
// Access-Control headers are received during OPTIONS requests
if ($_SERVER['REQUEST_METHOD'] == 'OPTIONS') {
if (isset($_SERVER['HTTP_ACCESS_CONTROL_REQUEST_METHOD']))
// may also be using PUT, PATCH, HEAD etc
header("Access-Control-Allow-Methods: GET, POST, OPTIONS");
if (isset($_SERVER['HTTP_ACCESS_CONTROL_REQUEST_HEADERS']))
header("Access-Control-Allow-Headers: {$_SERVER['HTTP_ACCESS_CONTROL_REQUEST_HEADERS']}");
exit(0);
}
echo "You have CORS!";
}
Security Notes
Check the HTTP_ORIGIN header against a list of approved origins.
If the origin isn't approved, then you should deny the request.
Please read the spec.
TL;DR
When a browser wants to execute a cross-site request it first confirms that this is okay with a "pre-flight" request to the URL. By allowing CORS you are telling the browser that responses from this URL can be shared with other domains.
CORS does not protect your server. CORS attempts to protect your users by telling browsers what the restrictions should be on sharing responses with other domains. Normally this kind of sharing is utterly forbidden, so CORS is a way to poke a hole in the browser's normal security policy. These holes should be as small as possible, so always check the HTTP_ORIGIN against some kind of internal list.
There are some dangers here, especially if the data the URL serves up is normally protected. You are effectively allowing browser content that originated on some other server to read (and possibly manipulate) data on your server.
If you are going to use CORS, please read the protocol carefully (it is quite small) and try to understand what you're doing. A reference URL is given in the code sample for that purpose.
Header security
It has been observed that the HTTP_ORIGIN header is insecure, and that is true. In fact, all HTTP headers are insecure to varying meanings of the term. Unless a header includes a verifiable signature/hmac, or the whole conversation is authenticated via TLS, headers are just "something the browser has told me".
In this case, the browser is saying "an object from domain X wants to get a response from this URL. Is that okay?" The point of CORS is to be able to answer, "yes I'll allow that".
I got the same error, and fixed it with the following PHP in my back-end script:
header('Access-Control-Allow-Origin: *');
header('Access-Control-Allow-Methods: GET, POST');
header("Access-Control-Allow-Headers: X-Requested-With");
Access-Control-Allow-Headers does not allow * as accepted value, see the Mozilla Documentation here.
Instead of the asterisk, you should send the accepted headers (first X-Requested-With as the error says).
Update:
* is now accepted is Access-Control-Allow-Headers.
According to MDN Web Docs 2021:
The value * only counts as a special wildcard value for requests without credentials (requests without HTTP cookies or HTTP authentication information). In requests with credentials, it is treated as the literal header name * without special semantics. Note that the Authorization header can't be wildcarded and always needs to be listed explicitly.
Many description internet-wide don't mention that specifying Access-Control-Allow-Origin is not enough. Here is a complete example that works for me:
<?php
if ($_SERVER['REQUEST_METHOD'] === 'OPTIONS') {
header('Access-Control-Allow-Origin: *');
header('Access-Control-Allow-Methods: POST, GET, DELETE, PUT, PATCH, OPTIONS');
header('Access-Control-Allow-Headers: token, Content-Type');
header('Access-Control-Max-Age: 1728000');
header('Content-Length: 0');
header('Content-Type: text/plain');
die();
}
header('Access-Control-Allow-Origin: *');
header('Content-Type: application/json');
$ret = [
'result' => 'OK',
];
print json_encode($ret);
I've simply managed to get dropzone and other plugin to work with this fix (angularjs + php backend)
header('Access-Control-Allow-Origin: *');
header("Access-Control-Allow-Credentials: true");
header('Access-Control-Allow-Methods: GET, PUT, POST, DELETE, OPTIONS');
header('Access-Control-Max-Age: 1000');
header('Access-Control-Allow-Headers: Origin, Content-Type, X-Auth-Token , Authorization');
add this in your upload.php or where you would send your request (for example if you have upload.html and you need to attach the files to upload.php, then copy and paste these 4 lines).
Also if you're using CORS plugins/addons in chrome/mozilla be sure to toggle them more than one time,in order for CORS to be enabled
If you want to create a CORS service from PHP, you can use this code as the first step in your file that handles the requests:
// Allow from any origin
if(isset($_SERVER["HTTP_ORIGIN"]))
{
// You can decide if the origin in $_SERVER['HTTP_ORIGIN'] is something you want to allow, or as we do here, just allow all
header("Access-Control-Allow-Origin: {$_SERVER['HTTP_ORIGIN']}");
}
else
{
//No HTTP_ORIGIN set, so we allow any. You can disallow if needed here
header("Access-Control-Allow-Origin: *");
}
header("Access-Control-Allow-Credentials: true");
header("Access-Control-Max-Age: 600"); // cache for 10 minutes
if($_SERVER["REQUEST_METHOD"] == "OPTIONS")
{
if (isset($_SERVER["HTTP_ACCESS_CONTROL_REQUEST_METHOD"]))
header("Access-Control-Allow-Methods: POST, GET, OPTIONS, DELETE, PUT"); //Make sure you remove those you do not want to support
if (isset($_SERVER["HTTP_ACCESS_CONTROL_REQUEST_HEADERS"]))
header("Access-Control-Allow-Headers: {$_SERVER['HTTP_ACCESS_CONTROL_REQUEST_HEADERS']}");
//Just exit with 200 OK with the above headers for OPTIONS method
exit(0);
}
//From here, handle the request as it is ok
CORS can become a headache, if we do not correctly understand its functioning. I use them in PHP and they work without problems. reference here
header("Access-Control-Allow-Origin: *");
header("Access-Control-Allow-Credentials: true");
header("Access-Control-Max-Age: 1000");
header("Access-Control-Allow-Headers: X-Requested-With, Content-Type, Origin, Cache-Control, Pragma, Authorization, Accept, Accept-Encoding");
header("Access-Control-Allow-Methods: PUT, POST, GET, OPTIONS, DELETE");
This much code works down for me when using angular 4 as the client side and PHP as the server side.
header("Access-Control-Allow-Origin: *");
this should work
header("Access-Control-Allow-Origin: *");
header("Access-Control-Allow-Headers: X-Requested-With, Content-Type, Origin, Cache-Control, Pragma, Authorization, Accept, Accept-Encoding");
I used these 5 headers and after that solved the cors error(backend: PHP, Frontend: VUE JS)
header('Access-Control-Allow-Origin: *');
header('Access-Control-Allow-Methods: GET, PUT, POST, DELETE, OPTIONS, post, get');
header("Access-Control-Max-Age", "3600");
header('Access-Control-Allow-Headers: Origin, Content-Type, X-Auth-Token');
header("Access-Control-Allow-Credentials", "true");
add this code in .htaccess
add custom authentication key's in header like app_key,auth_key..etc
Header set Access-Control-Allow-Origin "*"
Header set Access-Control-Allow-Headers: "customKey1,customKey2, headers, Origin, X-Requested-With, Content-Type, Accept, Authorization"