DEV Community

Nina Hwang
Nina Hwang

Posted on

CORS Explained + Enable in Python Projects

CORS

CORS("Cross-Origin Resource Sharing") refers to the situation when the domain requesting a resource is different from the domain serving that resource. This happens frequently when a front-end and a back-end are in different origins and the front-end communicates with the back-end using JavaScript code.

Origin

"Origin" is the combination of protocol(e.g. http, https), domain(e.g. somedomain.com, localhost), and port(e.g. 80, 443, 3000, 8000).

Therefore, all these are different origins.

  • http://localhost
  • http://localhost:8000
  • https://localhost

Allow CORS

Browsers restrict cross-origin HTTP requests initiated from scripts due to security issue. Therefore, if you want to enable CORS, you should specify allowed origins(origins that are permitted to make cross-origin requests), allowed methods(HTTP methods that are allowed for cross-origin requests), and allowed headers(HTTP request headers that should be supported for cross-origin requests) etc.

Types of CORS Request

Preflight Requests

Before performing cross-domain requests, browsers will initiate "preflight" request to determine whether those requests are allowed. The preflight requests are done by OPTIONS , which is a type of HTTP methods.

Simple Requests

If the request meets certain conditions, browsers don't send preflight requests.

Simple requests satisfy these conditions:

  1. HTTP method is either:
    • GET
    • HEAD
    • POST
  2. Apart from the headers automatically set by the user agent, the only headers which are allowed to be manually set are one of these:
    • Accept
    • Accept-Language
    • Content-Language
    • Content-Type
      • Only application/x-www-form-urlencoded, multipart/form-data, text/plain are allowed as values
  3. If the request is made using an XMLHttpRequest object, no event listeners are registered on the object returned by the XMLHttpRequest.upload property used in the request
  4. No ReadableStream object is used in the request.

For more information about CORS, check this document.

CORS Hands-On

Django

Install CORS module:
pip install django-cors-headers

# settings.py
ALLOWED_HOSTS = ['*'] # '*' is a wildcard which allows any host

INSTALLED_APPS = [
    ...
    'corsheaders',
    ...
]

MIDDLEWARE = [
    ...
    'corsheaders.middleware.CorsMiddleware',
    ...
]

# CORS settings
CORS_ORIGIN_ALLOW_ALL=True
CORS_ALLOW_CREDENTIALS = True

CORS_ALLOW_METHODS = (
    'DELETE',
    'GET',
    'OPTIONS',
    'PATCH',
    'POST',
    'PUT',
)

CORS_ALLOW_HEADERS = (
    'accept',
    'accept-encoding',
    'authorization',
    'content-type',
    'dnt',
    'origin',
    'user-agent',
    'x-csrftoken',
    'x-requested-with',
)
Enter fullscreen mode Exit fullscreen mode

For more information about django-cors-headers, check this document.

FastAPI

# main.py
from fastapi.middleware.cors import CORSMiddleware

app = FastAPI()

origins = ["*"]

app.add_middleware(
    CORSMiddleware,
    allow_origins=origins,
    allow_credentials=True,
    allow_methods=["*"],
    allow_headers=["*"],
)
Enter fullscreen mode Exit fullscreen mode

For more information about FastAPI CORS setup, check this document.

Flask

Install CORS extension:
pip install -U flask-cors

# main.py
from flask-cors import CORS

app = Flask(__name__)

CORS(app)
Enter fullscreen mode Exit fullscreen mode

For more information about flask-cors, check this document.

Discussion (4)

Collapse
thumbone profile image
Bernd Wechner

I appreciate the article, but you do make one mistake I see in such articles across the web. That is you quietly mix the roles and client and server in your presentation.

You start with "Most of browsers do not allow CORS" and then list three server solutions ...

It is precisely this that trips us up with CORS from the get go. What role the browser plays and what role the server plays. It's worth some effort to differentiate these clearly.

Collapse
ninahwang profile image
Nina Hwang Author

Thank you for the feedback! To be honest, the concept is still not perfectly crystal clear for me, and that's why I needed to summarize it. It got a little more clearer thanks to your comment:)

Collapse
ramkumarm15 profile image
Ramkumar

Good article!!

Collapse
iceorfiresite profile image
Ice or Fire

Great info!