Building a Simple Flask API with CORS: A Comprehensive Tutorial for Cross-Origin Resource Sharing

Learn how to build a powerful Flask API and implement CORS for secure cross-origin requests. Follow our step-by-step tutorial and develop robust APIs that seamlessly interact with frontend applications. Let's dive into Flask API development and explore the intricacies of CORS implementation.

· 6 min read
Flask & API logos
Building a Simple Flask API with CORS

Flask is a popular Python web framework that allows you to build APIs quickly and easily. In this tutorial, we'll walk through the process of creating a simple API using Flask and learn how to implement Cross-Origin Resource Sharing (CORS) to handle cross-domain requests. By the end of this tutorial, you'll have a basic API that supports CORS.

What Is CORS

Cross-Origin Resource Sharing (CORS) is a security mechanism that allows a web browser to make requests to a different domain than the one that served the original web page. By default, web browsers restrict cross-origin requests due to security concerns. CORS enables controlled access to resources on different domains, promoting a more open and interconnected web.

The Importance of CORS

It's essential to understand and implement CORS properly in your API development to strike a balance between security and interoperability. By configuring CORS effectively, you can ensure controlled access to your API while enabling legitimate cross-origin requests. These are the main reasons you might want to include CORS in your Flask app :

  1. Security: CORS plays a crucial role in maintaining security by preventing unauthorized access to sensitive data or resources. Without CORS restrictions, malicious websites could potentially access data from other domains on behalf of the user, leading to data breaches and privacy violations.
  2. Cross-Domain API Communication: In modern web development, it's common to build distributed systems where multiple services or APIs reside on different domains. CORS allows these services to interact with each other securely, facilitating seamless communication between applications.
  3. Client-Side Development: Many client-side applications, such as Single-Page Applications (SPAs) or JavaScript frameworks, rely on APIs to fetch data from servers. Without CORS, these applications would be limited to only making requests to the same origin, severely restricting their ability to consume data from external APIs.
  4. Enabling Third-Party Integrations: CORS enables developers to integrate third-party services, such as payment gateways, social media APIs, or mapping services, into their applications. It empowers developers to leverage external services and enrich their applications with additional functionality and features.
  5. Promoting Collaboration and Interoperability: CORS fosters collaboration between different domains and encourages interoperability by allowing developers to share and access resources across various platforms. It enables the creation of mashups, composite applications, and integrated web services that provide enhanced user experiences.

With a clear understanding of CORS and its significance in web development, we are now ready to dive into the practical implementation. Let's proceed and begin coding our Flask API with CORS.

Installation and Setup

Make sure you have Python installed on your machine. You can check your Python version by running python --version in your terminal. If Python is not installed, download and install it from the official Python website here python.org.

Also you need to install venv because it's good practice to create a virtual environment to keep our project dependencies isolated. Simply run the command:

python -m pip install venv

Now we can start creating our project:

1. Open the terminal and Create a new folder and navigate inside of it by using the command:

mkdir flask-api && cd flask-api

2. We will create a new virtual environment and name it venv for convention:

python -m venv venv

3. Now after we created our virtual environment we have to activate it:

  • For Mac/Linux:
source venv/bin/activate
  • For Windows:
venv\Scripts\activate

You should have (venv) in your terminal which indicates that your virtual environment is indeed activated like so :

activate python virtual environement preview

4. Now we can install Flask and the necessary dependencies in our virtual environement:

pip install flask flask-cors names

5. Create a new python script app.py in flask-api folder. Our project should looke like this by now:

flask-api/
├── venv
└── app.py

Setting Up the Flask Application and CORS

Open app.py with the IDE of your choice, I will be using VSCode so i can open the folder as a project by running:

code .

Note : you don't have to do this if you aren't using VSCode.

1. We start by importing the necessary modules:

# Other modules
import names
from random import randint
# Flask modules
from flask import Flask, jsonify
from flask_cors import CORS

2. Next we can create a function that gives us a list of dummy data that we can serve from our API and that will be by using the names module:

def get_dummy_data(count: int = 10):
	dummy_data = list()
	for _ in range(count):
		person = {
			"name": names.get_full_name(),
			"age": randint(18, 60),
			"is_working": randint(0, 1) == 1,
		}
		dummy_data.append(person)
	return dummy_data

3. Create the Flask application instance and enable CORS by adding the following code:

app = Flask(__name__)
CORS(app, resources={r"/api/*": {"origins": ["http://localhost:3000", "http://127.0.0.1:3000"]}})

4. Let's define our API route that will return a JSON response from the dummy data function. Add the following code below the application instance:

@app.route('/api/data', methods=['GET'])
def dummy_data():
    data = get_dummy_data()
    return jsonify(data), 200

5. Finally we need to add one more thing to be able to run our application:

if __name__ == '__main__':
    app.run(host="0.0.0.0", port=5000)

The full script should look like this:

# Other modules
import names
from random import randint
# Flask modules
from flask import Flask, jsonify
from flask_cors import CORS

def get_dummy_data(count: int = 10):
	dummy_data = list()
	for _ in range(count):
		person = {
			"name": names.get_full_name(),
			"age": randint(18, 60),
			"is_working": randint(0, 1) == 1,
		}
		dummy_data.append(person)
	return dummy_data

app = Flask(__name__)
CORS(app, resources={r"/api/*": {"origins": ["http://localhost:3000", "http://127.0.0.1:3000"]}})

@app.route('/api/data', methods=['GET'])
def dummy_data():
    data = get_dummy_data()
    return jsonify(data), 200

if __name__ == '__main__':
    app.run(host="0.0.0.0", port=5000)

6. Starting the flask application from the terminal:

python app.py

In this case, requests originating from let's say for example our frontend Nextjs app running on http://localhost:3000 or http://127.0.0.1:3000 will be permitted to access the /api/data as well as any other paths that begin with /api/. However, requests from origins other than what we defined will be blocked by CORS.

If you would like for requests from all origins to be permitted you can set origins to be "*" like so :

CORS(app, resources={r"/api/*": {"origins":"*"}})

Testing Our CORS

In the same folder, we open our terminal and, after ensuring that your virtual environment is activated, we start by running our Flask app:

python app.py

Now open your browser and head to localhost:5000/api/data, if the API is working as intended you should see the dummy data:
API response preview

We will start another simple http server on port 8000 by going back to the terminal and running the command:

python -m http.server

Let's try to fetch data in our http server from the Flask API. Open your browser and head to localhost:8000 then open the browser developer tools, select Console tab and run the following command:

await fetch("http://localhost:5000/api/data")

You will be faced with the following error:

CORS errors preview
This means our CORS are working because the request was blocked since http://localhost:8000 was not included in our CORS origins.

If we go back and add the new server to our CORS:

CORS(app, resources={r"/api/*": {"origins": ["http://localhost:3000", "http://127.0.0.1:3000", "http://localhost:8000"]}})

Then we try to make the same request in the Console:

CORS error fixed preview

Now we get a 200 STATUS response which means its working properly and http://localhost:8000 is now allowed to make requests to our Flask API.

Conclusion

Congratulations! You've successfully built a simple API with Flask and implemented CORS to handle cross-origin requests. CORS is an essential security feature that allows controlled access to your API from different domains. Flask and Flask-CORS provide an easy way to handle CORS in your API development.

Remember that enabling CORS without proper security measures can have implications. Always consider the security requirements of your application and implement appropriate access controls.

You can find the project source code on Github.