Request header field Access-Control-Allow-Headers is not allowed by itself in preflight response

ExpressCorsMeanjs

Express Problem Overview


I have come across CORS issues multiple times and can usually fix it but I want to really understand by seeing this from a MEAN stack paradigm.

Before I simply added middleware in my express server to catch these things, but it looks like there is some kind of pre-hook that is erroring out my requests.

>Request header field Access-Control-Allow-Headers is not allowed by Access-Control-Allow-Headers in preflight response

I assumed that I could do this:

app.use(function(req, res, next) {
  res.header("Access-Control-Allow-Headers","*")
})

or the equivalent but this doesn't seem to fix it. I also of course tried

app.use(function(req, res, next) {
  res.header("Access-Control-Allow-Headers","Access-Control-Allow-Headers")
})

Still no luck.

Express Solutions


Solution 1 - Express

When you start playing around with custom request headers you will get a CORS preflight. This is a request that uses the HTTP OPTIONS verb and includes several headers, one of which being Access-Control-Request-Headers listing the headers the client wants to include in the request.

You need to reply to that CORS preflight with the appropriate CORS headers to make this work. One of which is indeed Access-Control-Allow-Headers. That header needs to contain the same values the Access-Control-Request-Headers header contained (or more).

https://fetch.spec.whatwg.org/#http-cors-protocol explains this setup in more detail.

Solution 2 - Express

This is what you need to add to make it work.

response.setHeader("Access-Control-Allow-Origin", "*");
response.setHeader("Access-Control-Allow-Credentials", "true");
response.setHeader("Access-Control-Allow-Methods", "GET,HEAD,OPTIONS,POST,PUT");
response.setHeader("Access-Control-Allow-Headers", "Access-Control-Allow-Headers, Origin,Accept, X-Requested-With, Content-Type, Access-Control-Request-Method, Access-Control-Request-Headers");

The browser sends a preflight request (with method type OPTIONS) to check if the service hosted on the server is allowed to be accessed from the browser on a different domain. In response to the preflight request if you inject above headers the browser understands that it is ok to make further calls and i will get a valid response to my actual GET/POST call. you can constraint the domain to which access is granted by using Access-Control-Allow-Origin", "localhost, xvz.com" instead of * . ( * will grant access to all domains)

Solution 3 - Express

This problem solved with

 "Origin, X-Requested-With, Content-Type, Accept, Authorization"

Particular in my project (express.js/nodejs)

app.use(function(req, res, next) {
  res.header("Access-Control-Allow-Origin", "*");
  res.header("Access-Control-Allow-Methods", "GET,HEAD,OPTIONS,POST,PUT");
  res.header("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept, Authorization");
  next();
});

Update:

Every time error: Access-Control-Allow-Headers is not allowed by itself in preflight response error you can see what wrong with chrome developer tool:
enter image description here

above error is missing Content-Type so add string Content-Type to Access-Control-Allow-Headers

Solution 4 - Express

The accepted answer is ok, but I had difficulties to understand it. So here is a simple example to clarify it.

In my ajax request I had a standard Authorization header.

$$(document).on('ajaxStart', function(e){
var auth_token = localStorage.getItem(SB_TOKEN_MOBILE);
if( auth_token ) {
    var xhr = e.detail.xhr;

    xhr.setRequestHeader('**Authorization**', 'Bearer ' + auth_token);
}

This code produces the error in the question. What I had to do in my nodejs server was to add Authorization in allowed headers:

res.setHeader('Access-Control-Allow-Headers', 'X-Requested-With,content-type,**Authorization**');

Solution 5 - Express

Just to add that you can put those headers also to Webpack config file. I needed them as in my case as I was running webpack dev server.

devServer: {
    headers: {
      "Access-Control-Allow-Origin": "*",
      "Access-Control-Allow-Credentials": "true",
      "Access-Control-Allow-Methods": "GET,HEAD,OPTIONS,POST,PUT",
      "Access-Control-Allow-Headers": "Origin, X-Requested-With, Content-Type, Accept, Authorization"
    }
},

Solution 6 - Express

To add to the other answers. I had the same problem and this is the code i used in my express server to allow REST calls:

app.all('*', function(req, res, next) {
  res.header('Access-Control-Allow-Origin', 'URLs to trust of allow');
  res.header('Access-Control-Allow-Methods', 'GET, POST, OPTIONS, PUT, PATCH, DELETE');
  res.header('Access-Control-Allow-Headers', 'Content-Type');
  if ('OPTIONS' == req.method) {
  res.sendStatus(200);
  } else {
    next();
  }
});

What this code basically does is intercepts all the requests and adds the CORS headers, then continue with my normal routes. When there is a OPTIONS request it responds only with the CORS headers.

EDIT: I was using this fix for two separate nodejs express servers on the same machine. In the end I fixed the problem with a simple proxy server.

Solution 7 - Express

I just ran into this issue myself, in the context of ASP.NET make sure your Web.config looks like this:

  <system.webServer>
<modules>
  <remove name="FormsAuthentication" />
</modules>

<handlers>
  <remove name="ExtensionlessUrlHandler-Integrated-4.0" />
  <!--<remove name="OPTIONSVerbHandler"/>-->
  <remove name="TRACEVerbHandler" />
  <!--
  <add name="ExtensionlessUrlHandler-Integrated-4.0" path="*." verb="*" type="System.Web.Handlers.TransferRequestHandler" preCondition="integratedMode,runtimeVersionv4.0" />
  -->
</handlers>

<httpProtocol>
  <customHeaders>
    <add name="Access-Control-Allow-Origin" value="*" />
    <add name="Access-Control-Allow-Headers" value="Content-Type, Authorization" />
    <add name="Access-Control-Allow-Methods" value="GET, POST, PUT, DELETE, OPTIONS" />
  </customHeaders>
</httpProtocol>

Notice the Authorization value for the Access-Control-Allow-Headers key. I was missing the Authorization value, this config solves my issue.

Solution 8 - Express

In Chrome:

> Request header field X-Requested-With is not allowed by > Access-Control-Allow-Headers in preflight response.

For me, this error was triggered by a trailing space in the URL of this call.

jQuery.getJSON( url, function( response, status, xhr ) {
   ...
}

Solution 9 - Express

Very good i used this on a silex project

$app->after(function (Request $request, Response $response) {
        $response->headers->set('Access-Control-Allow-Origin', '*');
        $response->headers->set("Access-Control-Allow-Credentials", "true");
        $response->headers->set("Access-Control-Allow-Methods", "GET,HEAD,OPTIONS,POST,PUT");
        $response->headers->set("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept, Authorization");
    });

Solution 10 - Express

res.setHeader('Access-Control-Allow-Headers', '*');

Solution 11 - Express

I received the error the OP stated using Django, React, and the django-cors-headers lib. To fix it with this stack, do the following:

In settings.py add the below per the official documentation.

from corsheaders.defaults import default_headers

CORS_ALLOW_HEADERS = default_headers + (
'YOUR_HEADER_NAME',
)

Solution 12 - Express

After spending almost a day, I just found out that adding the below two codes solved my issue.

Add this in the Global.asax

protected void Application_BeginRequest()
{
  if (Request.HttpMethod == "OPTIONS")
  {
    Response.StatusCode = (int)System.Net.HttpStatusCode.OK;             
    Response.End();
  }
}

and in the web config add the below

<httpProtocol>
  <customHeaders>
    <add name="Access-Control-Allow-Origin" value="*" />        
    <add name="Access-Control-Allow-Methods" value="*" />
    <add name="Access-Control-Allow-Headers" value="Content-Type, Authorization" />
  </customHeaders>
</httpProtocol>

Solution 13 - Express

this problem occurs when we make custom header for request.This request that uses the HTTP OPTIONS and includes several headers.

The required header for this request is Access-Control-Request-Headers , which should be part of response header and should allow request from all the origin. Sometimes it needs Content-Type as well in header of response. So your response header should be like that -

response.header("Access-Control-Allow-Origin", "*"); // allow request from all origin
response.header("Access-Control-Allow-Methods", "GET,HEAD,OPTIONS,POST,PUT");
response.header("Access-Control-Allow-Headers", "Access-Control-Allow-Headers, Origin, X-Requested-With, Content-Type, Accept, Authorization");

Solution 14 - Express

If you are trying to add a custom header on the request headers, you have to let the server know that specific header is allowed to take place. The place to do that is in the class that filters the requests. In the example shown below, the custom header name is "type":

public class CorsFilter implements Filter {
    @Override
    public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException {
        HttpServletRequest request = (HttpServletRequest) req;
        HttpServletResponse response = (HttpServletResponse) res;
        response.setHeader("Access-Control-Allow-Origin",  request.getHeader("Origin"));
        response.setHeader("Access-Control-Allow-Credentials", "true");
        response.setHeader("Access-Control-Allow-Methods", "GET,PUT,POST,DELETE,PATCH,OPTIONS");
        response.setHeader("Access-Control-Max-Age", "3600");
        response.setHeader("Access-Control-Allow-Headers", "Content-Type, Accept, X-Requested-With, remember-me, Authorization, type ");
        response.setHeader("Access-Control-Expose-Headers","Authorization");
    }
}

Solution 15 - Express

add this headers into your ajax or js function

headers: {
			"Cache-Control": null,
			"X-Requested-With": null,
		}

Solution 16 - Express

I too faced the same problem in Angular 6. I solved the issue by using below code. Add the code in component.ts file.

import { HttpHeaders } from '@angular/common/http';

headers;

constructor() {
    this.headers = new HttpHeaders();
    this.headers.append('Access-Control-Allow-Headers', 'Authorization');
}

getData() {
    this.http.get(url,this.headers). subscribe (res => {
    // your code here...
})}

Solution 17 - Express

In Post API call we are sending data in request body. So if we will send data by adding any extra header to an API call. Then first OPTIONS API call will happen and then post call will happen. Therefore, you have to handle OPTION API call first.

You can handle the issue by writing a filter and inside that you have to check for option call API call and return a 200 OK status. Below is the sample code:

package com.web.filter;

import java.io.IOException;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.catalina.connector.Response;

public class CustomFilter implements Filter {
	public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain)
			throws IOException, ServletException {
		HttpServletResponse response = (HttpServletResponse) res;
		HttpServletRequest httpRequest = (HttpServletRequest) req;
		response.setHeader("Access-Control-Allow-Origin", "*");
		response.setHeader("Access-Control-Allow-Methods", "POST, GET, PUT, OPTIONS, DELETE");
		response.setHeader("Access-Control-Max-Age", "3600");
		response.setHeader("Access-Control-Allow-Headers", "x-requested-with, Content-Type");
		if (httpRequest.getMethod().equalsIgnoreCase("OPTIONS")) {
			response.setStatus(Response.SC_OK);
		}
		chain.doFilter(req, res);
	}

	public void init(FilterConfig filterConfig) {
		// TODO
	}

	public void destroy() {
		// Todo
	}

}

Solution 18 - Express

Message is clear that 'Authorization' is not allowed in API. Set Access-Control-Allow-Headers: "Content-Type, Authorization"

Solution 19 - Express

const express = require('express')
const cors = require('cors')
const app = express()

app.get('/with-cors', cors(), (req, res, next) => {
  res.json({ msg: 'WHOAH with CORS it works! 🔝 🎉' })
})

Adding cors in get function Is what worked for me

Solution 20 - Express

I faced similar issues when trying to connect to a Django backend: > Request header field authorisation is not allowed by Access-Control-Allow-Headers in preflight response

After hours of searching, I finally resolved it with the help of the following comment: > Also make sure you're spelling Authorization the american way not the Britsh way. That's half an hour of my life I won't get back. Thx USA! [sigh]

So a hint for someone else who is stuck: check that you are spelling the word "Authorization" correctly. If you set the Access-Control-Allow-Headers = ["Authorisation"], you are allowing the wrong header!

Solution 21 - Express

Yes, Use this i was also facing issue while integrating in angular application.

Write this.

app.use((req, res, next) => {
  res.setHeader("Access-Control-Allow-Origin", "*");
  res.setHeader(
    "Access-Control-Allow-Headers",
    "Origin,X-Requested-With, Content-Type, Accept, Authorization"
  );
  res.setHeader("Access-Control-Allow-Methods", "GET,POST,PATCH,PUT,DELETE,OPTIONS");
  next();
});

Follow me Thanks

Solution 22 - Express

That same issue i was facing.

I did a simple change.

  <modulename>.config(function($httpProvider){
    delete $httpProvider.defaults.headers.common['X-Requested-With'];
});

Solution 23 - Express

Make sure all headers you require from client is passed to to Access-Control-Allow-Headers, else you'll keep running into CORS issues. In this case, that would be 'x-api-key' else you keep running into cors issues

const options = {
  method: "GET",
  headers: new Headers({
    "X-API-Key": "ds67GHjkshjh00ZZhhsskhjgasHJHJHJ&87",
  }),
};

response.setHeader(
    "Access-Control-Allow-Headers", 
    "X-CSRF-Token, X-Requested-With, Accept, Accept-Version, Content-Length, Content-MD5, Content-Type, Date, X-Api-Version, x-api-key");

Solution 24 - Express

I just added response.headers; after

http.Response response = await http.get(
        Uri.parse(
          api + "api/users/all",
        ),
      );

The CORS setup in the backend(Django) as official documentation, Djnago-cors-headers

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionmibbitView Question on Stackoverflow
Solution 1 - ExpressAnneView Answer on Stackoverflow
Solution 2 - Expressmanish aroraView Answer on Stackoverflow
Solution 3 - ExpressnguyênView Answer on Stackoverflow
Solution 4 - Expressuser732456View Answer on Stackoverflow
Solution 5 - ExpressJanneView Answer on Stackoverflow
Solution 6 - ExpressLuke KroonView Answer on Stackoverflow
Solution 7 - ExpressJosh SieglView Answer on Stackoverflow
Solution 8 - Expressuser3248255View Answer on Stackoverflow
Solution 9 - ExpressAl KativoView Answer on Stackoverflow
Solution 10 - ExpressKanomdookView Answer on Stackoverflow
Solution 11 - ExpressEricView Answer on Stackoverflow
Solution 12 - ExpressBiruk BelihuView Answer on Stackoverflow
Solution 13 - ExpressSai prateekView Answer on Stackoverflow
Solution 14 - ExpressKristina MojanovskaView Answer on Stackoverflow
Solution 15 - Expresskrupali desaiView Answer on Stackoverflow
Solution 16 - ExpressKarthikeyan VellingiriView Answer on Stackoverflow
Solution 17 - Expressuser11815301View Answer on Stackoverflow
Solution 18 - ExpressRajesh YadavView Answer on Stackoverflow
Solution 19 - ExpressAyman OUKACHAView Answer on Stackoverflow
Solution 20 - ExpressYongView Answer on Stackoverflow
Solution 21 - ExpressVaman PatelView Answer on Stackoverflow
Solution 22 - ExpressShashikant PanditView Answer on Stackoverflow
Solution 23 - ExpressChukwuEmekaView Answer on Stackoverflow
Solution 24 - ExpressMajor_Garlic0057View Answer on Stackoverflow