I am trying to add a token to my forms in order to prevent CSRF attacks
But the token validation isn’t working
Here is the input field which holds the token
<input type="hidden" name="auth_token" value="<?php echo $_SESSION['auth_token']; ?>">
And here is the token validation code
if ($_SERVER["REQUEST_METHOD"] == "POST") { // Validate token to avoid CSRF $auth_token = $_POST["auth_token"]; if (!$auth_token || $auth_token != $_SESSION['auth_token']) { // show an error message echo '<h1 class="error">Error: invalid form submission</h1><p>Your request was denied as this request could not be verified.</p>'; // return 405 http status code header($_SERVER['SERVER_PROTOCOL'] . ' 405 Method Not Allowed'); exit(); } // process form here }
It doesn’t work and it returns the error message in the if
block
Advertisement
Answer
I presume that the submitted auth_token
value is something random such as hwm7wherlwkju
or whatever. Testing !$auth_token
could give special results, depending if it’s missing or if it contains “1”, “true” or “”.
Secondly, use !==
instead of !=
to avoid automatic type casting in the comparaison.
So I would replace your “if” condition with this:
session_start(); // 1) Check if the recieved token is valid. if (!isset($_POST['auth_token']) || !isset($_SESSION['auth_token']) || $_POST['auth_token'] !== $_SESSION['auth_token']) { // Show an error message. echo "<h1 class="error">Error: invalid form submission</h1>n" . "<p>Your request was denied as this request could not be verified.</p>n"; // Return a 403 error. http_response_code(403); die(); } // 2) Generate a new token for the next request if you are displaying a page with a <form>. $_SESSION['auth_token'] = bin2hex(random_bytes(20));
About the token value generated, I think you should also check that you are not generating a new value in the session on each request before doing the comparaison for validation. The comparaison should be done first and then a new token value should be generated and stored in the session.