I have a Django(v2.2) project hosted on an url which looks like
https://some.example.com/mypath/ which has an API endpoint at blog/create.
I need to make a POST request from https://some.example.com/anotherpath/ofmine/ (using axios), but that gives me a 301 error with the following messages in Firefox 71.0:
Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at https://some.example.com/mypath/blog/create/. (Reason: CORS header ‘Access-Control-Allow-Origin’ missing).
Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at https://some.example.com/mypath/blog/create/. (Reason: CORS request did not succeed).
However, I can easily make the same requests to a dev server hosted locally.
Relevant settings:
INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'rest_framework',
'rest_framework_docs',
'corsheaders',
'django_extensions',
...
]
USE_X_FORWARDED_HOST = True
FORCE_SCRIPT_NAME = '/mypath'
CORS_ORIGIN_ALLOW_ALL = True
What could be the reason and possible workarounds for the error?
According to the django-cors-headers docs, you need to set the CORS_ORIGIN_WHITELIST to include your endpoint(s), or set CORS_ORIGIN_ALLOW_ALL to True to allow all hosts (not recommended for production though).
Stupid mistake. some.example.com redirects to www.some.example.com so I'd been trying to access APIs at some.example.com (which doesn't exist, hence the 301) from www.some.example.com. Prefixed the www on the request url and it's working fine; I don't even need CORS headers, of course.
Related
I have a django application which is hosted in IIS (with custom URL) and its front end is hosted in Angular. The front end is showing corse related error so i tried to resolve that by adding 'corseheaders' in settings.py of my backend code. After that when i tried to access the API (by clicking the hosted URL in IIS) the following error is showing in the browser.
Error occurred while reading WSGI handler:
Traceback (most recent call last):
File "D:\TESTAPP\API\venv\Lib\site-packages\wfastcgi.py", line 791, in main
env, handler = read_wsgi_handler(response.physical_path)
Following is the changes i have done in the settings.py of my backend(django). Actually i have added the last line with "corsheaders". if its removed the error is gone.
ALLOWED_HOSTS = ['*']
CORS_ORIGIN_ALLOW_ALL = True
# Application definition
INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'rest_framework',
'survey_app.apps.SurveyAppConfig',
'corsheaders',
]
Can you guys please help me out.
The frontend showing corse related errors is due to your frontend not being on the same domain as your Django API/backend, so all Django responses need to contain CORS related headers. This article is about Cross-Origin Resource Sharing (CORS).
On how to use django-cors-headers to solve cross-domain problems, you can refer to the following steps:
1.Install the package using pip:
pip install django-cors-headers
2.Add "corseheaders" to settings.py:
INSTALLED_APPS = (
……
'corsheaders',
……
)
3.Add middleware:
MIDDLEWARE = [
...
'corsheaders.middleware.CorsMiddleware',
'django.middleware.common.CommonMiddleware',
...
]
4.Add the following configuration in settings.py:
CORS_ALLOW_CREDENTIALS = True
CORS_ORIGIN_ALLOW_ALL = True
CORS_ORIGIN_WHITELIST = (
'*'
)
CORS_ALLOW_METHODS = (
'DELETE',
'GET',
'OPTIONS',
'PATCH',
'POST',
'PUT',
'VIEW',
)
CORS_ALLOW_HEADERS = (
'XMLHttpRequest',
'X_FILENAME',
'accept-encoding',
'authorization',
'content-type',
'dnt',
'origin',
'user-agent',
'x-csrftoken',
'x-requested-with',
'Pragma',
)
For more detailed configuration, please refer to the official documentation.
I am trying to build a web app using Django Rest framework.
When I run the app on localhost 127.0.0.0/8000 it works fine. But when I deploy it on an EC2 server the POST methods return 500 server error.
Here is one of the post methods in the views.py -
class customer_location(APIView):
def post(self, request, *args, **kwargs):
customer_id = json.loads(request.body).get('customer_id')
queryset = customers.objects.filter(cid= customer_id)
serialize = customer_details(queryset, many=True)
return Response(serialize.data, status=status.HTTP_200_OK)
The urls.py is like this -
from django.conf.urls import include, url
from django.urls import path
from rest_framework import routers
from . import views
urlpatterns = [
url(r'^customer_location/$', views.customer_location.as_view(), name='customer_location'),
]
The DEBUG mode is set to False and the EC2 instance IP address is added in the ALLOWED_HOSTS.
The GET methods are working fine but the POST methods give error.
As per SENTRY ERROR LOG the issue is -
raise JSONDecodeError("Expecting value", s, err.value) from None
And this is for this line in the view.py -
customer_id = json.loads(request.body).get('customer_id')
The inbound rules of the EC2 instance allows access for HTTP, HTTPS, SSH, PostgreSQL and Custom TCP rule for port 8000.
When I run the curl command from the terminal I can get the values for the POST Method-
curl --header "Content-Type: application/json" --request POST --data '{"customer_id":"1"}' http://ec2_ip/customer_location/
output -
[{"cid":"1","name":"Rachel". "location":"NYC"}]
The curl command returns values for the POST method for the same EC2 server while the api end point on the EC2 server returns 500 server error.
How can I fix this ?
To resolve cors problem you should install django-cors-headers in your app.
At first install it by pip install django-cors-headers
Add corsheaders inside your INSTALLED_APPS in settings.py
INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'corsheaders',
.....
]
Add corsheaders.middleware.CorsMiddleware at the top of your MIDDLEWARE in settings.py
MIDDLEWARE = [
'corsheaders.middleware.CorsMiddleware',
'django.middleware.common.CommonMiddleware',
....
]
Add the below line in anywhere inside the settings.py
CORS_ORIGIN_ALLOW_ALL = True
Finally add this line in settings.py
ALLOWED_HOSTS = ['*']
If your project runs properly with this configuration, then replace the '*' with your IP address. That's it!
I am developing an application which the frontend is an AngularJS API that makes requests to the backend API developed in Django Rest Framework.
The frontend is on the domain: https://front.bluemix.net
And my backend is on the domain: https://back.bluemix.net
I am having problems making requests from the frontend API to the backend API. The error is this:
Error: CSRF Failed: Referer checking failed - https://front.bluemix.net does not match any trusted origins.
I am using CORS and I have already included the following lines in my settings.py in the Django backend API:
ALLOWED_HOSTS = []
CORS_ALLOW_CREDENTIALS = True
CORS_ORIGIN_ALLOW_ALL = True
CORS_ALLOW_CREDENTIALS = True
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net/']
CORS_REPLACE_HTTPS_REFERER = True
CSRF_COOKIE_DOMAIN = 'bluemix.net'
CORS_ORIGIN_WHITELIST = (
'https://front.bluemix.net/',
'front.bluemix.net',
'bluemix.net',
)
Anyone knows how to solve this problem?
Django 4.0 and above
For Django 4.0 and above, CSRF_TRUSTED_ORIGINS must include scheme and host, e.g.:
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net']
Django 3.2 and lower
For Django 3.2 and lower, CSRF_TRUSTED_ORIGINS must contain only the hostname, without a scheme:
CSRF_TRUSTED_ORIGINS = ['front.bluemix.net']
You probably also need to put something in ALLOWED_HOSTS...
If you are running Django 4.x, you need to change the syntax to include the schema as part of the value.
CSRF_TRUSTED_ORIGINS = ['front.bluemix.net']
to
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net']
https://docs.djangoproject.com/en/dev/releases/4.0/#format-change
For anyone who follows this, if you have set CORS_ORIGIN_ALLOW_ALL to True, then you don't need to set the CORS_ORIGIN_WHITELIST variable anymore, as you are allowing every host already.
SOLUTION TO MY PROBLEM - it might help somebody
the problem we had was a peculiar one, we have a Client application sending requests using TokenAuthentication to another application, a CRM built using Django Admin and therefore using SessionAuthentication. When we opened the Django Admin application, the SessionMiddleware was creating automatically a session_id cookie for that domain. When opening the Client application and trying to perform a request, we got the following error:
Error: CSRF Failed: Referer checking failed - https://domainofthedjangoadminapp.com does not match any trusted origins.
That was only because the session_id cookie was already set in the browser and therefore, the request was made using SessionAuthentication instead of TokenAuthentication and failing.
Removing the cookie was obviously fixing the problem.
According to this documentation. https://docs.djangoproject.com/en/4.0/releases/4.0/#csrf-trusted-origins-changes
install cors-header by: doing
pip install django-cors-headers
Add corsheaders to you installed apps
INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'MyApp',
'crispy_forms',
'corsheaders',
]
Add the corsheader Middleware to your middleware
MIDDLEWARE = [
'**corsheaders.middleware.CorsMiddleware**',
'django.middleware.security.SecurityMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
]
4 Set the origin
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net']
Apr, 2022 Update:
If your django version is "4.x.x":
python -m django --version
// 4.x.x
Then, if the error is as shown below:
Origin checking failed - https://example.com does not match any trusted origins.
Add this code below to "settings.py":
CSRF_TRUSTED_ORIGINS = ['https://example.com']
In your case, you got the similar error to above:
Error: CSRF Failed: Referer checking failed - https://front.bluemix.net does not match any trusted origins.
So, you need to add this code to your "settings.py":
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net']
I was also facing this issue. Ensure that the domain name does not contain the trailing slash. Instead of
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net/']
Change it to
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net']
I am developing an application which the frontend is an AngularJS API that makes requests to the backend API developed in Django Rest Framework.
The frontend is on the domain: https://front.bluemix.net
And my backend is on the domain: https://back.bluemix.net
I am having problems making requests from the frontend API to the backend API. The error is this:
Error: CSRF Failed: Referer checking failed - https://front.bluemix.net does not match any trusted origins.
I am using CORS and I have already included the following lines in my settings.py in the Django backend API:
ALLOWED_HOSTS = []
CORS_ALLOW_CREDENTIALS = True
CORS_ORIGIN_ALLOW_ALL = True
CORS_ALLOW_CREDENTIALS = True
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net/']
CORS_REPLACE_HTTPS_REFERER = True
CSRF_COOKIE_DOMAIN = 'bluemix.net'
CORS_ORIGIN_WHITELIST = (
'https://front.bluemix.net/',
'front.bluemix.net',
'bluemix.net',
)
Anyone knows how to solve this problem?
Django 4.0 and above
For Django 4.0 and above, CSRF_TRUSTED_ORIGINS must include scheme and host, e.g.:
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net']
Django 3.2 and lower
For Django 3.2 and lower, CSRF_TRUSTED_ORIGINS must contain only the hostname, without a scheme:
CSRF_TRUSTED_ORIGINS = ['front.bluemix.net']
You probably also need to put something in ALLOWED_HOSTS...
If you are running Django 4.x, you need to change the syntax to include the schema as part of the value.
CSRF_TRUSTED_ORIGINS = ['front.bluemix.net']
to
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net']
https://docs.djangoproject.com/en/dev/releases/4.0/#format-change
For anyone who follows this, if you have set CORS_ORIGIN_ALLOW_ALL to True, then you don't need to set the CORS_ORIGIN_WHITELIST variable anymore, as you are allowing every host already.
SOLUTION TO MY PROBLEM - it might help somebody
the problem we had was a peculiar one, we have a Client application sending requests using TokenAuthentication to another application, a CRM built using Django Admin and therefore using SessionAuthentication. When we opened the Django Admin application, the SessionMiddleware was creating automatically a session_id cookie for that domain. When opening the Client application and trying to perform a request, we got the following error:
Error: CSRF Failed: Referer checking failed - https://domainofthedjangoadminapp.com does not match any trusted origins.
That was only because the session_id cookie was already set in the browser and therefore, the request was made using SessionAuthentication instead of TokenAuthentication and failing.
Removing the cookie was obviously fixing the problem.
According to this documentation. https://docs.djangoproject.com/en/4.0/releases/4.0/#csrf-trusted-origins-changes
install cors-header by: doing
pip install django-cors-headers
Add corsheaders to you installed apps
INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'MyApp',
'crispy_forms',
'corsheaders',
]
Add the corsheader Middleware to your middleware
MIDDLEWARE = [
'**corsheaders.middleware.CorsMiddleware**',
'django.middleware.security.SecurityMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
]
4 Set the origin
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net']
Apr, 2022 Update:
If your django version is "4.x.x":
python -m django --version
// 4.x.x
Then, if the error is as shown below:
Origin checking failed - https://example.com does not match any trusted origins.
Add this code below to "settings.py":
CSRF_TRUSTED_ORIGINS = ['https://example.com']
In your case, you got the similar error to above:
Error: CSRF Failed: Referer checking failed - https://front.bluemix.net does not match any trusted origins.
So, you need to add this code to your "settings.py":
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net']
I was also facing this issue. Ensure that the domain name does not contain the trailing slash. Instead of
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net/']
Change it to
CSRF_TRUSTED_ORIGINS = ['https://front.bluemix.net']
I am getting the following error message when I try to access my endpoints.
Request header field X-FirePHP-Version is not allowed by Access-Control-Allow-Headers in preflight response.
This is how my settings.py file looks
INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'rest_framework',
'api.apps.ApiConfig',
'django_server',
'corsheaders', # For Cross-Origin Resource Sharing
]
CORS_ORIGIN_ALLOW_ALL = True
CORS_ALLOW_CREDENTIALS = False
If you have additional headers that are going to be in your requests to a CORS enabled server, you should specify those in the CORS_ALLOW_HEADERS django-cors setting. This should solve it, but I would double check to make sure those headers are supposed to be there.
# In your project's settings.py
CORS_ALLOW_HEADERS = (
'x-requested-with',
'content-type',
'accept',
'origin',
'authorization',
'x-csrftoken',
'x-firephp-version', # Added to default list
)
# more settings...
Under the hood this simply sets the Access-Control-Request-Headers header on your server's responses.