Cross Origin Problem with Flask Api (Access-Control-Allow-Origin) - api

Hello all good people.
I have tested everything that I can find on internet and nothing is working to fix this problem. I'm really hoping that someone here can help me solve this.
When i try to do "patch" request from backend to my flask API I get this error (GET, DELETE & PUT are working fine):
Access to fetch at 'https://MYAPI-NOTREALURL.com' from origin
'https://MYBACKEND-NOTREALURL.com' has been blocked by CORS policy:
Response to preflight request doesn't pass access control check: The
'Access-Control-Allow-Origin' header contains multiple values
'https://MYBACKEND-NOTREALURL.com, *', but only one is allowed. Have
the server send the header with a valid value, or, if an opaque
response serves your needs, set the request's mode to 'no-cors' to
fetch the resource with CORS disabled.
This is how my code for API is written:
from flask_cors import CORS, cross_origin
from flask import render_template, redirect, flash, request, url_for, jsonify, session, make_response
from flask_restful import Api, Resource, reqparse
import requests
app = Flask(__name__)
cors = CORS(app, resources={r"/*": {"origins": "*"}})
api = Api(app)
class ordersByID(Resource):
def get(self,ID_ORDER):
****
return jsonify(data)
def patch(self,ID_ORDER):
req321 = request.form
result = updateOrder(req321,ID_ORDER)
return result
def delete(self,ID_ORDER):
****
return result
def put(self,ID_ORDER):
****
return result
api.add_resource(ordersByID, "/orders/id/<string:ID_ORDER>")
if __name__ == '__main__':
app.run(debug=True)
I have tested everything that I can find on internet and nothing is working when trying to do patch request. I'm doing patch request with fetch from popup window.
<form action="{{ **https://MYAPI-NOTREALURL.com** }}" id="popupForm" method="patch" onsubmit="formFetch(event,this,'patch')">
You can check javascript code under.
function formFetch(e,form,method) {
result = fetch(form.action, {method:method, body: new FormData(form)})
.then(response => response.json())
.then(data => document.getElementById('submitedFormConfirmationText').innerHTML = data['DB_Result']
);
e.preventDefault();
document.getElementById('submitedFormConfirmation').style.display = 'inline';
};
I really hope that someone can help me solve this problem without needing to redo whole code?

I managed to solve this.
For some strange reason "patch" with small letters was working on local but when deployed it did not work.
Changing method from "patch" to "PATCH" solved this problem.

Related

receive JSON array data from fetch or axios.get VueJS

I am going mental. So I have the code below. When I run it as is, I get
Access to XMLHttpRequest at 'URL' from origin 'http://localhost:8000' 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 I remove the CORS header I get the same error. I am not sure what I am doing wrong. I will tell you if I curl the URL it works fine. What am I missing here.
Also, I have tried this using both axios.get AND fetch so I am open to both solutions.
getRoomUserCount: function () {
return axios
.get('URL', {
responseType: "json",
});
},
What it SHOULD return is an array of data, then using the code below I grab the array
mounted: function () {
this.roomUserCount = this.getRoomUserCount();
},
CORS policy is ALWAYS server related. You cannot change anything on your client-side to change that.
Enable CORS on your server to fix this.

Vue3 app after logout throws CORS policy error

I have Vue3 app which makes requests with Axios. As I logout from the app and then login again app starts throwing error
create:1 Access to XMLHttpRequest at 'https://vue.tatrytec.eu/'
(redirected from 'https://tatrytec.eu/api/article/store') from origin
'https://vue.tatrytec.eu' 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.
One thing I dont understand is that as I reload the page it starts working and error is gone. The code is still the same. How can reload has impact to the CORS error?
The app code for Axios is in this Github repository.
import axios from "axios"
window.axios = axios;
//axios.defaults.baseURL = apiRoutes.API_URL_SHORT;
axios.defaults.withCredentials = true;
axios.defaults.headers.common['X-Requested-With'] = 'XMLHttpRequest';
let authToken = localStorage.getItem('authToken');
axios.defaults.headers.common['Authorization'] = 'Bearer ' + authToken;
axios.defaults.headers.common['Access-Control-Allow-Origin'] = 'https://vue.tatrytec.eu';
Hope somebody knows cause I have no idea what happened there.
The problem was in the login form axios setting. There was this code
axios.defaults.headers.common = {
'Authorization': 'Bearer ' + token
};
I dont know where I found it but this garbage code rewrites whole common object in axios settings. So I lost all other headers. Really would like to know where I found this code. The proper style is to use array syntax like common['Authorization'] = ... Vrrrrr.

Set-Cookie not accessible through axios or fetch

I am building a web application with a go backend and a vue.js frontend.
I want to do a simple sign in form in which I send the sign in request from a method of my component with Axios (or fetch) and get in response a JSON object of the user and a session token in the cookie to be stored and reused in future requests to the server.
The code of my components method :
class LoginComponent extends Vue {
sendLogin (): void {
axios.post<User>('http://192.168.1.227:8080/signin', body)
.then(res => console.log('Axios Response :', res)
.catch(err => console.error('Axios Error :', err))
}
}
The part of the code of the go server :
go API
with the headers :
go headers
the front and backend are on different IP addresses in a local network and they communicate through HTTP.
The problem that I faced is that when receiving the response after the post request to login I don't have access to the cookie that has been set by the server. When I use Axios to analyze the response the cookie isn't in the headers whereas when I look at the network logs in the browser, the cookie is in the headers but it is not saved and it is not sent when I do another request.
Also, the only header that is visible with Axios is Content-Type : application/json; charset=UTF-8
I tried many things to be able to see this cookie but it doesn't work :
adding { withCredentials: true } to the axios request or axios.defaults.withCredentials = true to the axios instance only stops the request because of CORS.
changing all the Access-Control headers to "*" didn't change anything
using { auth: { username: 'foo', password: 'bar' } } in the axios options instead of the body
The only thing that worked and automatically saved the cookie was to send the request via the attributes of the form html tag, like so :
<form method="POST" action="http://192.168.1.227/signin">
...
</form>
But this way I am redirected to the JSON response object and not to one of my routes from vue-router and I can't access the User object in my app.
Is there any way that my problem can be solved?
Ok so the comment of Зелёный was the answer.
I needed the go server to set Access-Control-Allow-Origin: http://192.168.1.218:8080 (the address of the frontend) and then configure axios with { withCredentials: true } to be able to automatically store the cookie. Although I still don't see it when I do a console.log on the axios response, it is successfully stored and reused for each call to the server.

make a HTTP Request from React-Redux from localhost

I am new to React Redux, and All I already did:
1) activate my backend server (localhost:5000)
2) activate my front-end server using npm start (localhost:8080)
3) I tried to dispatch action by using
this.props.dispatch({type: ActionTypes.FILE_UPLOAD_REQUEST, email: this.state.email, file: this.state.policyFile});
4) Using atlas-saga, and call my service function associated with the dispatch :
let result = yield call(Atlas.uploadFile, action.email, action.file);
5) define the function as :
export const uploadFile = (email, file) => {
return fetch(`${BASE_URL}/v1/files/${email}/policies`, {
method: 'POST',
headers:{} ,
body: {'file': file}
})
.then(response => response.json())
}
After I try to run a function at my react( a function that calls the dispatch), it gives me errors that they cannot found the route. This is the error message from the console.
Fetch API cannot load https://api-staging.autoarmour.co/v1/files/fakeemail#gmail.com/policies. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://localhost:8080' is therefore not allowed access. The response had HTTP status code 500. If an opaque response serves your needs, set the request's mode to 'no-cors' to fetch the resource with CORS disabled.
Yes, I did not create any reducer, just pure function that will upload a file. Thank you
I SOLVE IT, WOHOO!!!
The error message means that its not connected at the backend side at all. You need to make sure that it is connected. I solve it by connecting my redux to my react component. Thanks guys
Cheers!

Aurelia Post with http-fetch-client producing an options request

I'm creating a small forum where people in our company can put up adverts for goods or services they want to sell on the fly, using aurelia. I have a list of adverts page working fine, a details page for each advert working fine both using get requests from an api. However i can't seem to get the work the Post reqeust when someone wants to add a comment on an advert.
#inject(HttpClient)
export class ApiData {
constructor(httpClient) {
httpClient.configure(config => {
config
.withBaseUrl("MyUrl");
});
this.http = httpClient;
//.configure(x => {x.withHeader('Content-Type', 'application/json');});
}
postAdvertComment(comment, id) {
return this.http.fetch(`/adverts/${id}/comments`, {
method: "post",
body: json(comment),
headers: {
'Accept': 'application/json'
}
});
}
getAdverts() {
return this.http.fetch("/adverts")
.then(response => {
return this.adverts = response.json();
});
}
getAdvert(id) {
return this.http.fetch(`/adverts/${id}`)
.then(response => {
return this.advert = response.json();
});
}
}
Doing this project we've had some issue with CORS, all solved by adding in AllowCors tags in the api, including all methods etc.
<add key="CorsAllowedOrigins" value="*" />
<add key="CorsAllowedHeaders" value="" />
<add key="CorsAllowedMethods" value="*" />
However when i try and run the post, its running an options method and returns a 400 Bad request.
Here
We also get the following CORS error:
Fetch API cannot load MyURL/api/adverts/2/comments. 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:49877' is
therefore not allowed access. The response had HTTP status code 400. If an
opaque response serves your needs, set the request's mode to 'no-cors' to fetch
the resource with CORS disabled.
I don't know if it's a problem with our c# api or with how I'm trying to post from aurelia, but we have tried sending requests from postman and it works fine, tried sending post request within the same app using jquery and it works fine, and all the get requests work fine, but for some reason this post is causing all sorts of problems.
It seems to be a problem in your WebAPI, but before giving you some possible solutions I'd like to show you some important things.
Postman is not affected by CORS, so all requests work.
jQuery ajax uses XHR (XmlHttpRequest object) while aurelia-fetch-client uses fetch (window.fetch. However, the fetch-polyfill uses XHR in the background). They are
different approaches to solve the same problem. Just because one of them work, doesn't actually mean that the other one should work too.
The OPTIONS request is made by fetch, that's how it works. More information here https://developers.google.com/web/updates/2015/03/introduction-to-fetch?hl=en
To solve this problem try to remove those tags from web.config, and allow CORS in your Startup.cs. Like this:
public void Configuration(IAppBuilder app)
{
app.UseCors(CorsOptions.AllowAll); //or another parameter
//rest of your code
}
You don't have to set the content-type header to application/json. It is automatically made when you use the json() function ---> body: json(comment)
If you are using OWIN you might have to send the content-type as x-www-form-urlenconded. In that case, take a look at this Post 'x-www-form-urlencoded' content with aurelia-fetch-client