Lack of data validation - Session Cookie - Ruby

Lack of data validation - Session Cookie - Ruby

Need

Implementation of secure session cookie generation and validation

Context

  • Requirement of Ruby 2.0 or higher for running the application
  • Usage of Ruby on Rails for building web applications

Description

Non compliant code

        class SessionsController < ApplicationController
  def create
    session[:user_id] = params[:user_id]
    redirect_to root_url, notice: "Logged in!"
  end

  def destroy
    session[:user_id] = nil
    redirect_to root_url, notice: "Logged out!"
  end
end
        
        

The above code is a simple implementation of a session controller in a Ruby on Rails application. The vulnerability lies in the create method where the session[:user_id] is set directly from the parameters sent from the front-end ( params[:user_id]).

As there is no data validation, an attacker can manipulate the user_id parameter and set it to any value. This means that an attacker can hijack sessions by simply changing the user_id parameter, thus bypassing the authentication system and gaining unauthorized access to the application. This is a serious security flaw as it can lead to data breaches and other security issues.

In the destroy method, the session[:user_id] is set to nil when the user logs out. However, this does not mitigate the vulnerability in the create method.

Steps

  • Implement server-side data validation for the 'user_id' parameter in the 'create' action of the SessionsController.
  • Validate that the 'user_id' parameter is a valid user ID before assigning it to the session cookie.
  • Use a whitelist approach to validate the 'user_id' parameter, ensuring that it is a valid user ID in the system.
  • Consider using a database query or an ORM method to check the validity of the 'user_id' parameter.
  • If the 'user_id' parameter is not valid, handle the error appropriately (e.g., display an error message or redirect to an error page).
  • Ensure that the session cookie is secure by setting appropriate flags such as 'secure' and 'httponly'.
  • Consider using a secure random value for the session cookie instead of relying on the 'user_id' parameter.
  • Regularly update and patch the Ruby on Rails framework to benefit from the latest security enhancements and fixes.

Compliant code

        class SessionsController < ApplicationController
  def create
    user = User.find_by(id: params[:user_id])
    if user
      session[:user_id] = user.id
      redirect_to root_url, notice: "Logged in!"
    else
      redirect_to root_url, alert: "Invalid user ID!"
    end
  end

  def destroy
    session[:user_id] = nil
    redirect_to root_url, notice: "Logged out!"
  end
end
        
        

The updated code now includes a server-side validation for the 'user_id' parameter in the 'create' action of the SessionsController.

In the 'create' action, we first try to find a user with the ID provided in the 'user_id' parameter. If a user is found, we assign the user's ID to the session cookie and redirect to the root URL with a success message. If no user is found, we redirect to the root URL with an error message.

This approach ensures that only valid user IDs can be assigned to the session cookie, preventing attackers from setting an insecure session cookie.

In addition, the session cookie is now secure as it is tied to a valid user ID in the system.

Remember to set appropriate flags such as 'secure' and 'httponly' for the session cookie to further enhance its security.

Also, consider using a secure random value for the session cookie instead of relying on the 'user_id' parameter.

Lastly, regularly update and patch the Ruby on Rails framework to benefit from the latest security enhancements and fixes.

References