From e764efe1d4b083c7c11278936ea74d58d5d707af Mon Sep 17 00:00:00 2001 From: cktricky Date: Thu, 14 Nov 2013 09:39:57 -0500 Subject: [PATCH] working on A6 tutorial write-up now that the code is working --- .../layouts/tutorial/exposure/_ssn.html.erb | 69 ++++++++++++++----- 1 file changed, 51 insertions(+), 18 deletions(-) diff --git a/app/views/layouts/tutorial/exposure/_ssn.html.erb b/app/views/layouts/tutorial/exposure/_ssn.html.erb index 0890a3e..4e64a01 100644 --- a/app/views/layouts/tutorial/exposure/_ssn.html.erb +++ b/app/views/layouts/tutorial/exposure/_ssn.html.erb @@ -36,20 +36,13 @@ The Railsgoat application stores user's Social Security Numbers in plain-text within the database and because of this, it fails to adequately protect these numbers from theft. Additionally, the user's full SSN is sent back to the user within an HTTP response from the application.

- The WorkInfo model (app/models/work_info.rb) is missing code to encrypt this data prior to storage. Additionally, while code exists to render only the last 4 numbers of an SSN, at no time is it used. + The WorkInfo model (app/models/work_info.rb) is missing code to encrypt this data prior to storage. Additionally, while code exists to render only the last 4 numbers of an SSN (shown below), at no time is it used.

-				class WorkInfo < ActiveRecord::Base
-				  attr_accessible :DoB, :SSN, :bonuses, :income, :years_worked
-				  belongs_to :user
-
 				  # We should probably use this
 				  def last_four
-				    "***-**-" << self.SSN[-4,4]
+				    "***-**-" << self.decrypt_ssn[-4,4]
 				  end
-
-				end
-	
 			  
@@ -72,15 +65,55 @@
  • Only authorized users can access decrypted copies of the data
  • Use a strong algorithm
  • Strong key is generated, protected from unauthorized access, and key change is planned for.

  • - One additional item to note with rails specifically, the framework makes it easy to determine the type of environment running, example: -
    -					Rails.env.production?
    -				
    - ...or -
    -					Rails.env.development?
    -				
    - This allows developers to easily create different keys for development and production and should be considered an asset to utilize. While development keys are usually stored within the source code of most rails applications, and developers with access to the repo can download those keys, the same should NOT hold true for production keys. +

    + +

    + In the following code, we demonstrate switching from the storage of full SSN(s) in clear-text to storing them in the AES-256 encrypted format. The first thing to do is build the encrypt and decrypt functions. These can be found within app/models/work_info.rb. +

    +
    +				  def encrypt_ssn
    +				     aes = OpenSSL::Cipher::Cipher.new(cipher_type)
    +				     aes.encrypt
    +				     aes.key = key
    +				     aes.iv = iv if iv != nil
    +				     self.encrypted_ssn = aes.update(self.SSN) + aes.final
    +				     self.SSN = nil
    +				  end
    +
    +				  def decrypt_ssn
    +				     aes = OpenSSL::Cipher::Cipher.new(cipher_type)
    +				     aes.decrypt
    +				     aes.key = key
    +				     aes.iv = iv if iv != nil
    +				     aes.update(self.encrypted_ssn) + aes.final
    +				  end
    +				
    +				  def key
    +				    raise "Key Missing" if !(KEY)
    +				    KEY
    +				  end
    +
    +				  def iv
    +				    raise "No IV for this User" if !(self.key_management.iv)
    +				    self.key_management.iv
    +				  end
    +
    +				  def cipher_type
    +				    'aes-256-cbc'
    +				  end
    +			  
    +

    + Also within the WorkInfo model, we add the following line of code... +

    +
    +			  	 before_save :encrypt_ssn
    +			  
    +

    + The remaining pieces are: +

  • We "seed" the database with per-user initialization vectors (IV) and store them within the key_management table
  • +
  • Separate production and development encryption keys. Production keys should be stored in an HSM, environment variable, etc. but never within the source code. Development keys are irrelevant if not being used for real data
  • +
  • Change the view where SSNs are called and rendered to the user so that the "last_four" method is called instead
  • +
  • For new user's who are registering, we create an initialization specific to their account