Skip to main content

Security controls bypass or absence

Need

Implementation of robust security controls

Context

  • Usage of Ruby 2.5.0 for developing Ruby applications
  • Usage of Rails framework for building web applications

Description

Non compliant code

# app/controllers/application_controller.rb
class ApplicationController < ActionController::Base
before_action :authenticate_user

private

def authenticate_user
if session[:user_id]
@current_user = User.find(session[:user_id])
else
redirect_to login_url, alert: "Please log in to access this page"
end
end
end

# app/controllers/admin_controller.rb
class AdminController < ApplicationController
skip_before_action :authenticate_user
def dashboard
@users = User.all
end
end

In the above example, we have an ApplicationController which has a before_action callback to authenticate the user for every action in every controller that inherits from ApplicationController.

The authenticate_user method checks if there is a user_id in the session. If it exists, it sets the @current_user variable. If it doesn't, it redirects the user to the login page.

However, in the AdminController, which inherits from ApplicationController, the before_action callback to authenticate the user is skipped. This means that any user, authenticated or not, can access the actions in the AdminController without being authenticated.

This is a security vulnerability because it allows unauthorized access to potentially sensitive data or actions. It's a clear example of a security control bypass vulnerability.

Steps

  • Remove the 'skip_before_action' line in the 'AdminController' class.
  • Ensure that all controllers that require authentication have the 'before_action :authenticate_user' line.
  • Consider using a role-based access control (RBAC) system to manage user permissions.
  • Implement additional security controls such as authorization checks to restrict access to sensitive actions or resources.
  • Regularly review and update the security controls to address any new vulnerabilities or changes in the application.

Compliant code

# app/controllers/application_controller.rb
class ApplicationController < ActionController::Base
before_action :authenticate_user

private

def authenticate_user
if session[:user_id]
@current_user = User.find(session[:user_id])
else
redirect_to login_url, alert: "Please log in to access this page"
end
end
end

# app/controllers/admin_controller.rb
class AdminController < ApplicationController
def dashboard
@users = User.all
end
end

The AdminController class no longer skips the authenticate_user method from the ApplicationController class. This means that before any action in the AdminController class is performed, the system will first authenticate the user. If the user is not authenticated, they will be redirected to the login page with an alert message.

This change ensures that all controllers that require authentication have the before_action :authenticate_user line, which is a crucial security control to prevent unauthorized access.

In addition to this, it is recommended to implement a role-based access control (RBAC) system to manage user permissions. This would allow you to define roles with specific permissions and assign these roles to users, providing a more granular control over what actions a user can perform.

Furthermore, consider implementing additional security controls such as authorization checks to restrict access to sensitive actions or resources. This could involve checking if the authenticated user has the necessary permissions to perform a certain action or access a certain resource.

Lastly, it is important to regularly review and update the security controls to address any new vulnerabilities or changes in the application. This could involve regularly auditing the code, performing security tests, and staying updated on the latest security best practices and vulnerabilities.

References