I'm working on a small nodejs-express-react app. I'm sending a request against the Google Analytics Management API server-side then trying to fetch the response from the client-side. It doesn't work as the Status Code of the fetch is Status Code: 405. however, I'm seeing that the fetched URL is not the same as the requested URL. I don't understand what is wrong exactly.
I'm fetching /auth/google/callback but according to the network information and looking at the error the url requested is https://accounts.google.com/o/oauth2/v2/auth?response_type=code&redirect_uri=http%3A%2F%2Flocalhost%3A5000%2Fauth%2Fgoogle%2Fcallback&client_id=XXXXXXX-XXXXXXX.apps.googleusercontent.com
Here is the full error:
Access to fetch at 'https://accounts.google.com/o/oauth2/v2/auth?response_type=code&redirect_uri=http%3A%2F%2Flocalhost%3A5000%2Fauth%2Fgoogle%2Fcallback&client_id=XXXXXXXX-XXXXXXXX.apps.googleusercontent.com' (redirected from 'http://localhost:5000/auth/google/callback') from origin 'http://localhost:5000' has been blocked by CORS policy: Response to preflight request doesn't pass access control check: 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.
I have this on the server-side:
app.get(
"/auth/google",
passport.authenticate("google", { scope: ['Profile','https://www.googleapis.com/auth/analytics.readonly'] })
);
app.get(
"/auth/google/callback",
passport.authenticate("google", { failureRedirect: "/error", session: false }),
function(req, res) {
var token = req.user.token;
request('https://www.googleapis.com/analytics/v3/management/accounts?access_token=' + token,
function (error, response, body) {
console.log(JSON.parse(body).items);
res.send({data:JSON.parse(body).items})
});
}
);
And this on the client-side:
componentDidMount() {
fetch('/auth/google/callback', {
method: 'GET',
withCredentials: true,
headers: {
'Content-Type': 'application/json',
'Access-Control-Allow-Origin': '*'},
credentials: 'same-origin'
})
.then(res => res.json())
.then(user => this.setState({ data: data }));
}
How should I structure my node/express back-end so I can make the react-side fetch work correctly?
EDIT: I've added 'Access-Control-Allow-Origin': '*' in the header but still got the error.
fetch('/auth/google/callback' requires a full URL (for example https://localhost:8080/auth/google/callback)
EDIT
headers: {
'Content-Type': 'application/json',
'Access-Control-Allow-Origin': '*'
}
Related
In my Mern Stack Project I am facing a problem when I am creating a Lesson from postman its created successfully but when I am trying from my browser its given me 500 error in network tab. But in console i got CORS error and also 500 error. I am including SS in bellow if anyone can face this kind of problem please help me. I am trying all the similiar solution from stackoverflow.
Access to XMLHttpRequest at 'https://lms-api-v1.coderslab.com.bd/api/v1/lesson/add' from origin 'http://localhost:3000' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource.
const apiClient = axios.create({
baseURL: "https://my-link",
withCredentials: false,
accesscontrolalloworigin: "*",
accesscontrolallowMethods: "GET, POST, PUT, DELETE, PATCH, OPTIONS",
});
// Create Lesson
export const createLesson = (lessonData, token) => async (dispatch) => {
try {
dispatch({ type: NEW_LESSON_REQUEST });
const config = {
headers: {
Authorization: `Bearer ${token}`,
'Access-Control-Allow-Origin' : '*',
'Access-Control-Allow-Credentials':true,
'Access-Control-Allow-Methods':'GET,PUT,POST,DELETE,PATCH,OPTIONS',
},
};
const { data } = await apiClient.post(`lesson/add`, lessonData, config);
dispatch({
type: NEW_LESSON_SUCCESS,
payload: data,
});
} catch (error) {
dispatch({
type: NEW_LESSON_FAIL,
payload: error.response,
});
}
};
you need to allow origin from backend. like this
Access-Control-Allow-Origin: http://localhost:3000
Add this in backend
Access-Control-Allow-Origin: '*'
I am getting,
Access to fetch at 'http://localhost:9000/api/v1/content' 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.
and
for my FE(react)
and getting syntax err for BE(node),
SyntaxError: Unexpected token " in JSON at position 0
I have no issue with GET request but I can't POST.
Here is my FE
addContent = async (e) => {
e.preventDefault();
try {
const response = await fetch('http://localhost:9000/api/v1/content', {
method: 'POST',
body: JSON.stringify(this.state.title),
// mode:'cors', --> tried after researching but it didn't solve my issue
headers: {
'Content-Type': 'application/json'
}
});
if(!response.ok) {
throw Error(response.statusText)
}
} catch (err) {
console.log('addContent failed -', err)
}
}
Here is my BE
origin: ['http://localhost:3000', 'https://localhost:3000'],
credentials: true,
optionsSuccessStatus:200
}
app.use(cors(corsOptions));
Also, when I POST with postman, I was able to POST(got 200) however, it only returns _id. there is no body(content title that I want to post)
I read many articles that explained about cors issue but I couldn't find right answer to solve my issue. Please assume me as beginner of programing.. Thank you ahead!!
Try This
addContent = async (e) => {
e.preventDefault();
try {
const response = await fetch('http://localhost:9000/api/v1/content', {
method: 'POST',
body: JSON.stringify(this.state.title),
// mode:'cors', --> tried after researching but it didn't solve my issue
headers: {
'Access-Control-Allow-Origin': '*',
'Content-Type': 'application/json'
}
});
if(!response.ok) {
throw Error(response.statusText)
}
} catch (err) {
console.log('addContent failed -', err)
}
}
And also you can refer https://developer.mozilla.org/en-US/docs/Web/API/Fetch_API/Using_Fetch
And I suggest try once without using cors at express.
origin: ['http://localhost:3000', 'https://localhost:3000'],
credentials: true,
optionsSuccessStatus:200
}
//app.use(cors(corsOptions));
Your error here, means that you are not allowed to access localhost:9000 from any other URL.
I recommend you take a look at this (https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS)
If you want your API to be accessed by anyone, you can set your "Access-Control-Allow-Origin" header to "*".
Here is a full explanation of this header purpose (https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Access-Control-Allow-Origin).
I hope it will be useful.
I need to access a website login page with my ejs file login page here is my routes for my login page
router.get('/login', (req,res)=> {
res.render('login');
router.post('/login', passport.authenticate('local', {
successRedirect : '/index',
failureRedirect : '/',
failureFlash: 'Invalid email or password. Try Again!!!'
}));
here is my documentation of the other website:
URL: https://website/restapi/user/signin
POST Request
Resquest Headers:
content-type: application/json
Request Body:
json format
{"username":"VALUE","password":"VALUE"}
Ex:
{"username":"test","password":"test123"}
Response:
In case of success:
Response status:
200 OK
Response Header:
authorization: Bearer
eyJhbGciOiJIUzUxMiJ9.eyJzdWIiOiJmYWRpLmhlbnJpQHBoYXJvcy1zb2x1dGlvbnMuZGUiL
CJleHAiOjE1MjU4ODA0OTN9.wNrvFQSH-L4ibgcEhKd-4WE8H3t2P4vYDK8wcGtLIGcaJr0Z
TZPCCeXePaa4HbGvZ9fsgOWgBLCyRYOVTur27w
** The header "authorization" shall be used as request header with same name in any
rest further request
Response body:
json format
{"user":{"id":3,"username":"test","firstname":"Test","lastname":"User","email
":"test#gmail.com",
how can I add post routes using this API documentation include authorization?
Thanks #syed Mohib uddin i got the results
axios({
method: 'POST',
url:'website/rest/user/signin',
data,
headers: {
'content-type': 'application/json'
}
})
.then(res => console.log(res.headers.authorization))
.catch(err => console.log(err));
I am making a simple full-stack project wherein I have a very basic REST API built using NodeJS and Express. It is a server-side rendered website.
While trying to login, when I send a POST request to the login endpoint, I am getting the following error in the console
Access to XMLHttpRequest at 'http://127.0.0.1:3000/api/v1/users/login'
from origin 'http://localhost:3000' has been blocked by CORS policy:
Response to preflight request doesn't pass access control check: No
'Access-Control-Allow-Origin' header is present on the requested
resource.
This is the code snippet that sends the POST request
const login = async (email,password) => {
try {
const res = await axios({
method: 'POST',
url: 'http://127.0.0.1:3000/api/v1/users/login',
data: {
email,
password
}
});
if(res.data.status === 'success') {
alert('Logged in successfully');
window.setTimeout(() => {
location.assign('/');
}, 1500);
}
}
catch(err) {
console.log(err);
}
}
Please explain as to why I'm getting that error and how to fix it. The API is not deployed yet and it's running on localhost
Your request origin is:
http://localhost:3000
This is not the same as the domain you're sending the request to:
http://127.0.0.1:3000
To avoid this CORS error, the FQDN must be the same, including hostname and port. (Or you could configure your server for CORS.) As far as the server is concerned, the different host means a completely separate entity, even if it's the same machine.
Change your url to:
url: 'http://localhost:3000/api/v1/users/login',
could you add Access-Control-Allow-Origin header to the request and see ,
const login = async (email,password) => {
try {
const res = await axios({
method: 'POST',
url: 'http://127.0.0.1:3000/api/v1/users/login',
headers: {
'Access-Control-Allow-Origin': '*',
'Content-Type': 'application/json',
},
data: {
email,
password
}
});
if(res.data.status === 'success') {
alert('Logged in successfully');
window.setTimeout(() => {
location.assign('/');
}, 1500);
}
}
catch(err) {
console.log(err);
}
}
I don't know why this happens.
When I'm making a request to my server in Node.js and when it's GET then I can get a response. It looks like that:
fetch(config.apiUsersURL, {
method: "GET",
headers: {
"Content-Type": "application/json"
},
credentials: "same-origin",
mode: 'no-cors'
})
.then(res => this.setState({
isConected: true
}))
.catch(error => error);
When I'm requesting to the same url but with POST I'm getting nothing. Am I missing something?
const ObjToSend = { isReady: true };
fetch( config.apiUsersURL, {
method: 'POST',
mode: 'no-cors',
body: JSON.stringify(ObjToSend),
headers: {
"Content-Type": "application/json"
},
credentials: "same-origin",
mode: 'no-cors',
})
.then(res => res.json())
.then(r => this.setState({ questions: r }))
My endpoint looks like that:
let randomProblem2;
router.post('/', (req, resp) => {
resp.append('Access-Control-Allow-Origin', '*')
resp.append('Access-Control-Allow-Headers', 'Content-Type')
console.log("this shows if yes was clicked", req.body)
if(req.body.isReady){ //when clicked
randomProblem2 = problemManager.getRandomProblem();
randomize(randomProblem2, resp);
}
})
function randomize(randomProblem2, resp){
resp.json({
randomProblem : randomProblem2
}
)}
Since the mode you are using is no-cors, you cannot use javascript to access the response
Quoted below from MDN:
no-cors — Prevents the method from being anything other than HEAD, GET
or POST, and the headers from being anything other than simple
headers. If any ServiceWorkers intercept these requests, they may not
add or override any headers except for those that are simple headers.
In addition, JavaScript may not access any properties of the resulting
Response. This ensures that ServiceWorkers do not affect the semantics
of the Web and prevents security and privacy issues arising from
leaking data across domains.
Kindly check the MDN link below for the rest of mode options
https://developer.mozilla.org/en-US/docs/Web/API/Request/mode