This is an educational project, not for production. I wasn\'t intending to have user logins as part of this.
Can I make POST calls to Django with a CSRF token withou
For me, django wasn't listening to the headers that I was sending. I could curl into the api but couldn't access it with axios. Check out the cors-headers package... it might be your new best friend.
I fixed it by installing django-cors-headers
pip install django-cors-headers
And then adding
INSTALLED_APPS = (
...
'corsheaders',
...
)
and
MIDDLEWARE = [ # Or MIDDLEWARE_CLASSES on Django < 1.10
...
'corsheaders.middleware.CorsMiddleware',
'django.middleware.common.CommonMiddleware',
...
]
into my settings.py
I also had
ALLOWED_HOSTS = ['*']
CORS_ORIGIN_ALLOW_ALL = True
CORS_ALLOW_CREDENTIALS = True
CORS_EXPOSE_HEADERS = (
'Access-Control-Allow-Origin: *',
)
in my settings.py although that is probably overkill
The "easy way" almost worked for me. This seems to work:
import axios from 'axios';
axios.defaults.xsrfHeaderName = "X-CSRFTOKEN";
axios.defaults.xsrfCookieName = "XCSRF-TOKEN";
And in the settings.py file:
CSRF_COOKIE_NAME = "XCSRF-TOKEN"
I've found out, that axios.defaults.xsrfCookieName = "XCSRF-TOKEN";
and CSRF_COOKIE_NAME = "XCSRF-TOKEN"
DOESN'T WORK IN APPLE Safari on Mac OS
The solution for MAC Safari is easy, just change XCSRF-TOKEN
to csrftoken
So, in js-code should be:
import axios from 'axios';
axios.defaults.xsrfHeaderName = "X-CSRFTOKEN";
axios.defaults.xsrfCookieName = "csrftoken";
In settings.py:
CSRF_COOKIE_NAME = "csrftoken"
This configuration works for me without problems Config axios CSRF django
import axios from 'axios'
/**
* Config global for axios/django
*/
axios.defaults.xsrfHeaderName = "X-CSRFToken"
axios.defaults.xsrfCookieName = 'csrftoken'
export default axios
After spending too many hours researching, and implementing the above answer, I found my error for this problem! I have added this answer to be supplemental of the accepted answer. I had set up everything as mentioned, but the gotcha for me was actually in the browser itself!
If testing locally, make sure you are accessing react through 127.0.0.1
instead of localhost
! localhost
handles request headers differently and doesn't show the CSRF tokens in the header response, where as 127.0.0.1
will! So instead of localhost:3000
try 127.0.0.1:3000
!
Hope this helps.
There is actually a really easy way to do this.
Add axios.defaults.xsrfHeaderName = "X-CSRFToken";
to your app config and then set CSRF_COOKIE_NAME = "XSRF-TOKEN"
in your settings.py file. Works like a charm.