Node-Express-CORS issue - node.js

Ionic 2
I am using login provider but when i set the access control to
res.header('Access-Control-Allow-Origin', '*');
It is not working
But it works properly when i use
res.header('Access-Control-Allow-Origin', 'http://localhost:8100');
It is working
but now i want to deploy my app up on phone device i need to set it to wild card res.header('Access-Control-Allow-Origin', '*');. since my app on phone not working on http://localhost:8100 anymore
Anyone can help me solve this problem ?

If you are making a preflighted request then the wildcard is forbidden in the Access-Control-Allow-Origin header.
You can read the Origin request header in order to find out the origin. Then you can test it against a list of allowed origins (you could also assume that any origin is OK, but for a preflighted request there is a good chance that complete public access would be a security risk). Finally you can copy it into the Access-Control-Allow-Origin response header.

How is your HTTP request from your app looks like?
Look for "Types of CORS requests" in this article.
If your HTTP request is a simple one, i.e.
Method is HEAD, GET, or POST
Only have these headers
Accept
Accept-Language
Content-Language
Last-Event-ID
Content-Type of application/x-www-url-encoded, multipart/form-data, or text/plain
If your HTTP request is a simple one, preflight is not needed. And Access-Control-Allow-Origin with * is accepted by the mobile app.
Otherwise, a preflight request will be made (i.e. OPTION request) and Access-Control-Allow-Origin of * will be ignored. It must be fully specified like http://localhost:8100.

Related

How does Access-Control-Expose-Headers work?

I understand it determines the headers the client can access from the server response, however, I am confused on exactly when this is applied. Does it determine the headers for every cross-origin request that is allowed by the Access-Control-Allow-Origin header?
To test this I setup a test site in express and put the following code in it:
app.get('/',(req,res)=>{
res.set('Access-Control-Allow-Origin','https://www.google.com') // to be able to make a cross-origin request
res.set('foo', 'bar') //custom header that should get filtered because i havent set the access-control-expose-headers header
res.send('Hello world')
})
Based on my understanding of this, because I haven't set any special Access-Control-Expose-Headers header in the response, the client should only be able to access CORS-safelisted response headers and therefore should not be able to see my foo header.
But when I'm at https://www.google.com (Which I allowed for CORS with the Access-Control-Allow-Origin header) and send a GET request to my test site I see the foo header in the response just fine. Why is this? Could someone explain how this works or at least point me in the right direction? Thanks in advance.
I figured it out. The reason I was receiving my custom header was that I was reading the response headers in the Network tab of Chrome Dev Tools. When I run this script:
fetch('http://127.0.0.1:3000/')
.then(r => {console.log(response.headers.get('foo'))})
It prints null. So the header is not actually accessible to the fetch request, only to the Dev Tools.

Cross-origin resource sharing error: PreflightInvalidstatus in Azure Application API

I have backend Springboot API service which is running behind the Azure Application Gateway. The APIs are getting used in a Single page application. Spring boot APIs are well configured for CORS and working prefectly fine in ideal scenarios.
But getting CORS errror when Beackendend service is not responsive/down. I setup these values in Application gateway to deal with Preflight calls in case java service is not reachable.
Access-Control-Allow-Origin: {http_req_Origin}
Access-Control-Allow-Credentials: true
Access-Control-Allow-Methods: POST, GET, OPTIONS, DELETE, PUT
Access-Control-Allow-Headers: x-requested-with, authorization, content-type, unique-one-time-token
Access-Control-Max-Age: 1800
After doing these rewrite rules , there is still CORS error Cross-origin resource sharing error: PreflightInvalidstatus
See if any of the below can be workaround in your case
Make sure the request URL in your code isn’t missing a trailing
slash.
for example, you may need to add a trailing slash in your
code— e.g., http://localhost/api/auth/login/  or remove the slash
if present http://localhost/api/auth/login and try.
This may even happen sometimes when you try calling an https service as http, for example when you perform a request on :'http:// localhost/api/auth/login ' which might have to be be 'https:// localhost/api/auth/login
Or
You need to reply to that CORS preflight with the appropriate CORS
headers to make this work.
A CORS-preflight request is a CORS request that checks to see if
the CORS protocol is understood. It uses OPTIONS
as method and includes these  headers .You might need to reply to
that CORS preflight with the appropriate CORS headers.
References:
Fetch Standard (whatwg.org)
CORS#preflighted_requests
CORS

Juptyer Kernel Gateway CROS

I have a Jupyter KernelGatewayApp running on a VM instance in Google cloud. I defined an API which responds to a GET statement.
If I combine the ip address of the VM instance with the port of the Kernel Gateway and the GET statement with the right parameters, I get the desired result.
However, I would like to call the API using a javascript button on another site. This doesn't work as the browser is first sending an OPTIONS statement which I don't manage to respond to correctly.
Concretely, I have the following:
Running Jupyter Kernel Gateway on port 8888 : 33.44.567.789:8888
Working API : 33.44.567.789:8888/api?fname=john&lname=doe
Other website where a javascript button calls the above API : johndoe.me
Returns following error on requestor (browser) side:
XMLHttpRequest cannot load
http://33.44.567.789:8888/api?fname=john&lname=doe. Request header
field Content-type is not allowed by Access-Control-Allow-Headers in
preflight response.
Generates following message on server:
INFO:tornado.access:200 OPTIONS /api?fname=john&lname=doe
(xx.xxx.xx.xxx) 1.2 ms
Because of the thing I read here I added all different sort of parameters when launching the Jupyter Kernel Gateway:
jupyter kernelgateway --KernelGatewayApp.api='kernel_gateway.notebook_http' --KernelGatewayApp.seed_uri='/home/dummy_gmail_com/code/test_api.ipynb' --KernelGatewayApp.allow_origin='http://johndoe.me' --KernelGatewayApp.allow_methods='GET,OPTIONS,POST' --KernelGatewayApp.allow_credentials='true' --KernelGateway.allow_headers='Origin, X-Requested-With, Content-Type, Accept, content-type' --KernelGatewayApp.expose_headers='Origin, X-Requested-With, Content-Type,Accept' --KernelGatewayApp.answer_yes=True
The issue seems to be that the browser is issuing an OPTIONS instead of a GET but I'm not really sure. Is this linked to the cross origin fact ? Is there a way to handle this correctly or a way around this ?
Having had the same problem I found that CORS requests served by Jupyter Kernel Gateway worked with the following parameters:
jupyter kernelgateway --KernelGatewayApp.api='kernel_gateway.notebook_http' --KernelGatewayApp.seed_uri='/home/dummy_gmail_com/code/test_api.ipynb' --KernelGatewayApp.allow_origin='http://johndoe.me'
(Using OP's domains etc. for consistency.)
The parameter KernelGatewayApp.allow_origin='*' also worked/Solved the problem.
However I did go wrong prompted by the initial browser console error message which ran:
Access to fetch at 'http://localhost:8889/convert?degrees=164' from origin
'http://localhost:3000' has been blocked by CORS policy:
No 'Access-Control-Allow-Origin' header is present on the requested resource.
If an opaque response serves your needs, set the request's mode to 'no-cors' to
fetch the resource with CORS disabled.
This prompted me to set the request mode to 'no-cors'. The effect of this is to prevent an Origin header being sent with the request. Under these circumstances no amount of tinkering with the kernel gateway parameters resulted in a successful response.
Also when specifying the Allow Origin header as anything other than '*' it needs to be an exact string match to the 'Origin' header. For example:
Allow-Origin: http://127.0.0.1 does not match Origin: http://localhost
Allow-Origin: localhost does not match Origin: http://localhost
Allow-Origin: http://localhost/ does not match Origin: http://localhost
Allow-Origin: http://localhost does not match Origin: http://localhost:3000
etc.
as you can see with service /siteupdate, you can allow origin on a per service basis

Interacting with expressjs on another server throwing Access-Control-Allow-Headers errors

I am trying to implement Spika web chat ([http://spikaapp.com/][1]) on my Amazon server. I have my website code on one server instance and Spika chat server on another server instance. Spika chat server is up and running. Now when I try to interact with the server on my website I get this error :
XMLHttpRequest cannot load http://example.com:8000/spika/v1/user/list/Boom?_=1468157726669.
Request header field access-token is not allowed by Access-Control-Allow-Headers
in preflight response.
Earlier I had the CORS error I resolved it referring this : http://enable-cors.org/server_expressjs.html
Now I can login but my client but soon after login I get the above error. My current expressjs API handler code for enabling CORS :
app.use(function(req, res, next) {
res.setHeader("Access-Control-Allow-Origin", "*");
res.setHeader("Access-Control-Allow-Credentials", "true");
res.setHeader("Access-Control-Allow-Methods", "GET,HEAD,OPTIONS,POST,PUT");
res.setHeader("Access-Control-Allow-Headers", "Access-Control-Allow-Headers, Origin,Accept, X-Requested-With, Content-Type, Access-Control-Request-Method, Access-Control-Request-Headers");
next();
});
Thanks in advance for the help.
The server (that the POST request is sent to) needs to include the Access-Control-Allow-Headers header (etc) in its response. Putting them in your request from the client has no effect.
This is because it is up to the server to specify that it accepts cross-origin requests (and that it permits the Content-Type request header, and so on) – the client cannot decide for itself that a given server should allow CORS.
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.
I solved it using https://www.npmjs.com/package/cors. Thanks for all your help guys :)

origin key in http header is always null - CORS related

I am developing an ajax form update on localhost in express.js for learning express.js
The origin in header is alway set to be null by browser for CORS request (tried: firefox, chrome and safari)
Question:
1. "Origin: null" in request header is not the problem of express.js. Is this correct?
Why they(is it the browsers?) set the Origin to null? I think it should look like this one: "localhost:3000/myproject/test/form.html"
Should I use jquery ($.ajax() or $.ajaxSetup()) to set the origin, before calling ajax on localhost?
How to make the origin in header reflect the real situation?
Here is the screenshot: [...the screenshot is gone now...]
I read the following article about the CORS. The origin in header is null, which is not explained. Please help.
http://www.html5rocks.com/en/tutorials/cors/
"The first thing to note is that a valid CORS request always contains an Origin header. This Origin header is added by the browser, and can not be controlled by the user."
How to allow CORS?
The Origin header is null because you are making the CORS request from a local file (I bet the url starts with file://). In order to get a "normal" origin, you need to host the client file on a web server and access that file using http or https.
Also note that the Origin value is set by the browser and can not be overridden by client JavaScript code.
(P.S. I wrote that HTML Rocks article, I'll make a note to add a section about null Origin)

Resources