Shielding Your Actions with CSRF Tokens

Cross-Site Request Forgery (CSRF): The Pizza Order Gone Wrong

 Imagine it’s Friday evening. You’re at home, tired after a long day, and you decide to treat yourself by ordering a pizza from your favorite local pizzeria, PizzaPalace.com. You log in, place your favorite toppings into your cart, and leave the tab open while waiting for your friends to arrive.

Meanwhile, you start browsing another website, "FunnyMemes.com," to kill time. But little do you know, FunnyMemes.com is secretly run by someone who is up to no good.

The owner of FunnyMemes.com knows that PizzaPalace processes orders via a URL like this:

http://www.pizzapalace.com/order?item=AnchoviesPizza&address=YourHome

The attacker adds a hidden image or script to their page that looks like this:

 html:

<img src="http://www.pizzapalace.com/order?item=10XL-Pizzas&address=Attacker's-House" style="display:none;" />

 

Now, here’s what happens:

  • You visit FunnyMemes.com while still logged into PizzaPalace.
  • Your browser sees the hidden request for ordering 10 extra-large pizzas.
  • Because you’re logged in, your browser sends the request along with your valid session cookies from PizzaPalace.
  • PizzaPalace receives the request and processes it as if YOU ordered those pizzas.
  • The pizzas get delivered to the attacker’s address, and you get charged a ridiculous bill for pizzas you didn’t even order!

 


 

 

How CSRF Tokens Save the Day

Let’s replay the situation, but this time, PizzaPalace has CSRF protection in place:

  • When you log in to PizzaPalace, it gives your browser a special CSRF token that’s included in all your actions (like placing an order). Example:
    http://www.pizzapalace.com/order?item=AnchoviesPizza&address=YourHome&csrf_token=SUPERSECRET123
  • The token is random, unique to your session, and changes every time.
  • Now, when FunnyMemes.com tries to send their malicious request, it won’t have the correct CSRF token. The attacker can only guess, and the chances of guessing correctly are practically zero.
  • PizzaPalace’s server sees the request is missing the right token and immediately rejects it.

Result? Your pizzas are safe, your wallet is safe, and the attacker stays hungry.

 


 

 

Real-Life Analogy:

Think of the CSRF token as a pizza password. When you log in to PizzaPalace, they give you a password (CSRF token) that you need to include in every order. If someone else (the attacker) tries to place an order without knowing the password, PizzaPalace knows it’s fake and ignores it.

 


Why This Matters

Without CSRF protection, your online accounts could be hijacked in sneaky ways—like ordering pizzas you don’t want, changing your profile settings, or even signing you up for weird subscriptions. CSRF tokens act as your secret shield against such attacks.

So, the next time you log in to a website and see that little "CSRF token" in action, know that it’s quietly saving your pizza night (and much more).

 

 

So, let's dive on how we can do so in our django project...

 

To add CSRF protection in a Django project, Django provides built-in mechanisms to prevent CSRF (Cross-Site Request Forgery) attacks. Here’s how you can initialize and use CSRF tokens in your Django project:

1. Ensure and Enable the CSRF Middleware 

Django has a middleware that is enabled by default in the MIDDLEWARE setting. This middleware protects your app from CSRF attacks.

Make sure your settings.py has the following middleware enabled:

python

MIDDLEWARE = [ ... 'django.middleware.csrf.CsrfViewMiddleware', # This line ensures CSRF protection ... ]

2. Use CSRF Tokens in Templates

For any form that performs actions that modify data (such as POST requests), you need to include the CSRF token to protect against CSRF attacks.

Django provides a simple way to include the CSRF token in your templates. Add the {% csrf_token %} template tag inside the <form> tags:

 

html

<form method="POST" action="/order/"> {% csrf_token %} <input type="text" name="item" value="AnchoviesPizza"> <input type="text" name="address" value="YourHome"> <button type="submit">Place Order</button> </form>

The {% csrf_token %} tag generates a hidden input field with a unique token that Django can verify when the form is submitted.

3. CSRF Token in AJAX Requests

If you're using JavaScript (e.g., via AJAX) to send POST requests to the server, you need to include the CSRF token in the request headers.

First, get the CSRF token from the cookie:

 

 

javascript

function getCookie(name) { let cookieValue = null;

if (document.cookie && document.cookie !== '') {

const cookies = document.cookie.split(';');

for (let i = 0; i < cookies.length; i++)

{ const cookie = cookies[i].trim();

if (cookie.substring(0, name.length + 1) === (name + '=')) {

cookieValue = decodeURIComponent(cookie.substring(name.length + 1)); break;

} } }

return cookieValue;

}

const csrfToken = getCookie('csrftoken');

 

 

Then, include the token in your AJAX request:

javascript

fetch('/order/', {

method: 'POST',

headers: { 'Content-Type':

'application/json', 'X-CSRFToken': csrfToken, // Include CSRF token in header

},

body: JSON.stringify({ item: 'AnchoviesPizza', address: 'YourHome'

})

})

.then(response => response.json())

.then(data => console.log(data))

.catch(error => console.error('Error:', error));

 

 

 

4. CSRF in External Requests

If you're dealing with external requests (like a third-party website trying to interact with your server), ensure that your views are CSRF-protected, and handle requests appropriately. You can disable CSRF protection for specific views (if absolutely necessary) using the @csrf_exempt decorator, but this should be avoided unless you're sure it's safe.

 

For example, if you want to disable CSRF for a specific view:

python

from django.views.decorators.csrf import csrf_exempt @csrf_exempt

def external_view(request): # Handle external requests without CSRF protection ...

 

 

5. Testing CSRF Protection

Once CSRF protection is set up, it should automatically block requests that don’t include the correct token. If an attacker tries to make a malicious request (such as through the hidden image or script example in your story), Django will reject the request because it lacks the proper CSRF token.

 

 

Finally:

  • Ensure CSRF middleware is enabled in MIDDLEWARE in settings.py.
  • Include {% csrf_token %} inside your forms to send the token with requests.
  • For AJAX requests, include the CSRF token in the request headers using JavaScript.
  • Test your CSRF protection by attempting to submit forms or AJAX requests without the token (they should be rejected).

 

 

Just like the pizza example, when an attacker tries to make unauthorized requests on behalf of your users, Django's CSRF protection steps in, verifies the token, and blocks the attack. This adds a crucial layer of security to your web application..

 

 

Back