Forums

Trouble with Flask CORS Configuration for Netlify Frontend

Hello PythonAnywhere Community,

I am experiencing persistent CORS issues when trying to connect my Netlify-hosted frontend with my Flask backend hosted on PythonAnywhere. Despite setting up CORS in Flask using the flask_cors extension and verifying my configuration with curl tests, my requests are still encountering CORS errors.

Here's a brief overview of the problem:

Frontend URL: https://gentle-starburst-0dc595.netlify.app
Backend Flask App URL: https://hrano.pythonanywhere.com

I have configured CORS in my Flask app as follows:

from flask import Flask
from flask_cors import CORS

app = Flask(__name__)
CORS(app, resources={r"/*": {"origins": "https://gentle-starburst-0dc595.netlify.app"}})

I am using JavaScript's fetch API to make requests to the Flask backend. Here's an example call from the frontend:

fetch("https://hrano.pythonanywhere.com/getIDOfWhitelistedAddress", {
    method: 'POST',
    headers: {
        'Content-Type': 'application/json'
    },
    body: JSON.stringify({ address: walletAddress })
});

The curl tests for OPTIONS requests return the correct headers, indicating that the CORS settings are being respected:

< Access-Control-Allow-Origin: https://gentle-starburst-0dc595.netlify.app/
< Access-Control-Allow-Headers: Content-Type,Authorization
< Access-Control-Allow-Methods: GET,PUT,POST,DELETE

However, my browser is still blocking the requests due to CORS policy. I've tried multiple troubleshooting steps, such as clearing the browser cache, verifying the Flask routes, and ensuring there are no typos in the URLs or issues with the HTTP methods.

Here are the CORS error i am getting in my browser console

Access to fetch at 'https://hrano.pythonanywhere.com/getTotalWalletAddresses' from origin 'https://gentle-starburst-0dc595.netlify.app' has been blocked by CORS policy: Response to preflight request doesn't pass access control check: The 'Access-Control-Allow-Origin' header has a value 'https://gentle-starburst-0dc595.netlify.app/' that is not equal to the supplied origin. 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.
game.js:71




      GET https://hrano.pythonanywhere.com/getTotalWalletAddresses net::ERR_FAILED
fetchTotalWalletAddresses @ game.js:71
determinePlayersId @ game.js:88
examplePlayersIdUsage @ game.js:93
(anonymous) @ game.js:101
game.js:81 Error fetching total number of wallet addresses from the server: TypeError: Failed to fetch
    at fetchTotalWalletAddresses (game.js:71:32)
    at determinePlayersId (game.js:88:23)
    at examplePlayersIdUsage (game.js:93:11)
    at game.js:101:1
fetchTotalWalletAddresses @ game.js:81
await in fetchTotalWalletAddresses (async)
determinePlayersId @ game.js:88
examplePlayersIdUsage @ game.js:93
(anonymous) @ game.js:101
game.js:97 Failed to fetch playersId.
gentle-starburst-0dc595.netlify.app/:1 Access to fetch at 'https://hrano.pythonanywhere.com/getIDOfWhitelistedAddress' from origin 'https://gentle-starburst-0dc595.netlify.app' has been blocked by CORS policy: Response to preflight request doesn't pass access control check: The 'Access-Control-Allow-Origin' header has a value 'https://gentle-starburst-0dc595.netlify.app/' that is not equal to the supplied origin. 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.
game.js:27


       POST https://hrano.pythonanywhere.com/getIDOfWhitelistedAddress net::ERR_FAILED
fetchPlayerIdFromWalletAddress @ game.js:27
determinePlayerId @ game.js:48
await in determinePlayerId (async)
exampleRandomPlayersIdUsage @ game.js:117
(anonymous) @ game.js:124
game.js:38 Error fetching playerId from server: TypeError: Failed to fetch
    at fetchPlayerIdFromWalletAddress (game.js:27:32)
    at determinePlayerId (game.js:48:26)
    at async exampleRandomPlayersIdUsage (game.js:117:5)
fetchPlayerIdFromWalletAddress @ game.js:38
await in fetchPlayerIdFromWalletAddress (async)
determinePlayerId @ game.js:48
await in determinePlayerId (async)
exampleRandomPlayersIdUsage @ game.js:117
(anonymous) @ game.js:124
gentle-starburst-0dc595.netlify.app/:1 Access to fetch at 'https://hrano.pythonanywhere.com/getIDOfWhitelistedAddress' from origin 'https://gentle-starburst-0dc595.netlify.app' has been blocked by CORS policy: Response to preflight request doesn't pass access control check: The 'Access-Control-Allow-Origin' header has a value 'https://gentle-starburst-0dc595.netlify.app/' that is not equal to the supplied origin. 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.
game.js:27


       POST https://hrano.pythonanywhere.com/getIDOfWhitelistedAddress net::ERR_FAILED
fetchPlayerIdFromWalletAddress @ game.js:27
determinePlayerId @ game.js:48
await in determinePlayerId (async)
examplePlayerIdUsage @ game.js:54
(anonymous) @ game.js:62
game.js:38 Error fetching playerId from server: TypeError: Failed to fetch
    at fetchPlayerIdFromWalletAddress (game.js:27:32)
    at determinePlayerId (game.js:48:26)
    at async examplePlayerIdUsage (game.js:54:5)
fetchPlayerIdFromWalletAddress @ game.js:38
await in fetchPlayerIdFromWalletAddress (async)
determinePlayerId @ game.js:48
await in determinePlayerId (async)
examplePlayerIdUsage @ game.js:54
(anonymous) @ game.js:62
game.js:58 Wallet not connected or playerId fetch failed.
gentle-starburst-0dc595.netlify.app/:1 Access to fetch at 'https://hrano.pythonanywhere.com/getTotalWalletAddresses' from origin 'https://gentle-starburst-0dc595.netlify.app' has been blocked by CORS policy: Response to preflight request doesn't pass access control check: The 'Access-Control-Allow-Origin' header has a value 'https://gentle-starburst-0dc595.netlify.app/' that is not equal to the supplied origin. 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.
game.js:71


       GET https://hrano.pythonanywhere.com/getTotalWalletAddresses net::ERR_FAILED
fetchTotalWalletAddresses @ game.js:71
determinePlayersId @ game.js:88
exampleRandomPlayersIdUsage @ game.js:118
await in exampleRandomPlayersIdUsage (async)
(anonymous) @ game.js:124
game.js:81 Error fetching total number of wallet addresses from the server: TypeError: Failed to fetch
    at fetchTotalWalletAddresses (game.js:71:32)
    at determinePlayersId (game.js:88:23)
    at exampleRandomPlayersIdUsage (game.js:118:11)

I would appreciate any advice or guidance on resolving these CORS issues or any other configuration steps I might have overlooked.

Thank you for your help!

[edit by admin: formatting]

That's really odd. I think I can see the problem -- if you look at the headers, you are getting

Access-Control-Allow-Origin: https://gentle-starburst-0dc595.netlify.app/

--- note the trailing slash, which matches up with the error in the JS console:

https://hrano.pythonanywhere.com/getTotalWalletAddresses' from origin 'https://gentle-starburst-0dc595.netlify.app' has been blocked by CORS policy: Response to preflight request doesn't pass access control check: The 'Access-Control-Allow-Origin' header has a value 'https://gentle-starburst-0dc595.netlify.app/' that is not equal to the supplied origin

However, I don't see anything obvious in your Flask-CORS config that would add that trailing slash at the end of the "origins" parameter. Is there any chance that you're running an older version of the code that has a trailing slash there, and haven't reloaded the site from the "Web" page since correcting it?