-1

I am builing a small api in the background of a server out of php. I am using a subdomain of api.website.com. Just for debugging I have this on top of the index of my index.php in the subdomain

header("Access-Control-Allow-Origin: *");
header('Access-Control-Allow-Credentials: true');
header("Access-Control-Allow-Methods: GET, POST, OPTIONS, DELETE");

and for my javascript code on the main website is.

$.ajax({
  xhrFields: {
    withCredentials: true
  },
  headers: {
    "X-My-Custom-Header": "some value"
  },
  url: 'https://api.website.com/',
  type: 'GET',
  processData: false,
  contentType: "application/json",
  dataType: 'json',
  data: '{}',
  success: function(r) {
    console.log(r);
  },
  error: function(r) {}
});

All this worked fine till literally yesterday, today when I started working on it I got this.

Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'https://website.com' is therefore not allowed access

I find it weird that it all worked yesterday and now I don't know what is going on.

Ram
  • 143,282
  • 16
  • 168
  • 197
  • 3
    The issue is with the PHP, not the JS. If you're receiving that error, then the CORS headers are not being applied correctly, or are in the wrong part of your code. You need to debug why that is. – Rory McCrossan Oct 03 '18 at 15:01
  • what changed since yesterday? – Daniel A. White Oct 03 '18 at 15:11
  • I was messing with another code to make ajax load other html pages as modals plugins, dynamically, but that should not have done anything as it was not subdomain. – Mark Garcia Oct 03 '18 at 18:28
  • If I were to start with something simple, like lets say I make a new php called bob.php in the subdomain with the header using a the calling domain and ref it using ajax I seam to still get the same error – Mark Garcia Oct 03 '18 at 19:10
  • oh yea I was messing with ajax beforeSend setting setRequestHeader("Cache-Control", "no-cache"); and setRequestHeader("Pragma", "no-cache"); – Mark Garcia Oct 03 '18 at 20:07

3 Answers3

0

Some times when pages are being serve from server's cache the Access-Control-Allow-Origin header is missing, make sure the page is not bing served from cache or make sure the cache stting includes this header.

kleinohad
  • 5,800
  • 2
  • 26
  • 34
0

You cannot use withCredentials and a wild card origin. Otherwise that is a securtity risk. See: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Access-Control-Allow-Origin#Directives

Daniel A. White
  • 187,200
  • 47
  • 362
  • 445
  • Well to be honest I do have a function so I dont have to use the wild card. called cors that dynamically makes it header("Access-Control-Allow-Origin: https://www.website.com"); . I added the wild card when I started having problems for debugging purposes – Mark Garcia Oct 03 '18 at 18:34
0

Ok, I dont know how I solved the problem but I am guessing like the comment above said the header was being cache. I am restarting the ssl with cloudflare, because it loves to cache everything. Now in order to make it work I have to remove these two things from the javascript.

headers: {"X-My-Custom-Header": "some value"},

and

contentType: "application/json",

from all my ajax calls.

as I was mentioning the wild card, that I was using for only testing purposes, just to see if it was my dynamic php code that the issue. It was not, thankfully.

function cors() {

$domain = ltrim($_SERVER['HTTP_HOST'], "api.");
$origin = $_SERVER['HTTP_ORIGIN'];


if (preg_match("/^http[s]?[:]\/\/(w{3})?[.a-zA-Z ]*".$domain."$/i", $origin)) {
    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, DELETE");         

    if (isset($_SERVER['HTTP_ACCESS_CONTROL_REQUEST_HEADERS']))
        header("Access-Control-Allow-Headers: {$_SERVER['HTTP_ACCESS_CONTROL_REQUEST_HEADERS']}");
    exit(0);
}
header('Content-Type: application/json');
header('Accept: application/json');
}

this is called at the beginning with cors(); not to cause any header and continent cross contamination.

Thank you for the advice, I needed ideas as to brainstorm on what could be the problem.

Update: I thought that cloudflare was messing with the headers https://support.cloudflare.com/hc/en-us/articles/200308847-Does-Cloudflare-support-Cross-origin-resource-sharing-CORS- But looks like it might not be them even though purging the cache they had helped. Then I got stuck on another problem, the POST and GET was working just fine, but not things like DELETE and OPTIONS. So after dissecting and research I find the header() in PHP was not working. It turns out to be PHP headers not set with litespeed (but work with apache) because of litespeed.

I have to have the headers on .htaccess as a temporary fix. I mean PHP headers work but for some odd reason what I am seeing in the headers for postman program is not consistent in AJAX.