Prevention of automatic enumeration of corporate information
class FindingsController < ApplicationController
def show
@finding = Finding.find(params[:id])
if @finding
render json: { status: 'success', data: @finding }
else
render json: { status: 'error', message: 'Finding not found' }
end
end
end
The above code is a simple Ruby on Rails controller that retrieves a finding based on an
id
passed in through the parameters. The vulnerability lies in the difference in response when a finding exists versus when it does not exist.
When the
id
passed in the parameters corresponds to an existing finding, the server responds with the status 'success' and the data of the finding. However, when the
id
does not correspond to an existing finding, the server responds with the status 'error' and a message 'Finding not found'.
This difference in response can be exploited by an attacker to enumerate all valid finding IDs. By making requests with different IDs and observing the response, an attacker can determine which IDs correspond to real findings and which do not. This is a vulnerability because it allows an attacker to gather information about the system that they should not have access to.
class FindingsController < ApplicationController
def show
begin
@finding = Finding.find(params[:id])
render json: { status: 'success', data: @finding }
rescue ActiveRecord::RecordNotFound
render json: { status: 'error', message: 'Unable to process request' }
end
end
end
The updated code now handles the scenario where a finding with the provided ID does not exist. Instead of explicitly stating that the finding was not found, a generic error message 'Unable to process request' is returned. This prevents potential attackers from enumerating system information by observing different responses for existing and non-existing finding IDs.
The
begin
and
rescue
block is used to handle exceptions in Ruby. If the
Finding.find(params[:id])
line throws an
ActiveRecord::RecordNotFound
exception (which it will do if a finding with the provided ID does not exist), the code execution will immediately jump to the
rescue
block.
In the
rescue
block, a JSON response is rendered with a status of 'error' and a generic message 'Unable to process request'. This ensures that the response does not reveal any sensitive information about the system.