I have a react js app which does a simple http get. It does not use webpack and use package.json
var request = require('request');
var options = {
url: 'http://localhost:8181/api/v1/status',
headers: {
'Access-Control-Allow-Origin':'*'
}
}
function callback(error, response, body) {
if (!error && response.statusCode == 200) {
var info = JSON.parse(body);
console.log(info.stargazers_count + " Stars");
console.log(info.forks_count + " Forks");
}
}
request(options, callback);
This code is getting failed and I am getting the following error
localhost/:1 Failed to load http://localhost:8181/api/v1/status: Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://localhost:3000' is therefore not allowed access. The response had HTTP status code 405. If an opaque response serves your needs, set the request's mode to 'no-cors' to fetch the resource with CORS disabled.
The server which I am trying to access is running python and I am already appending necessary header to make the request.
I am quite new to reactjs
How to fix this issue?
Let's breakdown the error message. The first part:
Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource.
Means your Python server did not set an Access-Control-Allow-Origin header. You should make sure your python server sets this header in the response. If that didn't work, continue:
The response had HTTP status code 405.
HTTP Status Code 405 means method not allowed. Your python server may also need to set the header: Access-Control-Allow-Methods: <method>, <method>. So in include each one you want to allow, such as GET, POST, OPTIONS.
https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Access-Control-Allow-Methods
Related
This question already has answers here:
Handle response - SyntaxError: Unexpected end of input when using mode: 'no-cors'
(5 answers)
Closed 4 years ago.
When trying to resolve a fetch promise with JS is set the mode to 'no-cors' based on this answer. However setting the mode to 'cors' results in having:
Access to fetch at
'{endpoint}'
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.
So I wrote this in my function:
search() {
return fetch(`${baselink}${summonerEndpoint}${summoner}${apikey}`, {mode: 'no-cors'}).then(response => {
return response.json()
}).then(jsonResponse => {
console.log(jsonResponse);
if (!jsonResponse.info) {
return [];
}
return jsonResponse.info.items.map(info => ({
id: info.id,
accountId: info.accountId,
name: info.name,
profileIconId: info.profileIconId,
revisionDate: info.revisionDate,
summonerLevel: info.summonerLevel
}));
});
}
This results in following error Uncaught (in promise) SyntaxError: Unexpected end of input for return response.json(), but with no further message. What am I doing wrong?
If an opaque response serves your needs
It doesn't. You want to see the response. You can't see an opaque response (that is what opaque response means).
no-cors mode means that if the browser has to do anything that requires permission from CORS, it will fail silently instead of throwing an error.
So it is silently failing to get the response, then trying to parse that nothing as JSON (which throws a different error).
You need:
To not use no-cors mode
The server to grant permission using CORS
See this question for more information about CORS in general.
I am trying to use public json file as data source with following javascript:
const url = "https://data.melbourne.vic.gov.au/resource/ez6b-syvw.json";
var table = new Tabulator("#example-table", {
ajaxConfig:{
method: 'GET'
},
ajaxURL: url, //ajax URL
index:"MessageID",
autoResize:true,
layout:"fitData", //layout options
placeholder:"Awaiting Data...",
columns:[ //Define Table Columns
{title:"timestamp", field:"timestamp"},
{title:"temperature", field:"temp_avg"},
{title:"humidity", field:"humidity_avg"},
{title:"latitude", field:"latitude"},
{title:"longtitude", field:"longtitude"},
],
ajaxResponse:function(url, params, response){
//url - the URL of the request
//params - the parameters passed with the request
//response - the JSON object returned in the body of the response.
return response; //pass the data array into Tabulator
},
rowClick:function(e, row){ //trigger an alert message when the row is clicked
alert("Row " + row.getData().MessageId + " Clicked!!!!");
},
});
But I get following console message in chrome:
Access to fetch at 'https://data.melbourne.vic.gov.au/resource/ez6b-syvw.json' from origin 'http://192.168.0.6' has been blocked by CORS policy: Request header field access-control-allow-origin is not allowed by Access-Control-Allow-Headers in preflight response.
data.melbourne.vic.gov.au/resource/ez6b-syvw.json:1 Failed to load resource: net::ERR_FAILED
tabulator.min.js:5 Ajax Load Error - Connection Error: TypeError: Failed to fetch
(anonymous) # tabulator.min.js:5
tabulator.min.js:5 Ajax Load Error: TypeError: Failed to fetch
I donot know what am I doing wrong?
Please help.
Thanks.
It looks like there is an issue getting the data from your resource. Tabulator appears to always send an Access-Control-Allow-Origin, but your resource does not allow this. So, a workaround is to use your own fetch request instead of the Tabulator ajax options. Then you can use setData on the table instance.
Here is an example. https://jsfiddle.net/nrayburn/8wd3zo9q/33/
I am not sure if this is a bug, or if I am just not seeing a way to do it.
Add this in your ajaxConfig and you are good to go.
ajaxConfig:{
mode: "no-cors",
method: 'GET'
}
I create simple google chrome extension and I get JSON data but this error is generated
dashboard.html:1 Access to XMLHttpRequest at 'https://humane-like-developer-edition.ap4.force.com/services/apexrest/SessionHuman' from origin 'chrome-extension://dgbedclgdamcknolmpacbbigocadoiko' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource.
This is my code
var HttpClient=function()
{
this.get=function(aUrl,aCallback)
{
var anHttpRequest=new XMLHttpRequest();
anHttpRequest.onreadystatechange=function()
{
if(anHttpRequest.readyState==4 && anHttpRequest.status==200)
{
aCallback(anHttpRequest.responseText);
}
}
anHttpRequest.open("GET",aUrl,true);
anHttpRequest.send(null);
}
}
var theurl='https://humane-like-developer-edition.ap4.force.com/services/apexrest/SessionHuman';
var client=new HttpClient();
client.get(theurl,function(response){
alert(response);
No 'Access-Control-Allow-Origin' header is present on the requested resource.
The requested resource must respond an Access-Control-Allowed-Origin header matching your Origin request header.
If it is a public API you should respond with *.
Note: Protocol is type of the response if it is not *, multiple values are not allowed, as well as wildcards are not allowed.
I'm trying to send an ajax post request to a node.js microservice through nginx. The requuest is as follows:
$.post('http://localhost:80/api/signup', formData, function( data, status) {
console.log(JSON.stringify(data));
console.log(JSON.stringify(status));
}).done(function(data, status) {
alert( "second success" );
console.log(JSON.stringify(data));
console.log(JSON.stringify(status));
})
.fail(function(data, status) {
console.log('error');
console.log(JSON.stringify(data));
console.log(JSON.stringify(status));
})
.always(function(data, status) {
console.log(JSON.stringify(data));
console.log(JSON.stringify(status));
console.log('fiished');
});
The request reaches the microservice. But the response is as follows (which is always the error function):
"data" is always:
{"readyState":0,"status":0,"statusText":"error"}
And the "status" is always:
error
which is not the expected response at success nor failure.
How can I fix this?
Moreover, "formData" parameters appear as queries on the url once submitted. How can I stop that?
Update*
I have also tried adding event.preventDefault(); but now it gives me the following:
XMLHttpRequest cannot load http://localhost:3000/api/signup. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'null' is therefore not allowed access.
{"readyState":0,"status":0,"statusText":"error"}
I have also tried:
$.ajax({
type: "POST",
url: "http://localhost:3000/api/signup",
data: JSON.stringify(formData),
success: function(dataString) {
console.log(JSON.stringify(dataString));
}, error: function(error) {
console.log(JSON.stringify(error));
}
});
But got the same No 'Access-Control-Allow-Origin' header is present on the requested resource as above.
Update
There is a valid and possibly more detailed answer on "No 'Access-Control-Allow-Origin' header is present on the requested resource". However, I find the answer I accepted here more direct and clear.
Are you executing the ajax request from the browser or localhost? If you are executing it from your browser it may be CORS issue. If you want to be able to execute that ajax request from your browser you should modify your server configuration/code to allow cross-origin HTTP requests.
This looks similar to your issue. CORS issue in Jquery Ajax Post
I have built a API using node.js and express.
But i need to be able to proxy some requests on a specific route to a external server and show the response from the external server to the clint doing the request.
But i also need to forward the basic auth that the client is send along with the request.
I have tried using the request module like:
app.get('/c/users/', function(req,res) {
//modify the url in any way you want
var newurl = 'https://www.external.com'
request(newurl).pipe(res),
})
But it seems to not send the basic auth header because i get "403 Forbidden" back form the external server(www.external.com)
The request im making is looking like:
GET http://example.se:4000/c/users/ HTTP/1.1
Accept-Encoding: gzip,deflate
X-version: 1
Authorization: Basic bmR4ZHpzNWZweWFpdjdxfG1vcmV1c2*******=
Accept: application/json
Host: example.se:4000
Connection: Keep-Alive
User-Agent: Apache-HttpClient/4.1.1 (java 1.5)
And it works if i do the exact same request but against www.external.com directly so there is some issue when doing the proxy in node.
The request module is totally unaware of anything that you don't pass explicitly to it. To set the request headers and copy the response headers as well do the following:
// copy headers, except host header
var headers = {}
for (var key in req.headers) {
if (req.headers.hasOwnProperty(key)) {
headers[key] = req.get(key)
}
}
headers['host'] = 'final-host'
var newurl = 'http://final-host/...'
request.get({url:newurl, headers: headers }, function (error, response, body) {
// debug response headers
console.log(response.headers)
// debug response body
console.log(body)
// copy response headers
for (var key in response.headers) {
if (response.headers.hasOwnProperty(key)) {
res.setHeader(key, response.headers[key])
}
}
res.send(response.statusCode, body)
})
Try explicitly passing in the auth details like so
request(newurl).auth(username, password).pipe(res);
https://github.com/mikeal/request#http-authentication